📄 cmmdriver.c
字号:
free(node);
}
__except(GetExceptionCode()==STATUS_ACCESS_VIOLATION ?
EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH)
{
RETAILMSG( 1, ( _T("CMM DeleteNodeFromFreeList exception occurred\n")) );
}
}
static void ReleaseAllocMem(ALLOC_MEM_T *node, CODEC_MEM_CTX *CodecMem)
{
FREE_MEM_T *free_node;
BOOL r;
__try
{
#if (_WIN32_WCE >= 600)
#ifdef E2E_CMM
{
printD("decommit CodecAddr\n");
r = VirtualFreeEx(CodecMem->callerProcess, // HANDLE hProcess
node->u_addr,
0,
MEM_RELEASE);
if (r == FALSE)
{
RETAILMSG(1, (L"[%d][CMM_Close] CMM VirtualFreeEx returns FALSE.(u_addr : 0x%08x cacheFlag : %d callerprocess:%ld, Err:0x%x)\n",
CodecMem->inst_no, node->u_addr, node->cacheFlag, CodecMem->callerProcess, GetLastError()));
}
}
#else
{
printD("decommit CodecAddr\n");
r = VirtualFreeEx(CodecMem->callerProcess, // HANDLE hProcess
node->u_addr,
node->size,
MEM_DECOMMIT);
if (r == FALSE)
{
RETAILMSG(1, (L"[%d][CMM_Close] CMM VirtualFreeEx returns FALSE.(u_addr : 0x%08x cacheFlag : %d callerprocess:%ld)\n",
CodecMem->inst_no, node->u_addr, node->cacheFlag, CodecMem->callerProcess));
}
}
#endif
#endif
FreeCodecBuff(node);
if(node->cacheFlag){
free_node = (FREE_MEM_T *)malloc(sizeof(FREE_MEM_T));
if(free_node != NULL)
{
free_node->startAddr = node->cached_p_addr;
free_node->size = node->size;
InsertNodeToFreeList(free_node, CodecMem->inst_no);
}
else
{
RETAILMSG(1, (L"[%d][CMM_Close] Fail to create free node with cacheFlag\n"));
}
}
// Delete from AllocMem list
DeleteNodeFromAllocList(node, CodecMem->inst_no);
}
__except(GetExceptionCode()==STATUS_ACCESS_VIOLATION ?
EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH)
{
RETAILMSG( 1, ( _T("CMM ReleaseAllocMem exception occurred\n")) );
}
}
// Remove Fragmentation in FreeMemList
static void MergeFragmentation(UINT8 inst_no)
{
FREE_MEM_T *node1, *node2;
node1 = FreeMemHead;
while(node1 != FreeMemTail){
node2 = FreeMemHead;
while(node2 != FreeMemTail){
if(node1->startAddr + node1->size == node2->startAddr){
node1->size += node2->size;
printD("find merge area !! ( node1->startAddr + node1->size == node2->startAddr)\n");
DeleteNodeFromFreeList(node2, inst_no);
break;
}
else if(node1->startAddr == node2->startAddr + node2->size){
printD("find merge area !! ( node1->startAddr == node2->startAddr + node2->size)\n");
node1->startAddr = node2->startAddr;
node1->size += node2->size;
DeleteNodeFromFreeList(node2, inst_no);
break;
}
node2 = node2->next;
}
node1 = node1->next;
}
}
static DWORD GetMemArea(UINT32 allocSize, UINT8 inst_no)
{
FREE_MEM_T *node = NULL;
FREE_MEM_T *match_node = NULL;
DWORD allocAddr = 0;
int i = 0;
printD("request Size : %ld\n", allocSize);
if(FreeMemHead == FreeMemTail){
RETAILMSG(1, (TEXT("All memory is gone\r\n")));
return(allocAddr);
}
// find best chunk of memory
for(node = FreeMemHead; node != FreeMemTail; node = node->next){
if(match_node != NULL)
{
if((node->size >= allocSize) && (node->size < match_node->size))
{
match_node = node;
}
else
{
//???
}
}
else
{
if(node->size >= allocSize)
{
match_node = node;
}
else
{
// ???
}
}
}
printD("match : startAddr(0x%08x) size(%ld)\n", (match_node == NULL) ? 0 : match_node->startAddr, (match_node == NULL) ? 0 : match_node->size);
// rearange FreeMemArea
if(match_node != NULL){
allocAddr = match_node->startAddr;
match_node->startAddr += allocSize;
match_node->size -= allocSize;
if(match_node->size == 0) // delete match_node.
DeleteNodeFromFreeList(match_node, inst_no);
return(allocAddr);
}
else RETAILMSG(1, (TEXT("there is no suitable chunk\r\n")));
return(allocAddr);
}
static ALLOC_MEM_T * GetCodecVirAddr(UINT8 inst_no, CMM_ALLOC_PRAM_T *in_param)
{
DWORD p_startAddr;
ALLOC_MEM_T *p_allocMem;
DMA_ADAPTER_OBJECT Adapter;
UINT8 *v_addr;
PHYSICAL_ADDRESS p_addr;
//
// if user request cachable area, allocate from reserved area
// if user request uncachable area, allocate dynamically
//
printD("GetCodecVirAddr \n");
__try
{
if(in_param->cacheFlag){
p_startAddr = GetMemArea((UINT32)in_param->size, inst_no);
if(!p_startAddr){
RETAILMSG(1, (L"[CMM:ERR] There is no more memory\n\r"));
return NULL;
}
p_allocMem = (ALLOC_MEM_T *)malloc(sizeof(ALLOC_MEM_T));
if(p_allocMem == NULL)
{
RETAILMSG(1, (L"[CMM:ERR] There is no more memory\n\r"));
return NULL;
}
memset(p_allocMem, 0x00, sizeof(ALLOC_MEM_T));
p_allocMem->cached_p_addr = p_startAddr;
p_allocMem->v_addr = CachedVirAddr + (p_allocMem->cached_p_addr - CODEC_MEM_START);
if (p_allocMem->v_addr == NULL)
{
RETAILMSG(1, (L"[CMM:ERR] Phy2Vir_AddrMapping() : Mapping Failed [PA:0x%08x]\n\r", p_allocMem->cached_p_addr));
free(p_allocMem);
return NULL;
}
printD("v_addr : 0x%x p_addr : 0x%x\n", p_allocMem->v_addr, p_allocMem->cached_p_addr);
}
else{
memset(&Adapter, 0, sizeof(DMA_ADAPTER_OBJECT));
Adapter.InterfaceType = Internal;
Adapter.ObjectSize = sizeof(DMA_ADAPTER_OBJECT);
v_addr = (PBYTE)HalAllocateCommonBuffer(&Adapter, (UINT32)in_param->size, &p_addr, FALSE);
if(v_addr == NULL){
RETAILMSG(1, (TEXT("[CMM] dynamic allocation error\r\n")));
return NULL;
}
p_allocMem = (ALLOC_MEM_T *)malloc(sizeof(ALLOC_MEM_T));
if(p_allocMem == NULL)
{
RETAILMSG(1, (L"[CMM:ERR] There is no more memory\n\r"));
return NULL;
}
memset(p_allocMem, 0x00, sizeof(ALLOC_MEM_T));
p_allocMem->uncached_p_addr = p_addr;
p_allocMem->v_addr = v_addr;
printD("v_addr : 0x%x p_addr : 0x%x\n", p_allocMem->v_addr, p_allocMem->uncached_p_addr.LowPart);
}
p_allocMem->size = (UINT32)in_param->size;
p_allocMem->inst_no = inst_no;
p_allocMem->cacheFlag = in_param->cacheFlag;
InsertNodeToAllocList(p_allocMem, inst_no);
}
__except(GetExceptionCode()==STATUS_ACCESS_VIOLATION ?
EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH)
{
RETAILMSG( 1, ( _T("CMM GetCodecVirAddr Exception occurred.\n")) );
return NULL;
}
return(p_allocMem);
}
static void FreeCodecBuff(ALLOC_MEM_T *node)
{
DMA_ADAPTER_OBJECT Adapter;
printD("FreeCodecBuff \n");
__try
{
if(!node->cacheFlag){
memset(&Adapter, 0, sizeof(DMA_ADAPTER_OBJECT));
Adapter.InterfaceType = Internal;
Adapter.ObjectSize = sizeof(DMA_ADAPTER_OBJECT);
HalFreeCommonBuffer(&Adapter, 0, node->uncached_p_addr, (PVOID)node->v_addr, FALSE);
}
}
__except(GetExceptionCode()==STATUS_ACCESS_VIOLATION ?
EXCEPTION_EXECUTE_HANDLER : EXCEPTION_CONTINUE_SEARCH)
{
RETAILMSG( 1, ( _T("CMM FreeCodecBuff Exception occurred\n")) );
}
}
static UINT8 GetInstanceNo()
{
UINT8 i;
for(i = 0; i < MAX_INSTANCE_NUM; i++)
{
if(instanceNo[i] == FALSE)
{
instanceNo[i] = TRUE;
return i;
}
}
// Instance is all created, there is no room
return -1;
}
static void ReturnInstanceNo(UINT8 inst_no)
{
instanceNo[inst_no] = FALSE;
}
static void PrintList()
{
ALLOC_MEM_T *node1;
FREE_MEM_T *node2;
int count = 0;
DWORD p_addr;
for(node1 = AllocMemHead; node1 != AllocMemTail; node1 = node1->next){
if(node1->cacheFlag)
p_addr = node1->cached_p_addr;
else
p_addr = (DWORD)node1->uncached_p_addr.LowPart;
printD(" [AllocList][%d] inst_no : %d p_addr : 0x%08x v_addr:0x%08x size:%ld cacheflag : %d\n",
count++, node1->inst_no, p_addr, node1->v_addr, node1->size, node1->cacheFlag);
}
count = 0;
for(node2 = FreeMemHead; node2 != FreeMemTail; node2 = node2->next){
printD(" [FreeList][%d] startAddr : 0x%08x size:%ld\n", count++, node2->startAddr , node2->size);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -