Goodmorning to all.
there are some days that I try to fix a bug in my code with FreeRTOS.
I use MPLAB X V1.90 FreeRTOS without timers . (I try with another FreeRTOS version with timer and core-modified that I found on web, but the problem s the same)
uP: PIC32MX340F032H
I use one ModBus task and one ADC task to aquire a measure with an external ADC (on SPI)
Clock:
#pragma config FPLLMUL = MUL_20, FPLLIDIV = DIV_10, FPLLODIV = DIV_1, FWDTEN = OFF
#pragma config FCKSM = CSDCMD, FPBDIV = DIV_2, OSCIOFNC = OFF, POSCMOD = HS, IESO = OFF
#pragma config FSOSCEN = ON, FNOSC = PRIPLL, CP = OFF, BWP = ON
The code that I use to create the task and semaphore are:
void vCreateMBManageTask (void){ xTaskCreate( vMBProcess, "ModBusProcess", (configMINIMAL_STACK_SIZE)*3, NULL, tskIDLE_PRIORITY+2, NULL);}
void vCreateMBManageSemaphore (void){ vSemaphoreCreateBinary ( xBinaryMBManage );}
void vCreateADCManageTask (void){ xTaskCreate( vADCProcess, "ADCProcess", (configMINIMAL_STACK_SIZE)*3, NULL, tskIDLE_PRIORITY+1, NULL);}
void vCreateADCManageSemaphore (void){ vSemaphoreCreateBinary ( xBinaryADCManage );}
the MB process is the same:
static void vMBProcess ( void *pvParameters ){
static portTickType TaskMBManageTick = DELAY_MSEC(95);
static UCHAR *ucMBFrame;
static UCHAR ucRcvAddress;
static USHORT usLength;
static UCHAR ucFunctionCode;
static eMBException eException;
UCHAR i;
eMBEventType eEvent;
eMBErrorCode eStatus = MB_ENOERR;
xSemaphoreTake ( xBinaryMBManage, TaskMBManageTick );
for( ;; ) { if (xSemaphoreTake ( xBinaryMBManage, TaskMBManageTick ) == pdTRUE) {
.....
the FreeRTOS config is that:
#define configUSE_PREEMPTION 1
#define configUSE_IDLE_HOOK 0
#define configUSE_TICK_HOOK 0
#define configTICK_RATE_HZ ( ( portTickType ) 1000 )
#define configCPU_CLOCK_HZ ( ( unsigned long ) 25000000UL )
#define configPERIPHERAL_CLOCK_HZ ( ( unsigned long ) 25000000UL )
#define configMAX_PRIORITIES ( ( unsigned portBASE_TYPE ) 5 )
#define configMINIMAL_STACK_SIZE ( 380 )
#define configISR_STACK_SIZE ( 400 )
#define configTOTAL_HEAP_SIZE ( ( size_t ) 24000 )//( ( size_t ) 16000 )
#define configMAX_TASK_NAME_LEN ( 8 )
#define configUSE_TRACE_FACILITY 0
#define configUSE_16_BIT_TICKS 0
#define configIDLE_SHOULD_YIELD 1
#define configUSE_MUTEXES 1
#define configUSE_COUNTING_SEMAPHORES 1
//#define configCHECK_FOR_STACK_OVERFLOW 2
#define configCHECK_FOR_STACK_OVERFLOW 0
#define configQUEUE_REGISTRY_SIZE 0
/* Co-routine definitions. */
#define configUSE_CO_ROUTINES 0
#define configMAX_CO_ROUTINE_PRIORITIES ( 2 )
/* Set the following definitions to 1 to include the API function, or zeroto exclude the API function. */
#define INCLUDE_vTaskPrioritySet 1
#define INCLUDE_uxTaskPriorityGet 1
#define INCLUDE_vTaskDelete 1
#define INCLUDE_vTaskCleanUpResources 0
#define INCLUDE_vTaskSuspend 1
#define INCLUDE_vTaskDelayUntil 1
#define INCLUDE_vTaskDelay 1
#define INCLUDE_uxTaskGetStackHighWaterMark 1
/* The priority at which the tick interrupt runs. This should probably bekept at 1. */
#define configKERNEL_INTERRUPT_PRIORITY 0x01
/* The maximum interrupt priority from which FreeRTOS.org API functions canbe called. Only API functions that end in ...FromISR() can be used withininterrupts. */
#define configMAX_SYSCALL_INTERRUPT_PRIORITY 0x03
The serial port is initialized in thi way: (RB14 is the direction for RS-485, ulBaudRate is 57600 Baud)
PORTSetPinsDigitalOut( IOPORT_B, BIT_14);
PORTClearBits( IOPORT_B, BIT_14);
// Resto configurazione
UARTConfigure(UART2, UART_ENABLE_PINS_TX_RX_ONLY );
UARTSetFifoMode(UART2, UART_INTERRUPT_ON_TX_DONE | UART_INTERRUPT_ON_RX_NOT_EMPTY);
UARTSetLineControl(UART2, mode);
UARTSetDataRate(UART2, 25000000ul, ulBaudRate);
UARTEnable(UART2, UART_ENABLE_FLAGS(UART_PERIPHERAL | UART_RX | UART_TX));
INTClearFlag(INT_SOURCE_UART_RX(UART2));
INTClearFlag(INT_SOURCE_UART_TX(UART2));
INTSetVectorPriority(INT_VECTOR_UART(UART2), INT_PRIORITY_LEVEL_5);
INTSetVectorSubPriority(INT_VECTOR_UART(UART2), INT_SUB_PRIORITY_LEVEL_0);
// Configure UART2 RX Interrupt
INTEnable(INT_SOURCE_UART_RX(UART2), INT_ENABLED);
The UART interrupt: (I try with the wrapper with assembly code and this version, direct in the ISR )
//void __attribute__( (interrupt(ipl5), vector(_UART_2_VECTOR))) vMBInterruptWrapper( void );
void __ISR(_UART_2_VECTOR, ipl5) vMBInterruptHandler(void)[/code]
I debug the program and 2 or 3 times per second I send a packet ModBus with a dedicated C#-program.
My code responde to the packet until excpetion appears
What it happen is that, after some time, the code give exception with this value:
Expeption #7 (load/store exception)
EPC: 0x9D009528
At that program counter the code assemply is this:
175: pxItemToRemove->pxPrevious->pxNext = pxItemToRemove->pxNext;
9D009504 8FC20010 LW V0, 16(S8)
9D009508 8C420008 LW V0, 8(V0)
9D00950C 8FC30010 LW V1, 16(S8)
9D009510 8C630004 LW V1, 4(V1)
9D009514 AC430004 SW V1, 4(V0)
176:
177: /* The list item knows which list it is in. Obtain the list from the list178: item. */
179: pxList = ( xList * ) pxItemToRemove->pvContainer;
9D009518 8FC20010 LW V0, 16(S8)
9D00951C 8C420010 LW V0, 16(V0)
9D009520 AFC20000 SW V0, 0(S8)
180:
181: /* Make sure the index is left pointing to a valid item. */
182: if( pxList->pxIndex == pxItemToRemove )
9D009524 8FC20000 LW V0, 0(S8)
9D009528 8C430004 LW V1, 4(V0)
9D00952C 8FC20010 LW V0, 16(S8)
9D009530 14620005 BNE V1, V0, 0x9D009548
9D009534 00000000 NOP183: {
184: pxList->pxIndex = pxItemToRemove->pxPrevious;
9D009538 8FC20010 LW V0, 16(S8)
9D00953C 8C430008 LW V1, 8(V0)
9D009540 8FC20000 LW V0, 0(S8)
9D009544 AC430004 SW V1, 4(V0)
185: }
that is the C code corrisponding to the FreeRTOS internal code:
void vListRemove( xListItem *pxItemToRemove ){xList * pxList;
pxItemToRemove->pxNext->pxPrevious = pxItemToRemove->pxPrevious;
pxItemToRemove->pxPrevious->pxNext = pxItemToRemove->pxNext; /* The list item knows which list it is in. Obtain the list from the list item. */
pxList = ( xList * ) pxItemToRemove->pvContainer;
/* Make sure the index is left pointing to a valid item. */
if( pxList->pxIndex == pxItemToRemove ) { pxList->pxIndex = pxItemToRemove->pxPrevious; }
pxItemToRemove->pvContainer = NULL; ( pxList->uxNumberOfItems )--;
}
the timer for timeout modbus (timeout for PKT recived) is this:
void __ISR(_TIMER_2_VECTOR, ipl5) Timer2Handler(void){
// every 100us (= 0.1msec)
if (TickTimeoutMB_msecX10>0){
TickTimeoutMB_msecX10--;
if(TickTimeoutMB_msecX10==0)
{vMBTimerInterruptHandler();}
}
timer defined here: (TIMER2_PERIOD= 2500)
OpenTimer2(T2_ON , TIMER2_PERIOD);
INTEnable(INT_T2, INT_ENABLED);
INTSetVectorPriority(INT_TIMER_2_VECTOR, INT_PRIORITY_LEVEL_5);
INTSetVectorSubPriority(INT_TIMER_2_VECTOR, INT_SUB_PRIORITY_LEVEL_0);
and routine called during timer 2 ISR on timeout:
BOOL
xMBRTUTimerT35Expired( void )
{
BOOL xNeedPoll = FALSE;
portBASE_TYPE xHigherPriorityTaskWoken = pdTRUE;
switch ( eRcvState )
{
-……..
}
xSemaphoreGiveFromISR(xBinaryMBManage,&xHigherPriorityTaskWoken);
return xNeedPoll;
}
Conclusion:
I debug the program and 2 or 3 times per second I send a packet ModBus .
My code responde to the packet until excpetion appears
Expeption #7 (load/store exception)
EPC: 0x9D009528
Try:
I try to comment the task creation of the ADC process but there are no change on the behavior of the code.
If I try to modified the time of semaphoreGive to MB process the exception do not change but occurs before or after. If I use 1msec in few then one minute the exception appears If I use 95msec very much time. (I left uP all week end operate and yestorday eavening the exception occurs).
I can’t expand time to infinity… There is something wrong that I can’t find!
Help that I need! :
Some one have advice… please tell me! I do not know what else do….
If you want some other part of code or information please tell me and I will answer in a few than a hour!
Many thanks!
Massimiliano