Ejemplo n.º 1
0
URET uffs_ReleaseDevice(uffs_Device *dev)
{
    URET ret;

    ret = uffs_BlockInfoReleaseCache(dev);
    if (ret != U_SUCC) {
        uffs_Perror(UFFS_MSG_SERIOUS,  "fail to release block info.");
        goto ext;
    }

    ret = uffs_BufReleaseAll(dev);
    if (ret != U_SUCC) {
        uffs_Perror(UFFS_MSG_SERIOUS,  "fail to release page buffers");
        goto ext;
    }

    ret = uffs_TreeRelease(dev);
    if (ret != U_SUCC) {
        uffs_Perror(UFFS_MSG_SERIOUS, "fail to release tree buffers!");
        goto ext;
    }

    ret = uffs_FlashInterfaceRelease(dev);
    if (ret != U_SUCC) {
        uffs_Perror(UFFS_MSG_SERIOUS, "fail to release tree buffers!");
        goto ext;
    }

    if (dev->mem.release)
        ret = dev->mem.release(dev);

    if (ret != U_SUCC) {
        uffs_Perror(UFFS_MSG_SERIOUS, "fail to release memory allocator!");
    }

    uffs_DeviceReleaseLock(dev);

ext:
    return ret;

}
URET uffs_FormatDevice(uffs_Device *dev, UBOOL force)
{
	u16 i, slot;
	URET ret = U_SUCC;
	
	if (dev == NULL)
		return U_FAIL;

	if (dev->ops == NULL) 
		return U_FAIL;

	uffs_GlobalFsLockLock();

	ret = uffs_BufFlushAll(dev);

	if (dev->ref_count > 1 && !force) {
		uffs_Perror(UFFS_MSG_NORMAL,
					"can't format when dev->ref_count = %d",
					dev->ref_count);
		ret = U_FAIL;
	}

	if (ret == U_SUCC && force) {
		uffs_DirEntryBufPutAll(dev);
		uffs_PutAllObjectBuf(dev);
		uffs_FdSignatureIncrease();
	}

	if (ret == U_SUCC &&
		uffs_BufIsAllFree(dev) == U_FALSE &&
		!force)
	{
		uffs_Perror(UFFS_MSG_NORMAL, "some page still in used!");
		ret = U_FAIL;
	}

	if (!force) {
		for (slot = 0; ret == U_SUCC && slot < dev->cfg.dirty_groups; slot++) {
			if (dev->buf.dirtyGroup[slot].count > 0) {
				uffs_Perror(UFFS_MSG_SERIOUS, "there still have dirty pages!");
				ret = U_FAIL;
			}
		}
	}

	if (ret == U_SUCC)
		uffs_BufSetAllEmpty(dev);


	if (ret == U_SUCC && uffs_BlockInfoIsAllFree(dev) == U_FALSE && !force) {
		uffs_Perror(UFFS_MSG_NORMAL,
					"there still have block info cache ? fail to format");
		ret = U_FAIL;
	}

	if (ret == U_SUCC)
		uffs_BlockInfoExpireAll(dev);

	for (i = dev->par.start; ret == U_SUCC && i <= dev->par.end; i++) {
		if (uffs_FlashIsBadBlock(dev, i) == U_FALSE) {
			uffs_FlashEraseBlock(dev, i);
			if (HAVE_BADBLOCK(dev))
				uffs_BadBlockProcess(dev, NULL);
		}
		else {
#ifdef CONFIG_ENABLE_BAD_BLOCK_VERIFY
			_ForceFormatAndCheckBlock(dev, i);
#endif
		}
	}

	if (ret == U_SUCC && uffs_TreeRelease(dev) == U_FAIL) {
		ret = U_FAIL;
	}

	if (ret == U_SUCC && uffs_TreeInit(dev) == U_FAIL) {
		ret = U_FAIL;
	}

	if (ret == U_SUCC && uffs_BuildTree(dev) == U_FAIL) {
		ret = U_FAIL;
	}

	uffs_GlobalFsLockUnlock();

	return ret;
}