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

📄 imgsftal.c

📁 M-System DOC(Disk on a Chip) Flash芯片映像读写工具, 可以进行二片Flash芯片的内容互相拷贝, 提高烧录程序的效率.
💻 C
📖 第 1 页 / 共 3 页
字号:
	pBuff[14]=fh->bBdks;
}
#endif

static void Buffer2MediaHeader(MediaHeader*fh,EXBYTE*pBuff)
{
	ExMemSet(fh,0,sizeof(MediaHeader));
	fh->wFlashType=pBuff[1];
	fh->wFlashType<<=8;
	fh->wFlashType+=pBuff[0];
	fh->dwMediaSize=pBuff[5];
	fh->dwMediaSize<<=8;
	fh->dwMediaSize+=pBuff[4];
	fh->dwMediaSize<<=8;
	fh->dwMediaSize+=pBuff[3];
	fh->dwMediaSize<<=8;
	fh->dwMediaSize+=pBuff[2];
	fh->dwOsakver=pBuff[9];
	fh->dwOsakver<<=8;
	fh->dwOsakver+=pBuff[8];
	fh->dwOsakver<<=8;
	fh->dwOsakver+=pBuff[7];
	fh->dwOsakver<<=8;
	fh->dwOsakver+=pBuff[6];
	fh->bFloors=pBuff[10];
	fh->bMediaType=pBuff[11];
	fh->bPercentUsed=pBuff[12];
	fh->bBdtls=pBuff[13];
	fh->bBdks=pBuff[14];
}

#ifndef PUTIMAGE
static void PartitionHeader2Buffer(PartitionHeader*ph,EXBYTE*pBuff)
{
	ExMemSet(pBuff,0,PARTITION_HEADER_SIZE);

	pBuff[0]=(EXBYTE)ph->dwSize;
	pBuff[1]=(EXBYTE)(ph->dwSize>>8);
	pBuff[2]=(EXBYTE)(ph->dwSize>>16);
	pBuff[3]=(EXBYTE)(ph->dwSize>>24);
	pBuff[4]=(EXBYTE)ph->dwSpares;
	pBuff[5]=(EXBYTE)(ph->dwSpares>>8);
	pBuff[6]=(EXBYTE)(ph->dwSpares>>16);
	pBuff[7]=(EXBYTE)(ph->dwSpares>>24);
	pBuff[8]=(EXBYTE)ph->dwFlags;
	pBuff[9]=(EXBYTE)(ph->dwFlags>>8);
	pBuff[10]=(EXBYTE)(ph->dwFlags>>16);
	pBuff[11]=(EXBYTE)(ph->dwFlags>>24);
	pBuff[12]=ph->pProtKey[0];
	pBuff[13]=ph->pProtKey[1];
	pBuff[14]=ph->pProtKey[2];
	pBuff[15]=ph->pProtKey[3];
	pBuff[16]=ph->pProtKey[4];
	pBuff[17]=ph->pProtKey[5];
	pBuff[18]=ph->pProtKey[6];
	pBuff[19]=ph->pProtKey[7];
	pBuff[20]=ph->bProtType;
	pBuff[21]=(EXBYTE)(ph->wSectorPerUnit);
	pBuff[22]=(EXBYTE)(ph->wSectorPerUnit>>8);
	pBuff[23]=(EXBYTE)ph->dwMTDFlags;
	pBuff[24]=(EXBYTE)(ph->dwMTDFlags>>8);
	pBuff[25]=(EXBYTE)(ph->dwMTDFlags>>16);
	pBuff[26]=(EXBYTE)(ph->dwMTDFlags>>24);
}
#endif

static void Buffer2PartitionHeader(PartitionHeader*ph,EXBYTE*pBuff)
{
	ExMemSet(ph,0,sizeof(PartitionHeader));

	ph->dwSize=pBuff[3];
	ph->dwSize<<=8;
	ph->dwSize+=pBuff[2];
	ph->dwSize<<=8;
	ph->dwSize+=pBuff[1];
	ph->dwSize<<=8;
	ph->dwSize+=pBuff[0];

	ph->dwSpares=pBuff[7];
	ph->dwSpares<<=8;
	ph->dwSpares+=pBuff[6];
	ph->dwSpares<<=8;
	ph->dwSpares+=pBuff[5];
	ph->dwSpares<<=8;
	ph->dwSpares+=pBuff[4];

	ph->dwFlags=pBuff[11];
	ph->dwFlags<<=8;
	ph->dwFlags+=pBuff[10];
	ph->dwFlags<<=8;
	ph->dwFlags+=pBuff[9];
	ph->dwFlags<<=8;
	ph->dwFlags+=pBuff[8];

	ph->pProtKey[0]=pBuff[12];
	ph->pProtKey[1]=pBuff[13];
	ph->pProtKey[2]=pBuff[14];
	ph->pProtKey[3]=pBuff[15];
	ph->pProtKey[4]=pBuff[16];
	ph->pProtKey[5]=pBuff[17];
	ph->pProtKey[6]=pBuff[18];
	ph->pProtKey[7]=pBuff[19];

	ph->bProtType=pBuff[20];

	ph->wSectorPerUnit=pBuff[22];
	ph->wSectorPerUnit<<=8;
	ph->wSectorPerUnit+=pBuff[21];

	ph->dwMTDFlags=pBuff[26];
	ph->dwMTDFlags<<=8;
	ph->dwMTDFlags+=pBuff[25];
	ph->dwMTDFlags<<=8;
	ph->dwMTDFlags+=pBuff[24];
	ph->dwMTDFlags<<=8;
	ph->dwMTDFlags+=pBuff[23];
}

#ifndef PUTIMAGE
static void DataHeader2Buffer(DataHeader*ui,EXBYTE*pBuff)
{
	ExMemSet(pBuff,0,UNIT_DATA_SIZE);

	pBuff[0]=(EXBYTE)ui->dwUnit;
	pBuff[1]=(EXBYTE)(ui->dwUnit>>8);

	pBuff[2]=(EXBYTE)ui->dwSector;
	pBuff[3]=(EXBYTE)(ui->dwSector>>8);

	pBuff[4]=(EXBYTE)ui->wDataLen;
	pBuff[5]=(EXBYTE)(ui->wDataLen>>8);

	pBuff[6]=(EXBYTE)(ui->dataType);
	pBuff[7]=ui->bFloor;
	pBuff[8]=ui->bPart;
}
#endif

static void Buffer2DataHeader(DataHeader*ui,EXBYTE*pBuff)
{
	ExMemSet(ui,0,sizeof(DataHeader));

	ui->dwUnit=pBuff[1];
	ui->dwUnit<<=8;
	ui->dwUnit+=pBuff[0];

	ui->dwSector=pBuff[3];
	ui->dwSector<<=8;
	ui->dwSector+=pBuff[2];

	ui->wDataLen=pBuff[5];
	ui->wDataLen<<=8;
	ui->wDataLen+=pBuff[4];

	ui->dataType=pBuff[6];
	ui->bFloor=pBuff[7];
	ui->bPart=pBuff[8];
}

#ifndef PUTIMAGE
static ExStatus EXAPI GetFromDoc()
{
#ifdef HW_PROTECTION
	EXBYTE b;
#endif /* HW_PROTECTION */
	EXBYTE bPart,bParts,bFloor;
	FLExtendedDiskInfo infoSrc,infoSrcFloor;
	EXDWORD dwNumberOfVirtUnitOnPreviousFloors[MAX_FLOORS];	/* contains number of  virtual unit of the partition on previous floors */
	PhysicalInfo physicalInfoSrc;
	FLFlash*flashSrc;


	/* itit PutImage() */
	dataHeader.dataType=DT_INIT;
	dataHeader.bFloor=0xff;
	dataHeader.bPart=0xff;
	CheckStat(ProgressBarManager());
	CheckStat(PutImage());

    flashSrc=flFlashOf(params.bSocketSrc);
	CheckStat(flGetPhysicalInfo(IoreqSrc(0,0,&physicalInfoSrc,0,0)));
	infoSrc.dwStructSize=sizeof(infoSrc);
	infoSrcFloor.dwStructSize=sizeof(infoSrcFloor);
	CheckStat(flGetExtendedDiskInfo(IoreqSrc(0,0,&infoSrc,FL_ALL_FLOORS,0)));

	/* check media supported */
	switch(physicalInfoSrc.mediaType)
	{
	case FL_DOC_OREN:
	case FL_MDOC512_G3:
	case FL_MDOC256_P3:

#ifdef FL_MALLOC
		if((pExtra=(EXBYTE *)ExMemAlloc(flashSrc->sharedSectors*16))==EXNULL)
			return EX_MALLOC_ERROR;
#else
		pExtra = extra_area;
#endif

		break;
	default:
		ExSprintf((char*)pError,"Media type %d == %s not supported",physicalInfoSrc.mediaType,TranslateTffsDocType(physicalInfoSrc.mediaType));
		return EX_USER_CUSTOM_ERROR;
	}

	ExSprintf((char*)pMsg,"Source: %s %dMB\n\n",TranslateTffsDocType(physicalInfoSrc.mediaType),physicalInfoSrc.mediaSize>>20);
	WriteMsgDevice(&msgDev,pMsg);

#ifdef HW_PROTECTION
	for(b=0;b<=1;b++)
	{
		switch(params.srcPass[b].bPartType)
		{
		case 0:	/* binary */
			CheckStat(bdkInsertProtectionKey(IoreqSrc(params.srcPass[b].bPart,0,params.srcPass[b].pPassword,0,0)));
			break;
		case 1:	/* BDTL */
			CheckStat(flInsertProtectionKey(IoreqSrc(params.srcPass[b].bPart,0,params.srcPass[b].pPassword,0,0)));
			break;
		default:
			b=2;
			break;
		}
	}
#endif /* HW_PROTECTION */

	ExMemSet(&mediaHeader,0,sizeof(MediaHeader));
	ExMemSet(pPartitionHeader,0,(EXWORD)(VOLUMES*sizeof(PartitionHeader)));

	/* fill media header */
	mediaHeader.wFlashType=physicalInfoSrc.type;
	mediaHeader.dwMediaSize=physicalInfoSrc.mediaSize;
	mediaHeader.dwOsakver=infoSrc.dwTrueFFSVersion;
	mediaHeader.bFloors=infoSrc.bNoOfFloors;
	mediaHeader.bMediaType=physicalInfoSrc.mediaType;
	mediaHeader.bPercentUsed=(EXBYTE)infoSrc.dwPercentUsed;
	mediaHeader.bBdtls=infoSrc.bNoOfDiskPartitions;
	mediaHeader.bBdks=infoSrc.bNoOfBinaryPartitions;
	bParts=(EXBYTE)(mediaHeader.bBdks+mediaHeader.bBdtls);

	/* fill partition headers */
	for(bPart=0;bPart<bParts;bPart++)
	{
		CheckStat(flGetExtendedDiskInfo(IoreqSrc(0,bPart<mediaHeader.bBdks?FL_BDK_PARTITION:FL_DISK_PARTITION,&infoSrc,FL_ALL_FLOORS /* sizeof(infoSrc) */,(bPart<mediaHeader.bBdks)?bPart:bPart-mediaHeader.bBdks)));
		pPartitionHeader[bPart].dwSpares=infoSrc.dwSpareUnits;

#ifdef HW_PROTECTION
		if (bPart>=mediaHeader.bBdks)
			stat = flIdentifyProtection(IoreqSrc(bPart-mediaHeader.bBdks,0,EXNULL,0,0));
		else
			stat = bdkIdentifyProtection(IoreqSrc(bPart,0,EXNULL,0,0));

		if(stat!=flOK && stat!=flNotProtected)
		{
			CheckStat(stat);
		}
		if(ioreqSrc.irFlags&PROTECTABLE && !(ioreqSrc.irFlags&KEY_INSERTED))
			return flHWProtection;
		pPartitionHeader[bPart].bProtType=(EXBYTE)ioreqSrc.irFlags&(~KEY_INSERTED);
#endif /* HW_PROTECTION */


		pPartitionHeader[bPart].dwFlags=0;

		/* fill partition flags */
		if(!(infoSrc.dwPartitionFlags&SAFTL_ADVANCED_MATCHING))
			pPartitionHeader[bPart].dwFlags|=TL_SIMPLE_MATCHING;
		if(infoSrc.dwPartitionFlags&SAFTL_REL_PARTITION)
			pPartitionHeader[bPart].dwFlags|=TL_FORCE_REL;
		if(infoSrc.dwPartitionFlags&SAFTL_FAST_PARTITION)
			pPartitionHeader[bPart].dwFlags|=TL_FAST_MODE;
		if(infoSrc.dwPartitionFlags&SAFTL_NO_MATCHING)
			pPartitionHeader[bPart].dwFlags|=TL_NO_PLANES;

		/* fill MTD flags */
		pPartitionHeader[bPart].dwMTDFlags=MTD_DATA|MTD_EXTRA;
		if(pPartitionHeader[bPart].dwFlags&TL_FORCE_REL)
			pPartitionHeader[bPart].dwMTDFlags|=MTD_REL_MODE;
		if(pPartitionHeader[bPart].dwFlags&TL_FAST_MODE)
			pPartitionHeader[bPart].dwMTDFlags|=MTD_FAST_MODE;
		if(pPartitionHeader[bPart].dwFlags&TL_NO_PLANES)
			pPartitionHeader[bPart].dwMTDFlags|=MTD_NO_MATCHING;

		pPartitionHeader[bPart].wSectorPerUnit=(EXWORD)(infoSrc.dwUnitSize>>9);
		if((pPartitionHeader[bPart].dwFlags & TL_FORCE_REL)&&(flashSrc->flashTechnology & FL_SUPPORT_MLC))
		{
			if((pPartitionHeader[bPart].dwFlags & TL_FAST_MODE) && (flashSrc->flashTechnology & FL_SUPPORT_FAST))
				pPartitionHeader[bPart].wSectorPerUnit>>=1;
			else
				if(flashSrc->flashTechnology & FL_SUPPORT_RELIABLE)
					pPartitionHeader[bPart].wSectorPerUnit>>=1;
		}
		pPartitionHeader[bPart].dwSize=(infoSrc.dwVirtualUnits*pPartitionHeader[bPart].wSectorPerUnit)<<9;
	}

	/* set src's password to media header */
	if(params.chPass[0].bPartType!=2)
		ExMemCpy(pPartitionHeader[params.chPass[0].bPartType==0?params.chPass[0].bPart:params.chPass[0].bPart+mediaHeader.bBdks].pProtKey,params.chPass[0].pPassword,8);
	else
		if(params.srcPass[0].bPartType!=2)
			ExMemCpy(pPartitionHeader[params.srcPass[0].bPartType==0?params.srcPass[0].bPart:params.srcPass[0].bPart+mediaHeader.bBdks].pProtKey,params.srcPass[0].pPassword,8);

	if(params.chPass[1].bPartType!=2)
		ExMemCpy(pPartitionHeader[params.chPass[1].bPartType==0?params.chPass[1].bPart:params.chPass[1].bPart+mediaHeader.bBdks].pProtKey,params.chPass[1].pPassword,8);
	else
		if(params.srcPass[1].bPartType!=2)
			ExMemCpy(pPartitionHeader[params.srcPass[1].bPartType==0?params.srcPass[1].bPart:params.srcPass[1].bPart+mediaHeader.bBdks].pProtKey,params.srcPass[1].pPassword,8);

	/* call PutImage() to format */
	dataHeader.dwSector=0xffff;
	dataHeader.dwUnit=0xffff;
	dataHeader.wDataLen=MEDIA_HEADER_SIZE+PARTITION_HEADER_SIZE*bParts;
	dataHeader.dataType=DT_FORMAT;
	CheckStat(ProgressBarManager());
	CheckStat(PutImage());

	/* read OTP */
# ifdef HW_OTP
	CheckStat(flInquireCapabilities(IoreqSrc(0,0,EXNULL,SUPPORT_OTP_AREA,0)));
	if(ioreqSrc.irLength==CAPABILITY_SUPPORTED)
	{
		CheckStat(flOTPSize(IoreqSrc(0,0,EXNULL,0,0)));
		if(ioreqSrc.irFlags==LOCKED_OTP && ioreqSrc.irLength<0x6800)		/* OTP written */
		{
			dataHeader.wDataLen=(EXWORD)ioreqSrc.irLength;
			dataHeader.wDataLen=(dataHeader.wDataLen>>4)<<4;
			if(dataHeader.wDataLen!=(EXWORD)ioreqSrc.irLength)
				dataHeader.wDataLen+=16;
			CheckStat(flOTPRead(IoreqSrc(0,0,pMain,ioreqSrc.irLength,0)));

			/* call PutImage() to write OTP */
			dataHeader.dataType=DT_OTP;
			dataHeader.bFloor=0xff;
			dataHeader.bPart=0xff;
			dataHeader.dwSector=0;
			dataHeader.dwUnit=0;
			CheckStat(ProgressBarManager());
			CheckStat(PutImage());
		}
	}
# endif /* HW_OTP */

	/* read IPL */
#ifndef NO_IPL_CODE
	dataHeader.wDataLen=(EXWORD)infoSrc.dwIPLSize;
	CheckStat(flReadIPL(IoreqSrc(0,0,pMain,dataHeader.wDataLen,0)));
	dataHeader.dataType=DT_IPL;
	dataHeader.bFloor=0xff;
	dataHeader.bPart=0xff;
	dataHeader.dwSector=0;
	dataHeader.dwUnit=0;
	CheckStat(ProgressBarManager());
	CheckStat(PutImage());
#endif	/* NO_IPL_CODE */

	/* read BBT */
	flashSrc->args.noOfUnits=(EXWORD)(physicalInfoSrc.mediaSize/infoSrc.dwUnitSize);

#ifdef FL_MALLOC
	if((pBbtSrc=(EXBYTE *)ExMemAlloc((EXWORD)flashSrc->args.noOfUnits))==EXNULL)	/* free in BdkSrc */
		return EX_MALLOC_ERROR;
#else
	pBbtSrc = src_bbt_table;
#endif

	flashSrc->args.readMainBuf=pBbtSrc;
	flashSrc->args.startUnit=0;
	CheckStat(flashSrc->readBBT(flashSrc));

	/* read partitions */
	dwNumberOfVirtUnitOnPreviousFloors[0]=dwNumberOfVirtUnitOnPreviousFloors[1]=dwNumberOfVirtUnitOnPreviousFloors[2]=dwNumberOfVirtUnitOnPreviousFloors[3]=0;
	for(bFloor=0;bFloor<mediaHeader.bFloors;bFloor++)
	{
		dataHeader.bFloor=bFloor;
		for(bPart=0;bPart<bParts;bPart++)
		{
			EXDWORD dwVirtUnitOfFloor;
			
			/* check that the part exist on the floor */
			CheckStat(flGetExtendedDiskInfo(IoreqSrc(0,(bPart<mediaHeader.bBdks)?FL_BDK_PARTITION:FL_DISK_PARTITION,&infoSrcFloor,bFloor,(bPart<mediaHeader.bBdks)?bPart:bPart-mediaHeader.bBdks)));
			if(!infoSrcFloor.dwVirtualUnits)
				continue;
			
			dataHeader.bPart=bPart;

			if(bPart<mediaHeader.bBdks)	/* read BDK part */
			{
				EXDWORD dwPhyUnit=infoSrcFloor.dwFirstUnit;
				if(dwPhyUnit==0)	/* part continued from previous floor - skip media header unit */
					dwPhyUnit=infoSrcFloor.wHeaderLocation+infoSrcFloor.bHeaderUnits;

				dataHeader.dataType=DT_BDK;

				for(dwVirtUnitOfFloor=0;dwVirtUnitOfFloor<infoSrcFloor.dwVirtualUnits;dwVirtUnitOfFloor++,dwPhyUnit++)
				{
					EXWORD wSectorOfUnit;		/* sector offset from begin of unit */
					EXWORD wReadedSectors=0;	/* number of sectors in data chunk */

					/* skip bad block */
					while(pBbtSrc[dwPhyUnit]!=BBT_GOOD_UNIT)
						dwPhyUnit++;
					
					/* read current unit */
					for(wSectorOfUnit=0;wSectorOfUnit<pPartitionHeader[bPart].wSectorPerUnit;wSectorOfUnit++)
					{
						EXBYTE*pTmp=pMain+wReadedSectors*512;

						/* read 1 sector with ECC */
						flashSrc->args.noOfSectors=1;
						flashSrc->args.startSector=dwPhyUnit*(FLDword)pPartitionHeader[bPart].wSectorPerUnit+wSectorOfUnit;
						flashSrc->args.readMainBuf=pTmp;
						flashSrc->args.extraBuf=pTmp+512;
						flashSrc->args.opFlags=pPartitionHeader[bPart].dwMTDFlags;
						stat=flashSrc->flashRead(flashSrc);

						if(stat==EX_OK)
						{
							/* calculate ECC for readed sector */
							pTmp[519]=Hamming_Parity(pTmp+512,7);
							BCH_Parity(pTmp,520,pTmp+520);
							pTmp[527] = 0xFF;
							/* all extra areas should be after all data areas */
							ExMemCpy(pExtra+(wReadedSectors<<4),pTmp+512,16);

							if(wReadedSectors==0)	/* it's first sector in the data chunk, so copy its address to dataHeader */
							{
								dataHeader.dwUnit=dwVirtUnitOfFloor;
								dataHeader.dwSector=wSectorOfUnit;
							}
							wReadedSectors++;
						}
						/* we do put image if:	we read something AND 										*/
						/*  (empty sector found in this session OR we read 4 (8) sectors OR unit is over)	*/
						if( wReadedSectors && (stat!=EX_OK || !((wSectorOfUnit+1)%flashSrc->sharedSectors) || (wSectorOfUnit+1==pPartitionHeader[bPart].wSectorPerUnit)) )	/* sector empty or we reached end of data chunk or end of unit - flush the data */
						{
							/* copy extra areas to the end of data chunk */
							ExMemCpy(pMain+(wReadedSectors<<9),pExtra,wReadedSectors<<4);

							/* call PutImage() to write the BDK data */
							dataHeader.wDataLen=528*wReadedSectors;
							CheckStat(ProgressBarManager());
							CheckStat(PutImage());

							/* start new data chunk */

⌨️ 快捷键说明

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