📄 fsmdataitem.c
字号:
/*****************************************************************************
FILE NAME: FsmDataItem.c
DESCRIPTION:
This module contains Fsm data item manager.
Copyright (c) 2002, VIA Technologies, Inc.
*****************************************************************************/
#include "fsmdataitem.h"
#include "Fsmdfs.h"
#include "FsmQueue.h"
#define MAX_DIM_FD 10
/* Flags for Data Item descriptor. */
#define DID_FLAG_FREE 0x00
#define DID_FLAG_IN_USE 0x01
#define DID_FLAG_PENDING 0x02
typedef /*PACKED*/ struct
{
uint16 ItemType;
uint16 ItemId;
uint32 FirstLsn;
uint32 ItemLength;
uint8 Flag;
uint32 ErrorCode;
} FsmDataItemDescriptorT;
/* Global variables and function declare here*/
FsmDevObjHdrT * FsmDataItemDevObjP;
/* Local variables and function declare here*/
static FsmDataItemDescriptorT DataItemFds[MAX_DIM_FD];
static HMSEM DataItemMtxSem;
static uint32 DimErrorCode; /* data item manager error code. */
static uint32
LocateDataItem(
uint16 type,
uint16 id,
FsmItemDirEntryT * entry
);
static uint32
ReadDataItemEntry(
uint32 * Lsn,
uint32 * EntryCount,
FsmItemDirEntryT * Entry
);
static uint32
ReadSingleInstance(
uint32 FirstLsn,
uint32 offset,
uint8 * buf,
uint32 size,
uint32 * read_size
);
static uint32
ReadMultInstance(
uint32 FirstLsn,
uint32 offset,
uint8 * buf,
uint32 size,
uint32 * read_size
);
/*****************************************************************
* Function Name:
* FsmDataItemInit
*
* Description :
*
*
* Input :
*
* First Edit 2003.9.30 wsm
*
*****************************************************************/
uint32 FsmDataItemInit(FsmDevObjHdrT * DevObjP)
{
uint32 i;
FsmDataItemDevObjP = DevObjP;
DataItemMtxSem = FsmCreateMtxSem(1);
if (DataItemMtxSem == NULL)
{
return ERR_SYSTEM;
}
/* Initialize the data item fd */
for (i = 0 ; i < MAX_DIM_FD ; i++)
{
FsmMemorySet((uint8 *)&DataItemFds[i], 0, sizeof(FsmDataItemDescriptorT));
DataItemFds[i].Flag = DID_FLAG_FREE;
}
return ERR_NONE;
}
/*****************************************************************
* Function Name:
* FsmDataItemExit
*
* Description :
*
*
* Input :
*
* First Edit 2003.9.30 wsm
*
*
*****************************************************************/
uint32 FsmDataItemExit()
{
uint32 i;
/* uint32 status;*/
FsmGetMtxSem(DataItemMtxSem);
/* If it is called when system starts, FsmGetMtxSem always fails.
status = FsmGetMtxSem(DataItemMtxSem);
if(status != ERR_NONE)
{
return status;
}
*/
/* Initialize the data item fd */
for (i = 0 ; i < MAX_DIM_FD ; i++)
{
if (DataItemFds[i].Flag != DID_FLAG_FREE)
{
break;
}
}
FsmReleaseMtxSem(DataItemMtxSem);
if(i < MAX_DIM_FD)
return ERR_ACCESS_DENY;
FsmDataItemDevObjP = NULL;
return FsmDeleteMtxSem(DataItemMtxSem);
}
/*****************************************************************
* Function Name:
* FsmDataItemOpen
*
* Description :
* Open a data item file, return the file descriptor
*
* Input :
* type
* id
*
* First Edit 2003.9.30 wsm
*
*****************************************************************/
uint32 FsmDataItemOpen(uint16 type, uint16 id, uint32 mode)
{
uint32 fd;
FsmItemDirEntryT Entry;
FsmFlashMediaT * MediaP;
uint32 SpaceAvail;
#ifdef FSM_DEBUG
MonPrintf("enter interface Data Item Open in %d \n", __LINE__);
#endif
/* argument check */
if (FsmDataItemDevObjP == NULL)
{
DimErrorCode = ERR_INIT;
return INVALID_FILE_HANDLE;
}
MediaP = (FsmFlashMediaT *)FsmDataItemDevObjP->MediaObjP;
if (MediaP == NULL)
{
DimErrorCode = ERR_SYSTEM;
return INVALID_FILE_HANDLE;
}
if ((type == MATCH_TYPE) || (id == MATCH_ID))
{
DimErrorCode = ERR_PARAM;
return INVALID_FILE_HANDLE;
}
/* lock the item fd structure array */
if ((DimErrorCode = FsmGetMtxSem(DataItemMtxSem)) != ERR_NONE)
{
#ifdef FSM_DEBUG
MonPrintf("DataItemLock semaphore fail!");
#endif
return INVALID_FILE_HANDLE;
}
/* Check if the dataitem is in use */
for(fd = 0; fd < MAX_DIM_FD; fd++)
{
if ((DataItemFds[fd].Flag == DID_FLAG_FREE))
{
continue;
}
if ((DataItemFds[fd].ItemType == type) && (DataItemFds[fd].ItemId == id))
{
FsmReleaseMtxSem(DataItemMtxSem);
#ifdef FSM_DEBUG
MonPrintf("The Data Item is on using.");
#endif
DimErrorCode = ERR_NONE;
return fd;
}
}
for(fd = 0; fd < MAX_DIM_FD; fd++)
{
if ((DataItemFds[fd].Flag == DID_FLAG_FREE))
{
break;
}
}
/* if the fd array is full */
if (fd == MAX_DIM_FD)
{
#ifdef FSM_DEBUG
MonPrintf("The Data Item Fd is full.");
#endif
DimErrorCode = ERR_MAX_OPEN;
FsmReleaseMtxSem(DataItemMtxSem);
return INVALID_FILE_HANDLE;
}
/* this data item not in using */
DataItemFds[fd].Flag = DID_FLAG_IN_USE;
DataItemFds[fd].ItemType = type;
DataItemFds[fd].ItemId = id;
mode = mode & FSM_OPEN_MODE_MASK;
DimErrorCode = LocateDataItem(type, id, &Entry);
if(DimErrorCode == ERR_NONE)
{
if((mode == FSM_OPEN_ALWAYS)
|| (mode == FSM_OPEN_EXISTING))
{
DataItemFds[fd].FirstLsn = Entry.FirstLsn;
DataItemFds[fd].ItemLength = Entry.Length;
DataItemFds[fd].ErrorCode = ERR_NONE;
FsmReleaseMtxSem(DataItemMtxSem);
DimErrorCode = ERR_NONE;
return fd;
}
else if(mode == FSM_CREATE_NEW)
{
#ifdef FSM_DEBUG
MonPrintf("The Data Item already exist");
#endif
DimErrorCode = ERR_EXIST;
goto Open_exit;
}
else
{
/* FSM_CREATE_ALWAYS is not supported ??????????? */
#ifdef FSM_DEBUG
MonPrintf("The open mode is not supported!");
#endif
DimErrorCode = ERR_PARAM;
goto Open_exit;
}
}
else
{
if(mode == FSM_OPEN_EXISTING)
{
#ifdef FSM_DEBUG
MonPrintf("The Data Item not exist");
#endif
/* DimErrorCode = ERR_NOTEXIST; */
goto Open_exit;
}
/* FSM_CREATE_NEW, FSM_OPEN_ALWAYS, FSM_CREATE_ALWAYS. */
else if(DimErrorCode == ERR_NOTEXIST)
{
/* space check ,we resever one sector for create the item entry */
SpaceAvail = DfsAvailSpaceCalc(MediaP);
if (SpaceAvail < ACCUM_CNT_CREATE)
{
DimErrorCode = ERR_FULL;
goto Open_exit;
}
/* add a create operation to the queue */
DimErrorCode = QueueAddDataItem(CMD_CREATE, type, id, 0, NULL, 0);
if (DimErrorCode != ERR_NONE)
{
goto Open_exit;
}
DataItemFds[fd].FirstLsn = -1;
DataItemFds[fd].ItemLength = 0;
DataItemFds[fd].ErrorCode = ERR_NONE;
FsmReleaseMtxSem(DataItemMtxSem);
DimErrorCode = ERR_NONE;
return fd;
}
}
/* error exit */
Open_exit:
DataItemFds[fd].Flag = DID_FLAG_FREE;
DataItemFds[fd].ItemType = 0;
DataItemFds[fd].ItemId = 0;
FsmReleaseMtxSem(DataItemMtxSem);
return INVALID_FILE_HANDLE;
}
/*****************************************************************
* Function Name:
* FsmDataItemClose
*
* Description :
* Close an opened data item file
*
* Input :
* Fd
*
* First Edit 2003.9.30 wsm
*
*****************************************************************/
uint32 FsmDataItemClose(uint32 ItemFd)
{
uint32 status;
#ifdef FSM_DEBUG
MonPrintf("Interface Data Item Close in %d \n", __LINE__);
#endif
if(ItemFd >= MAX_DIM_FD)
{
return ERR_PARAM;
}
/* lock the item fd structure */
if ((status = FsmGetMtxSem(DataItemMtxSem)) != ERR_NONE)
{
#ifdef FSM_DEBUG
MonPrintf("Data item Lock semaphore fail! %d\n", ItemFd);
#endif
return status;
}
if (DataItemFds[ItemFd].Flag == DID_FLAG_FREE)
{
FsmReleaseMtxSem(DataItemMtxSem);
return ERR_PARAM;
}
/* free this item fd */
DataItemFds[ItemFd].Flag = DID_FLAG_FREE;
DataItemFds[ItemFd].ItemType = 0;
DataItemFds[ItemFd].ItemId = 0;
DataItemFds[ItemFd].FirstLsn = 0;
DataItemFds[ItemFd].ItemLength = 0;
DataItemFds[ItemFd].ErrorCode = ERR_NONE;
FsmReleaseMtxSem(DataItemMtxSem);
return ERR_NONE;
}
/*****************************************************************
* Function Name:
* FsmDataItemRead
*
* Description :
* Read content from an opened data item file
*
* Input :
* ItemId
* buffer
* size
*
* First Edit 2003.9.30 wsm
*
*****************************************************************/
uint32 FsmDataItemRead(uint16 type, uint16 id, uint32 offset, uint8 * buffer, uint32 size)
{
uint32 ReadSize = 0;
uint32 ItemLength;
uint32 fd;
uint16 reopen = FALSE;
uint16 eof = FALSE;
FsmItemDirEntryT Entry;
DEV_READ_FUNCPTR DevRead;
FsmFlashMediaT * MediaP;
#ifdef FSM_DEBUG
MonPrintf("Interface Data Item Read in %d \n", __LINE__);
#endif
/* arguments check */
if (FsmDataItemDevObjP == NULL)
{
DimErrorCode = ERR_SYSTEM;
return 0;
}
DevRead = FsmDataItemDevObjP->DevDrvP->FsmDevRead;
MediaP = (FsmFlashMediaT *)FsmDataItemDevObjP->MediaObjP;
if (MediaP == NULL)
{
DimErrorCode = ERR_SYSTEM;
return 0;
}
if ((type == MATCH_TYPE) || (id == MATCH_ID))
{
DimErrorCode = ERR_PARAM;
return 0;
}
if (buffer == NULL)
{
DimErrorCode = ERR_PARAM;
return 0;
}
if (size == 0)
{
DimErrorCode = ERR_NONE;
return 0;
}
/* arguments check end */
if ((DimErrorCode = FsmGetMtxSem(DataItemMtxSem)) != ERR_NONE)
{
#ifdef FSM_DEBUG
MonPrintf("Data item Lock semaphore fail! \n" );
#endif
return 0;
}
for (fd = 0; fd < MAX_DIM_FD; fd++)
{
if ((DataItemFds[fd].Flag == DID_FLAG_FREE))
{
continue;
}
if ((DataItemFds[fd].ItemType == type) && (DataItemFds[fd].ItemId == id))
{
/* has been opened. */
if (DataItemFds[fd].FirstLsn == (uint32)(-1))
{
if (DataItemFds[fd].ItemLength == 0)
{
/* it is an empty item */
FsmReleaseMtxSem(DataItemMtxSem);
DimErrorCode = ERR_EOF;
return 0;
}
else
reopen = TRUE;
}
else
reopen = FALSE;
break;
}
}
/* lock the write task. */
if ((DimErrorCode = FsmGetMtxSem(MediaP->MapTblLock)) != ERR_NONE )
{
#ifdef FSM_DEBUG
MonPrintf(" MapTblLock semaphore fail!\n");
#endif
FsmReleaseMtxSem(DataItemMtxSem);
return 0;
}
/* The data item is not opened or new created (without the firstlsn), so we look up in the media */
if ((fd == MAX_DIM_FD) || (reopen == TRUE))
{
DimErrorCode = LocateDataItem(type, id, &Entry);
if(DimErrorCode != ERR_NONE)
{
goto Read_exit;
}
/* if need to update the firstLsn field */
if (reopen == TRUE)
{
DataItemFds[fd].FirstLsn = Entry.FirstLsn ;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -