FreeRTOS Support Archive
The FreeRTOS support forum is used to obtain active support directly from Real
Time Engineers Ltd. In return for using our top quality software and services for
free, we request you play fair and do your bit to help others too! Sign up
to receive notifications of new support topics then help where you can.
This is a read only archive of threads posted to the FreeRTOS support forum.
The archive is updated every week, so will not always contain the very latest posts.
Use these archive pages to search previous posts. Use the Live FreeRTOS Forum
link to reply to a post, or start a new support thread.
[FreeRTOS Home] [Live FreeRTOS Forum] [FAQ] [Archive Top] [September 2014 Threads] Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by habcollector on September 22, 2014 Greetings,
I have been stumped by this problem and I am reaching out for assistance. Various Google searches and a review of past posts to this forum have not resulted in a solution.
I have a function that runs as part of a task. It uses two globally declared circular buffer structures (CircularBufferRight, CircularBufferLeft).
Within the function I allocate the memory, load the memory contents from a FAT FS SD Card, and use it - no problem.
The allocation occurs as thus:
initCB(&CircularBufferLeft, CIRCULARBUFFERSIZE);
initCB(&CircularBufferRight, CIRCULARBUFFERSIZE);
The problem occurs when I attempt to free the right memory. When I am finished processing and ready to leave the function I free the memory via:
freeCB(&CircularBufferLeft);
...and later via
freeCB(&CircularBufferRight);
Using:
HeapAvailable = xPortGetFreeHeapSize() for each memory allocation and freedom
I can tell that both the left and right memory are allocated. However only the left memory is released. Freeing the right memory never returns the memory to the heap.
On the very next time this function is run the firmware crashes to a hard fault when it tries to allocate the right memory (the memory that never released).
I have tried this using heap2, heap3 and heap4 - none have worked. I can really use some help - thank you for your time and consideration.
Below are some minimal specifics regarding my code and environment - as I need to I will add more, but my first thought is there is something obvious I am missing some kind person will point out.
TARGET HARDWARE: LPC1768 (M3)
RTOS: V8.0.0
DEVELOPMENT ENVIRONMENT: IAR
typedef struct
{
uint16t Size; // MAX NUMBER OF ELEMENTS
uint16t Start; // INDEX OF OLDEST ELEMENT
uint16t End; // INDEX AT WHICH TO WRITE NEW ELEMENT
uint16t *Elems; // VECTOR OF ELEMENTS
} volatile Type_CircularBuffer;
void initCB(TypeCircularBuffer *CircularBuffer, uint16t BufferSize)
{
CircularBuffer->Size = BufferSize + 1; // INCLUDES AN EMPTY LOCATION
CircularBuffer->Start = 0;
CircularBuffer->End = 0;
CircularBuffer->Elems = (uint16t *)pvPortMalloc(CircularBuffer->Size);
} // END OF init_CB
void freeCB(TypeCircularBuffer *CircularBuffer)
{
vPortFree(CircularBuffer->Elems);
} // END OF free_CB
Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by rtel on September 22, 2014 Do you have configASSERT() defined to something that will alert you if
it gets called (like a null loop)? If something have written over the
structures that are placed in the heap space by the pvPortMalloc()
function then the assert will get triggered.
What happens if you step through the vPortFree() code for the call that
does not seem to work? Can you see the path taken, and does everything
look normal?
Regards.
Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by heinbali01 on September 23, 2014 Hi,
~~~~~
typedef struct
{
uint16t Size; // MAX NUMBER OF ELEMENTS
uint16t Start; // INDEX OF OLDEST ELEMENT
uint16t End; // INDEX AT WHICH TO WRITE NEW ELEMENT
uint16t *Elems; // VECTOR OF ELEMENTS
} volatile Type_CircularBuffer;
void initCB(TypeCircularBuffer CircularBuffer, uint16t BufferSize)
{
CircularBuffer->Size = BufferSize + 1; // INCLUDES AN EMPTY LOCATION
CircularBuffer->Start = 0;
CircularBuffer->End = 0;
CircularBuffer->Elems = (uint16t )pvPortMalloc(CircularBuffer->Size);
~~~~
You are casting a pointer to a 16-bit number?
Didn't you mean a cast to ( uint16_t *) ?
And make sure that 'CIRCULARBUFFERSIZE' is a number of bytes, whereas your circular buffer looks like a buffer of 16-bit elements.
In that case you might want to reserve:
~~~~~
void initCB(TypeCircularBuffer CircularBuffer, uint16t BufferSize)
{
CircularBuffer->Size = sizeof( CircularBuffer->Elems[ 0 ] ) *
( BufferSize + 1 ); // INCLUDES AN EMPTY LOCATION
CircularBuffer->Start = 0;
CircularBuffer->End = 0;
CircularBuffer->Elems = ( uint16t * )pvPortMalloc(CircularBuffer->Size);
~~~~~
In the above case 'BufferSize' would indicate the nett number of 16-bit elements which can be stored in your 'CB'.
Regards,
Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by habcollector on September 23, 2014 Thank you so much for reading and responding Hein.
My apologies, I did cast to (uint16_t *), I transcribed the code to the post incorrectly.
define CIRCULARBUFFERSIZE (512u)
What I want is an array of type uint16_t 512 deep. I hope that is what I did.
Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by habcollector on September 23, 2014 This is the line in the code of pvPortMalloc where it crashes on the second allocation - remember first allocation was not cleared.
/* Insert the new block into the list of free blocks. */
prvInsertBlockIntoFreeList( ( pxNewBlockLink ) );
I do not see that configASSERT is defined - I have not used this config before I will have to research it and respond at a later time.
Problem allocating and freeing memory using pvPortMalloc and vPortFree in heap4Posted by habcollector on September 26, 2014 Thank you so much for responding. My error - memory corruption:
I was using:
CircularBuffer->Elems = (uint16t *)pvPortMalloc(CircularBuffer-Size)
To allocate Size number of uint16t type.
I should have instead done this:
CircularBuffer->Elems = (uint16t *)pvPortMalloc((sizeof(int16t) * CircularBuffer-Size))
Ugggggghhhhh... Why does the computer allways do what you tell it, instead of what you intended.
Copyright (C) Amazon Web Services, Inc. or its affiliates. All rights reserved.
|