论坛元老
- 积分
- 5246
- 金钱
- 5246
- 注册时间
- 2012-8-25
- 在线时间
- 1024 小时
|
本帖最后由 gotofly21 于 2020-5-11 16:57 编辑
stm32h7里面内存分块太多了,而且每块用途有区别.用heap5吧不能分配指定内存.于是乎,我就把heap4改为多块内存管理,并且可以再指定或者禁止块来分配内存,
测试有限,不敢保证没问题,内存数组定义是iar格式
头文件 heap_4_5.h- #define configUSE_MALLOC_FAILED_HOOK 1
- #define MEM_DTCM 0x01
- #define MEM_ARAM 0x02
- #define MEM_ARAM_DMA 0x04
- #define MEM_RAM1 0x08
- #define MEM_RAM2 0x10
- #define MEM_RAM3 0x20
- #define MEM_RAM4 0x40
- #define MEM_SDRAM 0x80
- #define MEM_NOMER (0xff-(MEM_ARAM_DMA|MEM_RAM3))
- #define MEM_ALL 0xff
- #define MEM_NO_NOMER (MEM_ARAM_DMA|MEM_RAM3)
-
- #define configTOTAL_HEAP_SIZE_DTCM ((size_t)20*1024) //128K
- #define configTOTAL_HEAP_SIZE_ARAM ((size_t)400*1024) //496k
- #define configTOTAL_HEAP_SIZE_ARAM_DMA ((size_t)15*1024) //16k
- #define configTOTAL_HEAP_SIZE_RAM1 ((size_t)128*1024) //128k
- #define configTOTAL_HEAP_SIZE_RAM2 ((size_t)128*1024) //128k
- #define configTOTAL_HEAP_SIZE_RAM3 ((size_t)5*1024) //32k eth
- #define configTOTAL_HEAP_SIZE_RAM4 ((size_t)64*1024) //64k
- #define configTOTAL_HEAP_SIZE_SDRAM ((size_t)16*1024*1024 - 128) //16M
- #define configTOTAL_HEAP_SIZE configTOTAL_HEAP_SIZE_DTCM
- #define MEM_BLOCKS 8
- void *pvPortMalloc( size_t xSize ) PRIVILEGED_FUNCTION;
- void vPortFree( void *pv ) PRIVILEGED_FUNCTION;
- void vPortInitialiseBlocks( void ) PRIVILEGED_FUNCTION;
- size_t xPortGetFreeHeapSize( void ) PRIVILEGED_FUNCTION;
- size_t xPortGetMinimumEverFreeHeapSize( void ) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_DMA( size_t xWantedSize ) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_eth( size_t xWantedSize ) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_temp( size_t xWantedSize ) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_nomer( size_t xWantedSize ) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_block( size_t xSize,uint8_t block_Fist,uint8_t block_forbid) PRIVILEGED_FUNCTION;
- void *pvPortMalloc_block_fixd( size_t xSize,uint8_t block) PRIVILEGED_FUNCTION;
- size_t xPortGetFreeHeapSize_block( uint8_t block ) PRIVILEGED_FUNCTION;
- size_t xPortGetMinimumEverFreeHeapSize_block( uint8_t block ) PRIVILEGED_FUNCTION;
复制代码
c文件 heap_4_5.c
- /*
- * FreeRTOS Kernel V10.2.1
- * Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * http://www.FreeRTOS.org
- * http://aws.amazon.com/freertos
- *
- * 1 tab == 4 spaces!
- */
- /*
- * A sample implementation of pvPortMalloc() and vPortFree() that combines
- * (coalescences) adjacent memory blocks as they are freed, and in so doing
- * limits memory fragmentation.
- *
- * See heap_1.c, heap_2.c and heap_3.c for alternative implementations, and the
- * memory management pages of http://www.FreeRTOS.org for more information.
- */
- #include <stdlib.h>
- #include <string.h>
- /* Defining MPU_WRAPPERS_INCLUDED_FROM_API_FILE prevents task.h from redefining
- all the API functions to use the MPU wrappers. That should only be done when
- task.h is included from an application file. */
- #define MPU_WRAPPERS_INCLUDED_FROM_API_FILE
- #include "FreeRTOS.h"
- #include "task.h"
- #include "heap_4_5.h"
- #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE
- #if( configSUPPORT_DYNAMIC_ALLOCATION == 0 )
- #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0
- #endif
- /* Block sizes must not get too small. */
- #define heapMINIMUM_BLOCK_SIZE ( ( size_t ) ( xHeapStructSize << 1 ) )
- /* Assumes 8bit bytes! */
- #define heapBITS_PER_BYTE ( ( size_t ) 8 )
- /* Allocate the memory for the heap. */
- #if( configAPPLICATION_ALLOCATED_HEAP == 1 )
- /* The application writer has already defined the array used for the RTOS
- heap - probably so it can be placed in a special segment or address. */
- //extern uint8_t ucHeap[ configTOTAL_HEAP_SIZE ];
- #else
- //static uint8_t ucHeap[ configTOTAL_HEAP_SIZE ];
- #endif /* configAPPLICATION_ALLOCATED_HEAP */
- /* Define the linked list structure. This is used to link free blocks in order
- of their memory address. */
-
-
-
-
-
- typedef struct A_BLOCK_LINK
- {
- struct A_BLOCK_LINK *pxNextFreeBlock; /*<< The next free block in the list. */
- size_t xBlockSize; /*<< The size of the free block. */
- } BlockLink_t;
- //#pragma location=".ram3"
- static uint8_t ucHeap_DTCM [ configTOTAL_HEAP_SIZE_DTCM ];
- #pragma location=".aixram"
- static uint8_t ucHeap_ARAM [ configTOTAL_HEAP_SIZE_ARAM ];
- #pragma location=".aixram_dma"
- static uint8_t ucHeap_ARAM_DMA [ configTOTAL_HEAP_SIZE_ARAM_DMA ];
- #pragma location=".ram1"
- static uint8_t ucHeap_RAM1 [ configTOTAL_HEAP_SIZE_RAM1 ];
- #pragma location=".ram2"
- static uint8_t ucHeap_RAM2 [ configTOTAL_HEAP_SIZE_RAM2 ];
- #pragma location=".ram3"
- static uint8_t ucHeap_RAM3 [ configTOTAL_HEAP_SIZE_RAM3 ];
- #pragma location=".ram4"
- static uint8_t ucHeap_RAM4 [ configTOTAL_HEAP_SIZE_RAM4 ];
- #pragma location=".sdram"
- __no_init static uint8_t ucHeap_SDRAM [ configTOTAL_HEAP_SIZE_SDRAM ];
- typedef struct
- {
- uint8_t *addr_start;
- size_t Msize;
- uint8_t mem_type;
- uint8_t baoliu[3];
- }Mem_block_t;
- Mem_block_t const Mem_block_s[]=
- {
- {ucHeap_DTCM,configTOTAL_HEAP_SIZE_DTCM,MEM_DTCM,0,0,0},
- {ucHeap_ARAM,configTOTAL_HEAP_SIZE_ARAM,MEM_ARAM,0,0,0},
- {ucHeap_ARAM_DMA,configTOTAL_HEAP_SIZE_ARAM_DMA,MEM_ARAM_DMA,0,0,0},
- {ucHeap_RAM1,configTOTAL_HEAP_SIZE_RAM1,MEM_RAM1,0,0,0},
- {ucHeap_RAM2,configTOTAL_HEAP_SIZE_RAM2,MEM_RAM2,0,0,0},
- {ucHeap_RAM3,configTOTAL_HEAP_SIZE_RAM3,MEM_RAM3,0,0,0},
- {ucHeap_RAM4,configTOTAL_HEAP_SIZE_RAM4,MEM_RAM4,0,0,0},
- {ucHeap_SDRAM,configTOTAL_HEAP_SIZE_SDRAM,MEM_SDRAM,0,0,0},
- };
- typedef struct
- {
- const Mem_block_t *Mem_block_p;
- BlockLink_t xStart, *pxEnd ;
- size_t xFreeBytesRemaining;
- size_t xMinimumEverFreeBytesRemaining;
- size_t xBlockAllocatedBit;
- }MemPool_t;
- MemPool_t MemPool_s[MEM_BLOCKS];
- /*-----------------------------------------------------------*/
- /*
- * Inserts a block of memory that is being freed into the correct position in
- * the list of free memory blocks. The block being freed will be merged with
- * the block in front it and/or the block behind it if the memory blocks are
- * adjacent to each other.
- */
- static void prvInsertBlockIntoFreeList( BlockLink_t *pxBlockToInsert ,MemPool_t *MemPool_p);
- /*
- * Called automatically to setup the required heap structures the first time
- * pvPortMalloc() is called.
- */
- static void prvHeapInit_block( uint8_t block_N );
- //static void prvHeapInit( void );
- /*-----------------------------------------------------------*/
- /* The size of the structure placed at the beginning of each allocated memory
- block must by correctly byte aligned. */
- static const size_t xHeapStructSize = ( sizeof( BlockLink_t ) + ( ( size_t ) ( portBYTE_ALIGNMENT - 1 ) ) ) & ~( ( size_t ) portBYTE_ALIGNMENT_MASK );
- /* Create a couple of list links to mark the start and end of the list. */
- //static BlockLink_t xStart, *pxEnd = NULL;
- /* Keeps track of the number of free bytes remaining, but says nothing about
- fragmentation. */
- //static size_t xFreeBytesRemaining = 0U;
- //static size_t xMinimumEverFreeBytesRemaining = 0U;
- /* Gets set to the top bit of an size_t type. When this bit in the xBlockSize
- member of an BlockLink_t structure is set then the block belongs to the
- application. When the bit is free the block is still part of the free heap
- space. */
- //static size_t xBlockAllocatedBit = 0;
- /*
- typedef enum
- {
- MEM_DTCM=0x01,
- MEM_ARAM=0x02,
- MEM_ARAM_DMA=0x04,
- MEM_RAM1=0x08,
- MEM_RAM2=0x10,
- MEM_RAM3=0x20,
- MEM_RAM4=0x40,
- MEM_SDRAM=0x80,
- MEM_NOMER=0xff-(MEM_ARAM_DMA|MEM_RAM3),
- MEM_ALL=0xff
- } MEM_ENEMT;
- */
- /*
- configTOTAL_HEAP_SIZE_DTCM
- configTOTAL_HEAP_SIZE_ARAM
- configTOTAL_HEAP_SIZE_ARAM_DMA
- configTOTAL_HEAP_SIZE_RAM1
- configTOTAL_HEAP_SIZE_RAM2
- configTOTAL_HEAP_SIZE_RAM3
- configTOTAL_HEAP_SIZE_RAM4
- configTOTAL_HEAP_SIZE_SDRAM
- */
- static int mem_init_f=0;
- /*-----------------------------------------------------------*/
- int mem_block_get(uint8_t mem_type)
- {
- int block_n=-1;
- switch(mem_type )
- {
- case MEM_DTCM : block_n=0;break;
- case MEM_ARAM: block_n=1;break;
- case MEM_ARAM_DMA: block_n=2;break;
- case MEM_RAM1: block_n=3;break;
- case MEM_RAM2: block_n=4;break;
- case MEM_RAM3: block_n=5;break;
- case MEM_RAM4: block_n=6;break;
- case MEM_SDRAM: block_n=7;break;
- }
-
- return block_n;
- }
- static void *pvPortMalloc_block_dwx( size_t xWantedSize, MemPool_t *MemPool_p)
- {
- BlockLink_t *pxBlock, *pxPreviousBlock, *pxNewBlockLink;
- void *pvReturn = NULL;
- vTaskSuspendAll();
- {
- /* If this is the first call to malloc then the heap will require
- initialisation to setup the list of free blocks. */
- if(mem_init_f==0)
- {
- uint8_t block;
- for( block=0;block< MEM_BLOCKS-1; block++) //sdram 后面 初始化
- {
- prvHeapInit_block(block);
- }
- mem_init_f=1;
- }
-
- if(MemPool_p->pxEnd == NULL )
- {
- xWantedSize=0;
- // prvHeapInit(MemPool_p);
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- /* Check the requested block size is not so large that the top bit is
- set. The top bit of the block size member of the BlockLink_t structure
- is used to determine who owns the block - the application or the
- kernel, so it must be free. */
- if( ( xWantedSize & MemPool_p->xBlockAllocatedBit ) == 0 )
- {
- /* The wanted size is increased so it can contain a BlockLink_t
- structure in addition to the requested amount of bytes. */
- if( xWantedSize > 0 )
- {
- xWantedSize += xHeapStructSize;
- /* Ensure that blocks are always aligned to the required number
- of bytes. */
- if( ( xWantedSize & portBYTE_ALIGNMENT_MASK ) != 0x00 )
- {
- /* Byte alignment required. */
- xWantedSize += ( portBYTE_ALIGNMENT - ( xWantedSize & portBYTE_ALIGNMENT_MASK ) );
- configASSERT( ( xWantedSize & portBYTE_ALIGNMENT_MASK ) == 0 );
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- if( ( xWantedSize > 0 ) && ( xWantedSize <= MemPool_p->xFreeBytesRemaining ) )
- {
- /* Traverse the list from the start (lowest address) block until
- one of adequate size is found. */
- pxPreviousBlock = &MemPool_p->xStart;
- pxBlock = MemPool_p->xStart.pxNextFreeBlock;
- while( ( pxBlock->xBlockSize < xWantedSize ) && ( pxBlock->pxNextFreeBlock != NULL ) )
- {
- pxPreviousBlock = pxBlock;
- pxBlock = pxBlock->pxNextFreeBlock;
- }
- /* If the end marker was reached then a block of adequate size
- was not found. */
- if( pxBlock != MemPool_p->pxEnd )
- {
- /* Return the memory space pointed to - jumping over the
- BlockLink_t structure at its start. */
- pvReturn = ( void * ) ( ( ( uint8_t * ) pxPreviousBlock->pxNextFreeBlock ) + xHeapStructSize );
- /* This block is being returned for use so must be taken out
- of the list of free blocks. */
- pxPreviousBlock->pxNextFreeBlock = pxBlock->pxNextFreeBlock;
- /* If the block is larger than required it can be split into
- two. */
- if( ( pxBlock->xBlockSize - xWantedSize ) > heapMINIMUM_BLOCK_SIZE )
- {
- /* This block is to be split into two. Create a new
- block following the number of bytes requested. The void
- cast is used to prevent byte alignment warnings from the
- compiler. */
- pxNewBlockLink = ( void * ) ( ( ( uint8_t * ) pxBlock ) + xWantedSize );
- configASSERT( ( ( ( size_t ) pxNewBlockLink ) & portBYTE_ALIGNMENT_MASK ) == 0 );
- /* Calculate the sizes of two blocks split from the
- single block. */
- pxNewBlockLink->xBlockSize = pxBlock->xBlockSize - xWantedSize;
- pxBlock->xBlockSize = xWantedSize;
- /* Insert the new block into the list of free blocks. */
- prvInsertBlockIntoFreeList( pxNewBlockLink ,MemPool_p);
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- MemPool_p->xFreeBytesRemaining -= pxBlock->xBlockSize;
- if( MemPool_p->xFreeBytesRemaining < MemPool_p->xMinimumEverFreeBytesRemaining )
- {
- MemPool_p->xMinimumEverFreeBytesRemaining = MemPool_p->xFreeBytesRemaining;
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- /* The block is being returned - it is allocated and owned
- by the application and has no "next" block. */
- pxBlock->xBlockSize |= MemPool_p->xBlockAllocatedBit;
- pxBlock->pxNextFreeBlock = NULL;
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- traceMALLOC( pvReturn, xWantedSize );
- }
- ( void ) xTaskResumeAll();
- configASSERT( ( ( ( size_t ) pvReturn ) & ( size_t ) portBYTE_ALIGNMENT_MASK ) == 0 );
- return pvReturn;
- }
- void *pvPortMalloc_block( size_t xSize,uint8_t block_Fist,uint8_t block_forbid)
- {
-
- uint8_t N=0x01;
- void *pvReturn = NULL;
- // MemPool_t *MemPool_p
- for(N=0x01;N!=0;N<<=1) // fist
- {
- if((N & MEM_ALL) == 0) continue;
- if((N & block_Fist) == 0 ) continue;
- if((N & block_forbid) ) continue;
- pvReturn = pvPortMalloc_block_dwx(xSize,MemPool_s+ mem_block_get( N)) ;
- if(pvReturn != NULL)
- {
- return pvReturn;
- }
- }
-
- for(N=0x01;N!=0;N<<=1) // fist 没成功
- {
- if((N & MEM_ALL ) == 0) continue;
- if((N & block_Fist ) ) continue;
- if((N & block_forbid) ) continue;
- pvReturn = pvPortMalloc_block_dwx(xSize,MemPool_s+ mem_block_get( N)) ;
- if(pvReturn != NULL)
- {
- return pvReturn;
- }
- }
-
-
- #if( configUSE_MALLOC_FAILED_HOOK == 1 )
- {
- if( pvReturn == NULL )
- {
- extern void vApplicationMallocFailedHook( void );
- vApplicationMallocFailedHook();
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
- #endif
-
- return pvReturn;
- }
- void *pvPortMalloc_block_fixd( size_t xSize,uint8_t block)
- {
- return pvPortMalloc_block( xSize, block, MEM_ALL-block);
- }
- void *pvPortMalloc( size_t xWantedSize )
- {
- return pvPortMalloc_block( xWantedSize, MEM_NOMER, MEM_NO_NOMER);
- }
- void *pvPortMalloc_nomer( size_t xWantedSize )
- {
- return pvPortMalloc_block( xWantedSize, (MEM_NOMER&(MEM_ALL -MEM_DTCM )), MEM_NO_NOMER);
- }
- void *pvPortMalloc_DMA( size_t xWantedSize )
- {
- return pvPortMalloc_block( xWantedSize, MEM_ARAM_DMA, MEM_ALL-MEM_ARAM_DMA);
- }
- void *pvPortMalloc_eth( size_t xWantedSize )
- {
- return pvPortMalloc_block( xWantedSize, MEM_RAM3, MEM_ALL-MEM_RAM3);
- }
- void *pvPortMalloc_temp( size_t xWantedSize )
- {
- return pvPortMalloc_block( xWantedSize, MEM_RAM2, MEM_NO_NOMER|MEM_DTCM);
- }
- /*-----------------------------------------------------------*/
- static void vPortFree_block( void *pv ,MemPool_t *MemPool_p )
- {
-
- uint8_t *puc = ( uint8_t * ) pv;
- BlockLink_t *pxLink;
- if( pv != NULL )
- {
- /* The memory being freed will have an BlockLink_t structure immediately
- before it. */
- puc -= xHeapStructSize;
- /* This casting is to keep the compiler from issuing warnings. */
- pxLink = ( void * ) puc;
- /* Check the block is actually allocated. */
- configASSERT( ( pxLink->xBlockSize & MemPool_p->xBlockAllocatedBit ) != 0 );
- configASSERT( pxLink->pxNextFreeBlock == NULL );
- if( ( pxLink->xBlockSize & MemPool_p->xBlockAllocatedBit ) != 0 )
- {
- if( pxLink->pxNextFreeBlock == NULL )
- {
- /* The block is being returned to the heap - it is no longer
- allocated. */
- pxLink->xBlockSize &= ~MemPool_p->xBlockAllocatedBit;
- vTaskSuspendAll();
- {
- /* Add this block to the list of free blocks. */
- MemPool_p->xFreeBytesRemaining += pxLink->xBlockSize;
- traceFREE( pv, pxLink->xBlockSize );
- prvInsertBlockIntoFreeList( ( ( BlockLink_t * ) pxLink ),MemPool_p );
- }
- ( void ) xTaskResumeAll();
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
-
- }
- void vPortFree( void *pv )
- {
- MemPool_t *MemPool_p = MemPool_s;
- int blockN;
- for(blockN=0;blockN<MEM_BLOCKS;blockN++,MemPool_p++)
- {
- if( ( (size_t) pv>= (size_t)MemPool_p->Mem_block_p->addr_start )
- &&( (size_t) pv < (size_t)MemPool_p->Mem_block_p->addr_start + MemPool_p->Mem_block_p-> Msize))
- {
- vPortFree_block(pv,MemPool_p ) ;
- break;
- }
-
- }
- }
- /*-----------------------------------------------------------*/
- size_t xPortGetFreeHeapSize_block( uint8_t block )
- {
- int block_N = mem_block_get(block);
- if(block_N<0) return 0;
- MemPool_t *MemPool_p = MemPool_s+ block_N;
- return MemPool_p->xFreeBytesRemaining;
- }
- /*-----------------------------------------------------------*/
- size_t xPortGetMinimumEverFreeHeapSize_block( uint8_t block )
- {
- int block_N = mem_block_get(block);
- if(block_N<0) return 0;
- MemPool_t *MemPool_p = MemPool_s+ block_N;
- return MemPool_p->xMinimumEverFreeBytesRemaining;
- }
- /*-----------------------------------------------------------*/
- size_t xPortGetFreeHeapSize( void )
- {
- size_t size_r=0;
- uint8_t block_N ;
- for(block_N=0x01;block_N!=0;block_N<<=1)
- {
- size_r += xPortGetFreeHeapSize_block(block_N);
- }
- return size_r;
-
- }
- size_t xPortGetMinimumEverFreeHeapSize( void )
- {
- size_t size_r=0;
- uint8_t block_N ;
- for(block_N=0x01;block_N!=0;block_N<<=1)
- {
- size_r += xPortGetMinimumEverFreeHeapSize_block(block_N);
- }
- return size_r;
-
- }
- void vPortInitialiseBlocks( void )
- {
- prvHeapInit_block(7);//sdram,sdram初始化完成后启用这个,要不然就飞了
- /* This just exists to keep the linker quiet. */
- }
- /*-----------------------------------------------------------*/
- static void prvHeapInit_block( uint8_t block_N )
- {
- MemPool_t *MemPool_p = MemPool_s+ block_N;
- memset(MemPool_p,0,sizeof(MemPool_t));
- MemPool_p->Mem_block_p = Mem_block_s+block_N;
-
- BlockLink_t *pxFirstFreeBlock;
- uint8_t *pucAlignedHeap;
- size_t uxAddress;
- size_t xTotalHeapSize =MemPool_p->Mem_block_p->Msize;// configTOTAL_HEAP_SIZE;
- /* Ensure the heap starts on a correctly aligned boundary. */
- uxAddress = ( size_t )MemPool_p->Mem_block_p->addr_start;// ( size_t ) ucHeap;
- if( ( uxAddress & portBYTE_ALIGNMENT_MASK ) != 0 )
- {
- uxAddress += ( portBYTE_ALIGNMENT - 1 );
- uxAddress &= ~( ( size_t ) portBYTE_ALIGNMENT_MASK );
- xTotalHeapSize -= uxAddress - ( size_t ) MemPool_p->Mem_block_p->addr_start;
- }
- pucAlignedHeap = ( uint8_t * ) uxAddress;
- /* xStart is used to hold a pointer to the first item in the list of free
- blocks. The void cast is used to prevent compiler warnings. */
- MemPool_p->xStart.pxNextFreeBlock = ( void * ) pucAlignedHeap;
- MemPool_p->xStart.xBlockSize = ( size_t ) 0;
- /* pxEnd is used to mark the end of the list of free blocks and is inserted
- at the end of the heap space. */
- uxAddress = ( ( size_t ) pucAlignedHeap ) + xTotalHeapSize;
- uxAddress -= xHeapStructSize;
- uxAddress &= ~( ( size_t ) portBYTE_ALIGNMENT_MASK );
- MemPool_p->pxEnd = ( void * ) uxAddress;
- MemPool_p->pxEnd->xBlockSize = 0;
- MemPool_p->pxEnd->pxNextFreeBlock = NULL;
- /* To start with there is a single free block that is sized to take up the
- entire heap space, minus the space taken by pxEnd. */
- pxFirstFreeBlock = ( void * ) pucAlignedHeap;
- pxFirstFreeBlock->xBlockSize = uxAddress - ( size_t ) pxFirstFreeBlock;
- pxFirstFreeBlock->pxNextFreeBlock = MemPool_p->pxEnd;
- /* Only one block exists - and it covers the entire usable heap space. */
- MemPool_p->xMinimumEverFreeBytesRemaining = pxFirstFreeBlock->xBlockSize;
- MemPool_p->xFreeBytesRemaining = pxFirstFreeBlock->xBlockSize;
- /* Work out the position of the top bit in a size_t variable. */
- MemPool_p->xBlockAllocatedBit = ( ( size_t ) 1 ) << ( ( sizeof( size_t ) * heapBITS_PER_BYTE ) - 1 );
- }
- /*-----------------------------------------------------------*/
- /*-----------------------------------------------------------*/
- static void prvInsertBlockIntoFreeList( BlockLink_t *pxBlockToInsert,MemPool_t *MemPool_p )
- {
- BlockLink_t *pxIterator;
- uint8_t *puc;
- /* Iterate through the list until a block is found that has a higher address
- than the block being inserted. */
- for( pxIterator = &MemPool_p->xStart; pxIterator->pxNextFreeBlock < pxBlockToInsert; pxIterator = pxIterator->pxNextFreeBlock )
- {
- /* Nothing to do here, just iterate to the right position. */
- }
- /* Do the block being inserted, and the block it is being inserted after
- make a contiguous block of memory? */
- puc = ( uint8_t * ) pxIterator;
- if( ( puc + pxIterator->xBlockSize ) == ( uint8_t * ) pxBlockToInsert )
- {
- pxIterator->xBlockSize += pxBlockToInsert->xBlockSize;
- pxBlockToInsert = pxIterator;
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- /* Do the block being inserted, and the block it is being inserted before
- make a contiguous block of memory? */
- puc = ( uint8_t * ) pxBlockToInsert;
- if( ( puc + pxBlockToInsert->xBlockSize ) == ( uint8_t * ) pxIterator->pxNextFreeBlock )
- {
- if( pxIterator->pxNextFreeBlock != MemPool_p->pxEnd )
- {
- /* Form one big block from the two blocks. */
- pxBlockToInsert->xBlockSize += pxIterator->pxNextFreeBlock->xBlockSize;
- pxBlockToInsert->pxNextFreeBlock = pxIterator->pxNextFreeBlock->pxNextFreeBlock;
- }
- else
- {
- pxBlockToInsert->pxNextFreeBlock = MemPool_p->pxEnd;
- }
- }
- else
- {
- pxBlockToInsert->pxNextFreeBlock = pxIterator->pxNextFreeBlock;
- }
- /* If the block being inserted plugged a gab, so was merged with the block
- before and the block after, then it's pxNextFreeBlock pointer will have
- already been set, and should not be set here as that would make it point
- to itself. */
- if( pxIterator != pxBlockToInsert )
- {
- pxIterator->pxNextFreeBlock = pxBlockToInsert;
- }
- else
- {
- mtCOVERAGE_TEST_MARKER();
- }
- }
复制代码
|
|