Line data Source code
1 : /** 2 : * Copyright (c) 2025 Huawei Technologies Co., Ltd. 3 : * This program is free software, you can redistribute it and/or modify it under the terms and conditions of 4 : * CANN Open Software License Agreement Version 2.0 (the "License"). 5 : * Please refer to the License for details. You may not use this file except in compliance with the License. 6 : * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED, 7 : * INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE. 8 : * See LICENSE in the root of the software repository for the full text of the License. 9 : */ 10 : #include "mem_pool.h" 11 : #include "mmpa_api.h" 12 : #ifdef __cplusplus 13 : extern "C" { 14 : #endif 15 : 16 0 : void InitMemPoolWithCSingleList(MemPool *pool, size_t memSize) 17 : { 18 0 : InitCSingleList(&pool->idleList); 19 0 : pool->memSize = memSize; 20 0 : pool->updating = 0; 21 0 : pool->seq = 0; 22 0 : pool->reuseMemFlag = false; 23 0 : } 24 : 25 0 : void DeInitMemPoolWithCSingleList(MemPool *pool) 26 : { 27 : CSingleListNode *curNode; 28 : CSingleListNode *nextNode; 29 0 : while (!mmCompareAndSwap64(&pool->updating, 0, 1)) { 30 : } 31 0 : CSingleListForEach(&pool->idleList, curNode, nextNode) { 32 0 : RemoveCSingleListNode(&pool->idleList, curNode); 33 0 : MemNode *memNode = GET_MAIN_BY_MEMBER(curNode, MemNode, node); 34 0 : mmFree(memNode); 35 : } 36 0 : mmSetData64(&pool->updating, 0); 37 0 : } 38 : 39 0 : void* MemPoolAllocWithCSingleList(MemPool *pool) 40 : { 41 0 : MemNode *memNode = NULL; 42 0 : while (!mmCompareAndSwap64(&pool->updating, 0, 1)) { 43 : } 44 0 : if (IsSingleListEmpty(&pool->idleList)) { 45 0 : memNode = (MemNode*)mmMalloc(sizeof(MemNode) + pool->memSize); 46 : } else { 47 0 : memNode = GET_MAIN_BY_MEMBER(GetSingleListHead(&pool->idleList), MemNode, node); 48 0 : RemoveCSingleListHead(&pool->idleList); 49 : } 50 0 : if (memNode != NULL) { 51 0 : memNode->flag = MEM_POOL_NODE_USED_FLAG | (((uint64_t)pool->seq) << MEM_POOL_NODE_SEQ_BITNUM); 52 0 : pool->seq++; 53 : } 54 0 : mmSetData64(&pool->updating, 0); 55 0 : return (void*)((memNode == NULL) ? NULL : memNode->data); 56 : } 57 : 58 0 : void MemPoolFreeWithCSingleList(MemPool *pool, void *mem, FnDestroy pfnDestroy) 59 : { 60 0 : if (mem == NULL) { 61 0 : return; 62 : } 63 : 64 0 : MemNode *memNode = GET_MAIN_BY_MEMBER(mem, MemNode, data); 65 0 : if (memNode == NULL) { 66 0 : return; 67 : } 68 : 69 0 : mmAtomicType64 flag = memNode->flag; 70 0 : if ((flag & MEM_POOL_NODE_USED_FLAG) != MEM_POOL_NODE_USED_FLAG) { 71 0 : return; 72 : } 73 0 : if (mmCompareAndSwap64(&memNode->flag, flag, MEM_POOL_NODE_IDLE_FLAG)) { 74 0 : if (pfnDestroy != NULL) { 75 0 : pfnDestroy(mem); 76 : } 77 0 : while (!mmCompareAndSwap64(&pool->updating, 0, 1)) { 78 : } 79 0 : if (GetMemPoolReuseFlag(pool)) { 80 0 : InsertCSingleListTail(&pool->idleList, &memNode->node); 81 : } else { 82 : // No insert to IDEL list, free memNode immediately 83 0 : mmFree(memNode); 84 0 : memNode = NULL; 85 : } 86 0 : mmSetData64(&pool->updating, 0); 87 : } 88 0 : return; 89 : } 90 : 91 0 : bool GetMemPoolReuseFlag(MemPool *pool) 92 : { 93 0 : return (pool->reuseMemFlag); 94 : } 95 : 96 : #ifdef __cplusplus 97 : } 98 : #endif