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

📄 cmmdriver.c

📁 6410BSP3
💻 C
📖 第 1 页 / 共 3 页
字号:

        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 + -