예제 #1
0
void yaffs_UnpackTags2TagsPart(yaffs_ExtendedTags *t,
		yaffs_PackedTags2TagsPart *ptt)
{

	memset(t, 0, sizeof(yaffs_ExtendedTags));

	yaffs_InitialiseTags(t);

	if (ptt->sequenceNumber != 0xFFFFFFFF) {
		t->blockBad = 0;
		t->chunkUsed = 1;
		t->objectId = ptt->objectId;
		t->chunkId = ptt->chunkId;
		t->byteCount = ptt->byteCount;
		t->chunkDeleted = 0;
		t->serialNumber = 0;
		t->sequenceNumber = ptt->sequenceNumber;

		/* Do extra header info stuff */

		if (ptt->chunkId & EXTRA_HEADER_INFO_FLAG) {
			t->chunkId = 0;
			t->byteCount = 0;

			t->extraHeaderInfoAvailable = 1;
			t->extraParentObjectId =
			    ptt->chunkId & (~(ALL_EXTRA_FLAGS));
			t->extraIsShrinkHeader =
			    (ptt->chunkId & EXTRA_SHRINK_FLAG) ? 1 : 0;
			t->extraShadows =
			    (ptt->chunkId & EXTRA_SHADOWS_FLAG) ? 1 : 0;
			t->extraObjectType =
			    ptt->objectId >> EXTRA_OBJECT_TYPE_SHIFT;
			t->objectId &= ~EXTRA_OBJECT_TYPE_MASK;

			if (t->extraObjectType == YAFFS_OBJECT_TYPE_HARDLINK)
				t->extraEquivalentObjectId = ptt->byteCount;
			else
				t->extraFileLength = ptt->byteCount;
		}
예제 #2
0
static int write_chunk(__u8 *data, __u32 objId, __u32 chunkId, __u32 nBytes)
{
	char spare[spareSize];
	yaffs_ExtendedTags t;
	yaffs_PackedTags2 *pt = (yaffs_PackedTags2 *)spare;

	memset(spare, 0xff, spareSize);

	error = write(outFile,data,chunkSize);
	if(error < 0) return error;

	yaffs_InitialiseTags(&t);
	
	t.chunkId = chunkId;
//	t.serialNumber = 0;
	t.serialNumber = 1;	// **CHECK**
	t.byteCount = nBytes;
	t.objectId = objId;
	
	t.sequenceNumber = YAFFS_LOWEST_SEQUENCE_NUMBER;

// added NCB **CHECK**
	t.chunkUsed = 1;

	nPages++;

	yaffs_PackTags2(pt,&t);

	if (convert_endian)
	{
		little_to_big_endian(pt);
	}
	
//	return write(outFile,&pt,sizeof(yaffs_PackedTags2));
	return write(outFile,spare, spareSize);
	
}
예제 #3
0
void yaffs_UnpackTags2(yaffs_ExtendedTags * t, yaffs_PackedTags2 * pt)
{

	memset(t, 0, sizeof(yaffs_ExtendedTags));

	yaffs_InitialiseTags(t);

	if (pt->t.sequenceNumber != 0xFFFFFFFF) {
		/* Page is in use */
#ifdef YAFFS_IGNORE_TAGS_ECC
		{
			t->eccResult = YAFFS_ECC_RESULT_NO_ERROR;
		}
#else
		{
			yaffs_ECCOther ecc;
			int result;
			yaffs_ECCCalculateOther((unsigned char *)&pt->t,
						sizeof
						(yaffs_PackedTags2TagsPart),
						&ecc);
			result =
			    yaffs_ECCCorrectOther((unsigned char *)&pt->t,
						  sizeof
						  (yaffs_PackedTags2TagsPart),
						  &pt->ecc, &ecc);
			switch(result){
				case 0: 
					t->eccResult = YAFFS_ECC_RESULT_NO_ERROR; 
					break;
				case 1: 
					t->eccResult = YAFFS_ECC_RESULT_FIXED;
					break;
				case -1:
					t->eccResult = YAFFS_ECC_RESULT_UNFIXED;
					break;
				default:
					t->eccResult = YAFFS_ECC_RESULT_UNKNOWN;
			}
		}
#endif
		t->blockBad = 0;
		t->chunkUsed = 1;
		t->objectId = pt->t.objectId;
		t->chunkId = pt->t.chunkId;
		t->byteCount = pt->t.byteCount;
		t->chunkDeleted = 0;
		t->serialNumber = 0;
		t->sequenceNumber = pt->t.sequenceNumber;

		/* Do extra header info stuff */

		if (pt->t.chunkId & EXTRA_HEADER_INFO_FLAG) {
			t->chunkId = 0;
			t->byteCount = 0;

			t->extraHeaderInfoAvailable = 1;
			t->extraParentObjectId =
			    pt->t.chunkId & (~(ALL_EXTRA_FLAGS));
			t->extraIsShrinkHeader =
			    (pt->t.chunkId & EXTRA_SHRINK_FLAG) ? 1 : 0;
			t->extraShadows =
			    (pt->t.chunkId & EXTRA_SHADOWS_FLAG) ? 1 : 0;
			t->extraObjectType =
			    pt->t.objectId >> EXTRA_OBJECT_TYPE_SHIFT;
			t->objectId &= ~EXTRA_OBJECT_TYPE_MASK;

			if (t->extraObjectType == YAFFS_OBJECT_TYPE_HARDLINK) {
				t->extraEquivalentObjectId = pt->t.byteCount;
			} else {
				t->extraFileLength = pt->t.byteCount;
			}
		}
예제 #4
0
int yflash_ReadChunkWithTagsFromNAND(yaffs_Device *dev,int chunkInNAND, __u8 *data, yaffs_ExtendedTags *tags)
{
	int nread;
	int pos;
	int h;
	
	CheckInit();
	
	
	
	if(data)
	{

		pos = (chunkInNAND % (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE)) * PAGE_SIZE;
		h = filedisk.handle[(chunkInNAND / (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE))];		
		lseek(h,pos,SEEK_SET);
		nread = read(h,data,dev->nDataBytesPerChunk);
		
		if(nread != dev->nDataBytesPerChunk) return YAFFS_FAIL;
	}
	
	if(tags)
	{
		pos = (chunkInNAND % (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE)) * PAGE_SIZE + PAGE_DATA_SIZE;
		h = filedisk.handle[(chunkInNAND / (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE))];		
		lseek(h,pos,SEEK_SET);

		if(0 && dev->isYaffs2)
		{
			nread= read(h,tags,sizeof(yaffs_ExtendedTags));
			if(nread != sizeof(yaffs_ExtendedTags)) return YAFFS_FAIL;
			if(yaffs_CheckAllFF((__u8 *)tags,sizeof(yaffs_ExtendedTags)))
			{
				yaffs_InitialiseTags(tags);
			}
			else
			{
				tags->chunkUsed = 1;
			}
		}
		else
		{
			yaffs_PackedTags2 pt;
			nread= read(h,&pt,sizeof(pt));
			yaffs_UnpackTags2(tags,&pt);
			if((chunkInNAND >> 6) == 300) {
			    if(fail300 && tags->eccResult == YAFFS_ECC_RESULT_NO_ERROR){
			       tags->eccResult = YAFFS_ECC_RESULT_FIXED;
			       fail300 = 0;
			    }
			    
			}
			if((chunkInNAND >> 6) == 320) {
			    if(fail320 && tags->eccResult == YAFFS_ECC_RESULT_NO_ERROR){
			       tags->eccResult = YAFFS_ECC_RESULT_FIXED;
			       fail320 = 0;
			    }
			}
			if(nread != sizeof(pt)) return YAFFS_FAIL;
		}
	}
	

	return YAFFS_OK;	

}
예제 #5
0
int yflash2_ReadChunkWithTagsFromNAND(yaffs_Device *dev,int chunkInNAND, __u8 *data, yaffs_ExtendedTags *tags)
{
	int nread;
	int pos;
	int h;
	int localData = 0;
	int retval = YAFFS_OK;
	int nRead;
	
	T(YAFFS_TRACE_MTD,(TSTR("read chunk %d data %x tags %x" TENDSTR),chunkInNAND,(unsigned)data, (unsigned)tags));
	
	CheckInit();
	
	
	
	
	if(dev->inbandTags){
		/* Got to suck the tags out of the data area */
		if(!data) {
			localData=1;
			data = yaffs_GetTempBuffer(dev,__LINE__);
		}

		
		yaffs_PackedTags2TagsPart * pt2tp;
		pt2tp = (yaffs_PackedTags2TagsPart *)&data[dev->nDataBytesPerChunk];

		
		pos = (chunkInNAND % (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE)) * PAGE_SIZE;
		h = filedisk.handle[(chunkInNAND / (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE))];
		
		lseek(h,pos,SEEK_SET);

		nRead = read(h, data,dev->totalBytesPerChunk);

		yaffs_UnpackTags2TagsPart(tags,pt2tp);
		
		if(nread != dev->totalBytesPerChunk)
			retval = YAFFS_FAIL;
			
		if(localData)
			yaffs_ReleaseTempBuffer(dev,data,__LINE__);



	}
	
	else {
	
		if(data)
		{

			pos = (chunkInNAND % (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE)) * PAGE_SIZE;
			h = filedisk.handle[(chunkInNAND / (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE))];		
			lseek(h,pos,SEEK_SET);
			nread = read(h,data,dev->nDataBytesPerChunk);
		
		
			if(nread != dev->nDataBytesPerChunk) 
				retval = YAFFS_FAIL;
		}
	
		if(tags)
		{
			pos = (chunkInNAND % (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE)) * PAGE_SIZE + PAGE_DATA_SIZE;
			h = filedisk.handle[(chunkInNAND / (PAGES_PER_BLOCK * BLOCKS_PER_HANDLE))];		
			lseek(h,pos,SEEK_SET);

			if(0 && dev->isYaffs2)
			{
				nread= read(h,tags,sizeof(yaffs_ExtendedTags));
				if(nread != sizeof(yaffs_ExtendedTags))
					 retval =  YAFFS_FAIL;
				if(yaffs_CheckAllFF((__u8 *)tags,sizeof(yaffs_ExtendedTags)))
				{
					yaffs_InitialiseTags(tags);
				}
				else
				{
					tags->chunkUsed = 1;
				}
			}
			else
			{
				yaffs_PackedTags2 pt;
				nread= read(h,&pt,sizeof(pt));
				yaffs_UnpackTags2(tags,&pt);
#ifdef SIMULATE_FAILURES
				if((chunkInNAND >> 6) == 100) {
					if(fail300 && tags->eccResult == YAFFS_ECC_RESULT_NO_ERROR){
						tags->eccResult = YAFFS_ECC_RESULT_FIXED;
						fail300 = 0;
					}
				}
				
				if((chunkInNAND >> 6) == 110) {
					if(fail320 && tags->eccResult == YAFFS_ECC_RESULT_NO_ERROR){
						tags->eccResult = YAFFS_ECC_RESULT_FIXED;
						fail320 = 0;
					}
				}
#endif
				if(failRead10>0 && chunkInNAND == 10){
					failRead10--;
					nread = 0;
				}
			
				if(nread != sizeof(pt))
					retval = YAFFS_FAIL;
			}
		}
	}
	


	return retval;	

}