I have an issue with memcpy within one of my tasks. After I searched in the forum, I noticed there are some other complaints. It is mostly if memcpy is used within an interrupt.
I am not using it inside an interrupt. It is probably something else.
Here is some piece of code where I have memcpy;
int32_t uart1_readline(void)
{
char c = '\0';
char i = 0;
while(c != LF)
{
if(uart1_fifo.num_bytes > 0){
c = uart1_getc();
memcpy(&uart1_fifo.line[i], c, 1);
i++;
}
}
c = '\0';
memcpy(&uart1_fifo.line[i], c, 1);
return i;
}
That makes us two. It was a copy and paste code from an example code in FreeRTOS.
I gave a try your advise and changed it touart1_fifo.line[i] = c;
Now it stuck at that line. So, apparently, memcpy was not the issue.
How come then assigning a value to a member of a struct be an issue?
You should really limit the loop to i < uart1_fifo.line_size until finding a match of end-of-line (LF) (or not) and shouldn‘t you decrement uart1_fifo.num_bytes somewhere ?
I am not sure which memory is used there. Is it in stack or in heap?
Since you are using malloc, it is coming from heap. Looking at the symptoms, it seems that the malloc was failing previously. You should check the return value of malloc to ensure that it was successful.
Which heap are you using? If you are using heap_4.c, can you replace these malloc calls with pvPortMalloc so that the memory comes from the one configured using configTOTAL_HEAP_SIZE ?
@aggarg, I was using heap_2.c. I have replaced it with your suggestion heap_4.c.
and replaced malloc with pvPortMalloc.
Initially, It seemed to work even with the original high memory allocation. But, after exact 10 lines of data received, uart has stopped receiving any more (I didn’t debug it yet for finding the reason). Therefore, once again, while I am still using pvPortMalloc, I lowered the memory size to 1 quarter of 1024. It has then allowed me to enter many lines. I tested more than 100 lines one after each other. It didn’t cause any issue.
Also, you need to ensure that you are not overflowing the line buffer:
int32_t uart1_readline(void)
{
char c = '\0';
char i = 0;
while(c != LF)
{
if(uart1_fifo.num_bytes > 0){
/* -1 is done to ensure there is space for NULL terminator. */
if( i < UART1_LINE_SIZE - 1 )
{
c = uart1_getc();
uart1_fifo.line[i] = c;
i++;
}
else
{
/* Line buffer is full, so break. */
break;
}
}
}
c = '\0';
uart1_fifo.line[i] = c;
return i;
}