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

📄 romprg.c

📁 S3C44B得FLASH烧片程序
💻 C
字号:

#include "option.h"
#include "44b.h"
#include "romdef.h"
#include "def.h"

INT8U SST39VF160_ProgFlash(INT32U ulRealAddr,INT16U usData);
void SST39VF160_EraseSector(INT32U TargetAddr);
INT32U SST39VF160_CheckId(void);
INT8U BlankCheck(INT32U ulTargetAddr,INT32U ulTargetSize);
INT8U _WAIT(void);
void LedDisp(int LedStatus);
#define _WR(ulADDR,usDATA)	*((volatile INT16U *)(ulADDR<<1))=(INT16U)usDATA		//the addr should be shifted
#define _RD(ulADDR)		(*((volatile INT16U *)(ulADDR<<1)))	
#define _RESET()		_WR(0x0,0xf0f0)		
#define BADDR2WADDR(ulADDR)	(ulADDR>>1)		
INT8U CheckBlank(INT32U ulRomAddr,INT32U ulRomSize) 
{
	INT32U i;
	for (i=ulRomAddr;i<(ulRomAddr+ulRomSize);i+=4)
	{
		if(*((volatile INT32U *)i)!=0xffffffff)
			return 0;
	}
	return 1;	//every cell is 0xffffffff
}
INT8U Verify(INT32U ulRomAddr,INT32U ulRamAddr,INT32U ulRomSize)
{
	INT32U i;
	for (i=0x0;i<ulRomSize;i+=4)
	{
		if(*((volatile INT32U *)(i+ulRomAddr))!=*((volatile INT32U *)(i+ulRamAddr)))
			return 0;	//the data is ROM and RAM is different!
	}
	
	return 1;
}

INT8U _WAIT(void) //Check if the bit6 toggle ends.
{
	volatile INT16U flashStatus,old;
	old=*((volatile INT16U *)0x0);

	while(1)
	{
		flashStatus=*((volatile INT16U *)0x0);
		if( (old&0x40) == (flashStatus&0x40) )
			break;
		old=flashStatus;
	}
	return 1;
}
INT32U SST39VF160_CheckId(void)
{
	INT16U usManId,usDevId;

	_RESET();
    
	_WR(SeqAddr1,SeqCom1);
	_WR(SeqAddr2,SeqCom2);
	_WR(SeqAddr1,SoftIdEntry);
	usManId=_RD(ManuIdAddr);
	usDevId=_RD(DevIdAddr);

	_RESET(); 
    
	return ((usManId<<16)+usDevId);
}
INT8U SST39VF160_WordProg_Test(INT32U ulAddr,INT16U usData)
{
	_WR(SeqAddr1,SeqCom1);
	_WR(SeqAddr2,SeqCom2);
	_WR(SeqAddr1,WordProg);
	_WR(ulAddr,usData);

	return _WAIT();
}

INT8U SST39VF160_ChipErase(void)
{
	_WR(SeqAddr1,SeqCom1);
	_WR(SeqAddr2,SeqCom2);
	_WR(SeqAddr1,Erase);
	_WR(SeqAddr1,SeqCom1);
	_WR(SeqAddr2,SeqCom2);
	_WR(SeqAddr1,ChipErase);

	return 1;
}
INT8U SST39VF160_ChipProg(INT32U ulRomAddr,INT32U ulRamAddr,INT32U ulRomSize)
{
	INT32U i,j,ulRomAddrOri,ulRamAddrOri,ulRomSizeOri;
	static int LedCount=0;
	INT16U usData;
	ulRomAddrOri	=ulRomAddr;
	ulRamAddrOri	=ulRamAddr;
	ulRomSizeOri	=ulRomSize;
	SST39VF160_ChipErase();				//I think this can be remove
	for(i=0;i<65536;i++);
	for(i=0;i<65536;i++);
	for(i=0;i<(ulRomSize/2);i++)
	{
		for(j=0;j<20;j++);
		if((i%(50*1024))==0)
			LedCount=(LedCount+1)%4;
		switch(LedCount)
		{
		case 0:
			LedDisp(0x1);
			break;
		case 1:
			LedDisp(0x2);
			break;
		case 2:
			LedDisp(0x4);
			break;
		case 3:
			LedDisp(0x8);
			break;
		}
		usData=*(INT16U *)ulRamAddr;
		SST39VF160_WordProg_Test(ulRomAddr,usData);
		ulRomAddr++;
		ulRamAddr+=2;
	} 
	return (Verify(ulRomAddrOri,ulRamAddrOri,ulRomSizeOri));	//program done
}
void Delay(INT32 time)
// time=0: adjust the Delay function by WatchDog timer.
// 100us resolution.
{
    INT32 i,adjust=0;
    INT32 delayLoopCount= 400;
    if(time==0) 
    {
	time=200;adjust=1;
	delayLoopCount=400;
	rWTCON=((MCLK/1000000-1)<<8)|(2<<3);
	rWTDAT=0xffff;
	rWTCNT=0xffff;	 
	rWTCON=((MCLK/1000000-1)<<8)|(2<<3)|(1<<5); 		// 1/64/(65+1),nRESET,interrupt  disable
    }								//if
    for(;time>0;time--)
	for(i=0;i<delayLoopCount;i++);

    	if(adjust==1) {
		rWTCON=((MCLK/1000000-1)<<8)|(2<<3);
		i=0xffff-rWTCNT;   				//  1count/16us
		delayLoopCount=8000000/(i*64);			//400*100/(i*64/200)   
    		}						//if
}//Delay
void PortInit(void)
{
	//LED4->PE7
	//LED5->PE6
	//LED6->PE5
	//LED7->PE4
	//PORT F GROUP
	/*  Bit8|7   |6	  |5   |4    |3	   |2	  |10		*/   
	/*  LED1|LED2|LED3|LED4|Input|Input|IICSDA|IICSCL	*/
	/*  001 |001 |001 |001 |00   |00   |00	  |10	10	*/
	rPDATF = 0x0;
	rPCONF = 0x09240a;
	rPUPF  = 0x1e3;
	
}
/******************** S3C44B0X EV. BOARD LED **********************/

void LedDisp(int LedStatus)
{
	unsigned int porttemp;
	LedStatus =~LedStatus;
	LedStatus &=0xf;
	porttemp=rPDATF&0x1f;
	rPDATF=porttemp|(LedStatus<<5);
}

void Main(void)
{

	rSYSCFG=CACHECFG;	// 在 此 处 设 断 点 , 停 下 来 后 用 get file 调 入 文 件 , 再 继 续 运 行 .
	PortInit();

//	if(*((volatile INT32U *)(0x0c300000)) != 0xea000006)  // 用 于 防 止 用 户 烧 录 错 误 的 程 序
//		while(1); 	// 如 果 程 序 停 在 这 里 ,说 明 该 地 址 数 据 不 正  确 ,需 要 重 新 GetFile
		
	SST39VF160_ChipProg(0x0,0x0c300000,RomSize);
	
				//在 下 面 的 while(1) 处 设 1 个 断 点 , 烧 片 完 成 后 会 停 下 来 .
	while(1);
}

⌨️ 快捷键说明

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