📄 ssp_slab.c
字号:
#ifdef __cplusplusextern "C"{#endif #include "syscfg.h"#include "sys/sys_pub.h"#include "aos.h"#include "ssp_slab.h"#include "cli/cli_pub.h"#ifndef CONFIG_AOS_RESERVED_MEM_SIZE#error pls define CONFIG_AOS_RESERVED_MEM_SIZE in syscfg.h#endif#define MEM_RESERVED_PAGE_NUM (CONFIG_AOS_RESERVED_MEM_SIZE/MEM_PAGE_SIZE)U8 * g_pPageOffset;MEM_BUF_S * g_pstMemBuf;PAGE_S * g_pstPages;U32 g_ulPageNum;U32 g_ulFreePageStart;U32 g_ulStaticMemStart;U32 g_ulStaticMemPageStart;U8 * g_pSlabPool;U32 g_ulSlabPoolSize;SLAB_DBG_INFO_S slab_dbg_info;#undef AOS_ASSERT#define AOS_ASSERT(f) do {}while(0)/*do nothing*U32 m_slab_init( ){ U32 index; slab_dbg_info.is_page_insufficient = FALSE; slab_dbg_info.is_slab_s_insufficient = FALSE; slab_dbg_info.is_release_slab = FALSE; if( AOS_SUCC !=sys_page_get( (VOID*)&g_pPageOffset, &g_ulPageNum ) ) { return MEM_SYS_MEM_INSUFICIENT; } g_pstPages = (PAGE_S*)g_pPageOffset; g_pstMemBuf = (MEM_BUF_S*)(g_pstPages + g_ulPageNum ); g_pSlabPool = (U8*)(g_pstMemBuf+CONFIG_MEM_BUF_NUM); if( (U32)g_pSlabPool >= ((U32)g_pPageOffset+MEM_RESERVED_PAGE_NUM*MEM_PAGE_SIZE ) ) { return MEM_SYS_MEM_INSUFICIENT; } g_ulSlabPoolSize = (U32)g_pPageOffset+MEM_RESERVED_PAGE_NUM*MEM_PAGE_SIZE - (U32)g_pSlabPool; for( index=0; index < MEM_RESERVED_PAGE_NUM; index++ ) { g_pstPages[index].status = PAGE_MNG; g_pstPages[index].buf_id = U16_BUTT; g_pstPages[index].slabp = (SLAB_S*)NULL; } g_ulFreePageStart = index; g_ulStaticMemStart = (U32)g_pPageOffset + MEM_PAGE_SIZE*g_ulPageNum; g_ulStaticMemPageStart = g_ulPageNum; for( ; index < g_ulPageNum; index++ ) { g_pstPages[index].status = PAGE_FREE; g_pstPages[index].buf_id = U16_BUTT; g_pstPages[index].slabp = (SLAB_S*)NULL; } for( index=0; index < CONFIG_MEM_BUF_NUM; index++ ) { g_pstMemBuf[index].status = FALSE; g_pstMemBuf[index].s_list_head= (SLAB_S*)NULL; g_pstMemBuf[index].s_list_tail= (SLAB_S*)NULL; g_pstMemBuf[index].firstnofull = (SLAB_S*)NULL; g_pstMemBuf[index].objsize= 0; g_pstMemBuf[index].objnum= 0; g_pstMemBuf[index].page_num = 0; g_pstMemBuf[index].slab_num = 0; g_pstMemBuf[index].name[0] = '\0'; } return AOS_SUCC;}U32 mem_buf_create( S8 name[], U32 size, U32 *pulBufId ){ U32 index, lockKey; U32 page_num, left_size, slab_size; AOS_ASSERT( NULL != pulBufId ); if(pulBufId == NULL) { return MEM_BUF_INVALID; } size += 2*sizeof(U32); if( size & 0x3 ) { size >>=2; size++; size <<=2; } page_num = 1; slab_size = MEM_PAGE_SIZE; for(;;) { if( slab_size < size ) { page_num++; slab_size += MEM_PAGE_SIZE; continue; } left_size = slab_size%size; if( left_size <= (slab_size >> 3) ) { break; } page_num++; slab_size += MEM_PAGE_SIZE; } lockKey = aos_int_lock(); for( index = 0; index < CONFIG_MEM_BUF_NUM; index++ ) { if( FALSE == g_pstMemBuf[index].status ) { break; } } if( index >= CONFIG_MEM_BUF_NUM ) { aos_int_unlock(lockKey); *pulBufId = U32_BUTT; return MEM_BUF_INSUFICIENT; } g_pstMemBuf[index].status = TRUE; g_pstMemBuf[index].s_list_head= (SLAB_S*)NULL; g_pstMemBuf[index].s_list_tail= (SLAB_S*)NULL; g_pstMemBuf[index].firstnofull = (SLAB_S*)NULL; g_pstMemBuf[index].objsize= size; g_pstMemBuf[index].objnum= slab_size/size; g_pstMemBuf[index].page_num = page_num; g_pstMemBuf[index].slab_num = 0; aos_strncpy( g_pstMemBuf[index].name, name, MAX_SLAB_NAME_LEN ); aos_int_unlock(lockKey); *pulBufId = index; return AOS_SUCC;}VOID *mem_buf_alloc( U32 buf_id, U32 mpe, U32 sid, S8 *file, U32 line ){ SLAB_S *pSlab; MEM_BUF_S *pBuf; PAGE_S *pPage; OBJ_CTRL_S *pObjCtrl; U8 *objp; if( (buf_id >= CONFIG_MEM_BUF_NUM) || (FALSE == g_pstMemBuf[buf_id].status) ) { return NULL; } if(file == NULL) { return NULL; } pBuf = &g_pstMemBuf[buf_id]; pSlab = pBuf->firstnofull; if( NULL == pSlab ) { U32 slab_s_size, index; slab_s_size = SIZEOF_SLAB_HEAD + SIZEOF_OBJ_CTRL* pBuf->objnum; pSlab = __mem_slab_s_get(slab_s_size); if( NULL == pSlab ) { slab_dbg_info.is_slab_s_insufficient = TRUE; return NULL; } pSlab->s_mem = __mem_page_get(pBuf->page_num); if( NULL == pSlab->s_mem ) { __mem_slab_s_release(pSlab,slab_s_size); slab_dbg_info.is_page_insufficient = TRUE; return NULL; } pPage = obj_to_page(pSlab->s_mem); index = pBuf->page_num; do { pPage->buf_id = (U16)buf_id; pPage->slabp = pSlab; pPage->status = PAGE_SLAB; pPage++; }while( --index ); pSlab->s_prev = NULL; pSlab->s_next = NULL; pSlab->inuse = 0; pSlab->free = 0; for( index = 0; index < pBuf->objnum; index++ ) { U8 *objp0; pSlab->obj_ctrl[index].mpe = 0; pSlab->obj_ctrl[index].sid = 0; pSlab->obj_ctrl[index].tick= 0; pSlab->obj_ctrl[index].ref = 0; pSlab->obj_ctrl[index].next= index+1; pSlab->obj_ctrl[index].file= "NULL"; pSlab->obj_ctrl[index].line= 0; objp0 = pSlab->s_mem + index*pBuf->objsize; *(U32*)objp0 = RED_MAGIC2; *(U32*)(objp0+pBuf->objsize-sizeof(U32)) = RED_MAGIC2; } if(index > 0) { pSlab->obj_ctrl[index-1].next = OBJ_CTRL_END; } pBuf->firstnofull = pSlab; if( NULL == pBuf->s_list_head ) { pBuf->s_list_head = pSlab; pBuf->s_list_tail = pSlab; } else { pBuf->s_list_tail->s_next = pSlab; pSlab->s_prev = pBuf->s_list_tail; pBuf->s_list_tail = pSlab; } pBuf->slab_num++; AOS_ASSERT( TRUE == __mem_slab_check( pBuf, pSlab ) ); AOS_ASSERT( TRUE == __mem_buf_check( pBuf ) ); } AOS_ASSERT( (NULL == pSlab->s_prev) || (pSlab->s_prev->s_next == pSlab) ); AOS_ASSERT( (NULL == pSlab->s_next) || (pSlab->s_next->s_prev == pSlab) ); pSlab->inuse++; objp = pSlab->s_mem + pSlab->free * pBuf->objsize; pObjCtrl = &pSlab->obj_ctrl[pSlab->free]; pObjCtrl->mpe = mpe; pObjCtrl->sid = sid; pObjCtrl->tick= aos_tick_get(); pObjCtrl->ref = 1; pObjCtrl->file = file; pObjCtrl->line = line; pSlab->free = pObjCtrl->next; if( OBJ_CTRL_END == pSlab->free ) { pBuf->firstnofull = pSlab->s_next; } pObjCtrl->next = OBJ_CTRL_END; *(U32*)objp = RED_MAGIC1; *(U32*)(objp+pBuf->objsize-sizeof(U32)) = RED_MAGIC1; objp +=sizeof(U32); AOS_ASSERT( TRUE == __mem_slab_check( pBuf, pSlab ) ); AOS_ASSERT( TRUE == __mem_buf_check( pBuf ) ); return objp;}VOID * mem_buf_fix(U32 ulSize){ U32 ulPages; U32 ulSizeNew; U32 i; if(ulSize == 0) { return (VOID *)NULL; } ulSizeNew = (g_ulStaticMemStart - ((U32)g_pPageOffset + (g_ulStaticMemPageStart << MEM_PAGE_ORDER) )); if(ulSize <= ulSizeNew) { g_ulStaticMemStart -= ulSize; return (VOID *)g_ulStaticMemStart; } ulSizeNew = ulSize - ulSizeNew; ulPages = ulSizeNew >> MEM_PAGE_ORDER; if( ulSizeNew & (MEM_PAGE_SIZE-1) ) { ulPages++; } if( g_ulStaticMemPageStart < ( g_ulFreePageStart + ulPages ) ) { return (VOID *)NULL; } g_ulStaticMemStart -= ulSize; g_ulStaticMemPageStart -= ulPages; for(i = 0;i < ulPages;i++) { g_pstPages[g_ulStaticMemPageStart + i].status = PAGE_FIX; g_pstPages[g_ulStaticMemPageStart + i].buf_id = U16_BUTT; g_pstPages[g_ulStaticMemPageStart + i].slabp = (SLAB_S *)NULL; } return (VOID *)g_ulStaticMemStart;}U32 mem_buf_inc_ref( VOID*objp ){ MEM_BUF_S *pBuf; SLAB_S *pSlab; U32 result, objNo; result = __mem_obj_verify( objp, &pBuf, &pSlab, &objNo ); if( AOS_SUCC != result ) { return result; } pSlab->obj_ctrl[objNo].ref++; return AOS_SUCC;}U32 mem_buf_get_ref( VOID*objp, U32 *pulRef ){ MEM_BUF_S *pBuf; SLAB_S *pSlab; U32 result, objNo; AOS_ASSERT( NULL != pulRef ); if(pulRef == NULL) { return AOS_FAIL; } *pulRef = 0; result = __mem_obj_verify( objp, &pBuf, &pSlab, &objNo ); if( AOS_SUCC != result ) { return result; } *pulRef = pSlab->obj_ctrl[objNo].ref; return AOS_SUCC;}U32 mem_buf_free( VOID*obj_p, S8 *pszFile, U32 ulLine ){ MEM_BUF_S *pBuf; SLAB_S *pSlab; OBJ_CTRL_S *pObjCtrl; U8 *objp = (U8*)obj_p; U32 result, objNo; result = __mem_obj_verify( objp, &pBuf, &pSlab, &objNo ); if( AOS_SUCC != result ) { aos_printf( MPE_MM, "MM-->free fail at file:%s, line:%d",pszFile,ulLine ); aos_task_show_call_stack(0); return result; } pObjCtrl = &pSlab->obj_ctrl[objNo]; pObjCtrl->ref--; if( pObjCtrl->ref ) { return AOS_SUCC; } objp -= sizeof(U32); *(U32*)objp = RED_MAGIC2; *(U32*)(objp+pBuf->objsize-sizeof(U32) ) = RED_MAGIC2; pObjCtrl->next = pSlab->free; pSlab->free = objNo; if( pSlab->inuse != pBuf->objnum ) { pSlab->inuse--; AOS_ASSERT( TRUE == __mem_slab_check( pBuf, pSlab ) ); AOS_ASSERT( TRUE == __mem_buf_check( pBuf ) ); return AOS_SUCC; } pSlab->inuse--; if( (pSlab == pBuf->s_list_tail) || (pSlab->s_next == pBuf->firstnofull) ) { pBuf->firstnofull = pSlab; AOS_ASSERT( TRUE == __mem_slab_check( pBuf, pSlab ) ); AOS_ASSERT( TRUE == __mem_buf_check( pBuf ) ); return AOS_SUCC; } if( pSlab == pBuf->s_list_head ) { pBuf->s_list_head = pSlab->s_next; } if( NULL != pSlab->s_prev ) { pSlab->s_prev->s_next = pSlab->s_next; } if( NULL != pSlab->s_next ) { pSlab->s_next->s_prev = pSlab->s_prev; } if( NULL != pBuf->firstnofull ) { AOS_ASSERT( NULL != pBuf->firstnofull->s_prev); pBuf->firstnofull->s_prev->s_next = pSlab; pSlab->s_prev = pBuf->firstnofull->s_prev; pBuf->firstnofull->s_prev = pSlab; pSlab->s_next = pBuf->firstnofull; } else { pBuf->s_list_tail->s_next = pSlab; pSlab->s_prev = pBuf->s_list_tail; pSlab->s_next = NULL; pBuf->s_list_tail = pSlab; } pBuf->firstnofull = pSlab; AOS_ASSERT( TRUE == __mem_slab_check( pBuf, pSlab ) ); AOS_ASSERT( TRUE == __mem_buf_check( pBuf ) ); return AOS_SUCC;}VOID mem_buf_show( U32 flags, U32 buf_id, U32 mpe, U32 sid, U32 time ){ (void)flags; (void)buf_id; (void)mpe; (void)sid; (void)time;}VOID mem_obj_show( VOID *objp ){ (void)objp;}VOID *__mem_page_get( U32 pageNum ){ U32 start; start = g_ulFreePageStart; if( (g_ulFreePageStart + pageNum) <= (g_ulStaticMemPageStart) ) { g_ulFreePageStart += pageNum; return (VOID*)( g_pPageOffset + (start<<MEM_PAGE_ORDER) ); } return (VOID*)NULL;}AOS_INLINE SLAB_S *__mem_slab_s_get( U32 size ){ SLAB_S *slabp; U32 new_size, i, page_num; if( g_ulSlabPoolSize >= size ) { slabp = (SLAB_S*)g_pSlabPool; g_pSlabPool += size; g_ulSlabPoolSize -= size; return slabp; } new_size = (g_ulStaticMemStart - ((U32)g_pPageOffset + (g_ulStaticMemPageStart << MEM_PAGE_ORDER) )); if(size <= new_size) { g_ulStaticMemStart -= size; return (VOID *)g_ulStaticMemStart; } new_size = size - new_size; page_num = new_size >> MEM_PAGE_ORDER; if( new_size & (MEM_PAGE_SIZE-1) ) { page_num++; } if((g_ulStaticMemPageStart - page_num) < g_ulFreePageStart) { return (VOID *)NULL; } g_ulStaticMemStart -= size;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -