Running FreeRTOS on PIC24E

rtel wrote on Friday, June 12, 2015:

[moved to the support forum from a private email]

I am using:

MPLAB X V3.00
MPLAB ICD 3
Compiler = XC16 (V1.24)
CPU = Microchip p24EP256GU810

The original project was designed for the PIC24F. To get it to compile on the PIC24EP, I did the following:

  1. Loaded the original project into MPLAB X
  2. Changed the device from the PIC24F to the p24EP256GU810 in MPLAB X IDE project.
  3. There was an issue with the size of ucHeap[ configTOTAL_HEAP_SIZE ] in heap_1.c. The compiler comlained about it being too large for “near” space. So I added the attribute to put it into far space and that seemed to fix that.

static unsigned char attribute((far)) ucHeap[ configTOTAL_HEAP_SIZE ];

  1. Included the device specific p24EP256GU810.h file in FreeRTOSConfig.h
  2. Removed the hardware configuration from main and replaced it with an oscillator configuration file.
  3. Commented out everything in main, and added an LED blink loop to see if everything was setup correctly without the FreeRTOS.
  4. Once that worked, removed the LED loop and uncommented the scheduler.

I have several routines enabled looking for traps. I receive misaligned read or write attempts (address errors) shortly after running the application. I believe the address that it was trying to access was in the prvCheckDelayedList function. I tried messing with the heap and stack sizes, and various settings in the FreeRTOSConfig.h file, but always got the same result.

At this point I went online and started reading the FreeRTOS forum to try to get some clues. I found the FreeRTOS Interactive link that points to Contributed Vs Official Code. I went to the separate forum that had Microchip information. Here is where I found “FreeRTOS V8.2.0 port for ALL 16 bit PICs with hardware stack checking (SPLIM)”.
The link was fairly recent, so I thought I would give it a shot. Mike has written port.c and portmap.h files and said these would just drop in am make things work. So I gave it a shot, and it seems to work for several minutes at least.

Is the difference due to the different architectures between the PIC24F and the PIC24ep?

I have since moved on and am adding a C1 interrupt for a CAN interface and some new vTasks. After adding this, I am having issues with address errors again. It happens routinely ~50 seconds after I start. The CAN interface is perfectly happy sending and receiving CAN messages, then the 50 second mark happens and I get an address error trap. (incidentally, I believe it is in the uxListRemove function when the address error occurs). So I probably don’t have my ISR working well with FreeRTOS.

I have read the documentation and the forums. The documentation says to do an assembly language wrapper that stores the context, runs the ISR, then restores the context. The example is done using the C30 compiler, but I haven’t found a way to implement a wrapper using the XC16 compiler. The closest thing that I have found is using a preprologue directive that will basically run an assembly language program before the ISR. But there is no postprologue, so I haven’t figured out how to restore the context after the ISR. On the forum, there is an example for the PIC24ep in which a person used a Yield in the ISR. Everything that I read says don’t do that. So can you help out with the correct way to write an ISR function for interfacing to FreeRTOS using the XC16 compiler?

rtel wrote on Friday, June 12, 2015:

Thank you for providing detailed information.

The original project was designed for the PIC24F. To get it to compile on the PIC24EP, I did the following:

Those steps sound correct to move from one chip to the other. One tip, rather than edit the source file to use the attribute((far)) attribute, you can instead use heap_4, set configAPPLICATION_ALLOCATED_HEAP to 1 in FreeRTOSConfig.h, then define the heap array yourself. Defining it yourself allows you to add any attributes you like. So you can add the line:

unsigned char attribute((far)) ucHeap[ configTOTAL_HEAP_SIZE ];

to your application (note the ‘static’ has been removed).

I tried messing with the heap and stack sizes, and various settings in the FreeRTOSConfig.h file, but always got the same result.

Do you have the stack overflow hook defined?

Mike has written port.c and portmap.h files

I looked at these, but unfortunately, as there are so many changes from the files we provide we cannot support them directly.

Is the difference due to the different architectures between the PIC24F and the PIC24ep

I think Mike has also added other enhancements. The files in the FreeRTOS download should also work for PIC24E.

The documentation says to do an assembly language wrapper that stores the context, runs the ISR, then restores the context.

Looking at the example interrupt handler called _U2RXInterrupt() provided in \FreeRTOS\Demo\PIC24_MPLAB\serial\serial.c I can’t see it is using an assembly wrapper. Also, reading the documentation page for the port, albeit a rather old page, I can’t see the “Interrupt service routines” section mentions having a wrapper either. Did I miss something?

On that port, calling taskYIELD() in the ISR is ok, BUT only if it is the very last instruction in the ISR. I suspect trying to add a wrapper is causing an issue.

One thing I note from the readme file in the contributed port is the phrase “As a note, there is no problem using EDS memory (i.e. >32k ram) in the application, it just can’t be used by FreeRTOS nor by the stack.” Could that be part of your problem, especially if you are adding the far attribute to the ucHeap array?

Regards.

bdrock wrote on Friday, June 12, 2015:

–Do you have the stack overflow hook defined?
Yes, but it is not being triggered in any case that I have found yet.

–I can’t see it is using an assembly wrapper. Also, reading the documentation page —for the port, albeit a rather old page, I can’t see the “Interrupt service
–routines” section mentions having a wrapper either. Did I miss something?
I am referring to the documentation “Using the FreeRTOS Real Time Kernel - A Practical Guide”. It is for the Pic33, I thought that it applied to all devices. It discusses the necessity for the wrapper in order to interface to FreeRTOS.

–One thing I note from the readme file in the contributed port is the phrase “As a
–note, there is no problem using EDS memory (i.e. >32k ram) in the application, it
–just can’t be used by FreeRTOS nor by the stack.”
This is definitely true. The Pic24ep contains a paged memory system. The first page, and then additional pages of EDS memory. There is a note in the datasheet:

For main system Stack Pointer (W15)
coherency, W15 is never subject to
(EDS) paging and is therefore,
restricted to the address range of
0x0000 to 0xFFFF.

The far attribute tells the compiler that the variable will not necessarily be allocated in near (first 8 KB) data space, (i.e., the variable can be located anywhere in data memory between 0x1000 and 0x7FFF for this device). So using far should not be an issue.

I will take a closer look at the serial.c example and continue with debug.

-b

tlafleur wrote on Friday, June 12, 2015:

I have a commercial project that run on a dsPIC33EP256GP502 using FreeRTOS
8.2 and CAN, I2C, UART using Mikes port.c and portmap.h files…

This was NOT a problem getting it to work, I started off with just the
blinking LED demo code on a dsPIC33F, changed to Mikes files, then added
the full demo for testing, added the UART, then onto the dsPIC33EP parts.
then I2C, and CAN… has been running for months now in many devices…
Mikes files do work just fine for both the EP and F processors… I use
heap4 for my project, I also NEVER delete a task.
Wrapper are not needed in this port… also, with mikes code, the
portasm_dsPIC.S is NOT needed.

It would be great if Richard would take the time to support this
processor!!!. Mikes changes are very clean and easy to understand.

this is my exit code in an interrupt…

/* Clear interrupt ECAN event flag that triggered this interrupt */
    IFS2bits.C1IF = EcanCLEAR_FLAG;

    if (xHigherPriorityTaskWoken == pdTRUE)                // do some
FreeRTOS management
    {
        taskYIELD();
    }

On Fri, Jun 12, 2015 at 2:56 AM, Real Time Engineers ltd. <rtel@users.sf.net

wrote:

Thank you for providing detailed information.

The original project was designed for the PIC24F. To get it to compile on
the PIC24EP, I did the following:

Those steps sound correct to move from one chip to the other. One tip,
rather than edit the source file to use the attribute((far)) attribute, you
can instead use heap_4, set configAPPLICATION_ALLOCATED_HEAP to 1 in
FreeRTOSConfig.h, then define the heap array yourself. Defining it yourself
allows you to add any attributes you like. So you can add the line:

unsigned char attribute((far)) ucHeap[ configTOTAL_HEAP_SIZE ];

to your application (note the ‘static’ has been removed).

I tried messing with the heap and stack sizes, and various settings in the
FreeRTOSConfig.h file, but always got the same result.

Do you have the stack overflow hook defined?

Mike has written port.c and portmap.h files

I looked at these, but unfortunately, as there are so many changes from
the files we provide we cannot support them directly.

Is the difference due to the different architectures between the PIC24F
and the PIC24ep

I think Mike has also added other enhancements. The files in the FreeRTOS
download should also work for PIC24E.

The documentation says to do an assembly language wrapper that stores the
context, runs the ISR, then restores the context.

Looking at the example interrupt handler called _U2RXInterrupt() provided
in \FreeRTOS\Demo\PIC24_MPLAB\serial\serial.c I can’t see it is using an
assembly wrapper. Also, reading the documentation page for the port, albeit
a rather old page, I can’t see the “Interrupt service routines” section
mentions having a wrapper either. Did I miss something?
FreeRTOS - PIC24 RTOS and dsPIC RTOS ports

On that port, calling taskYIELD() in the ISR is ok, BUT only if it is the
very last instruction in the ISR. I suspect trying to add a wrapper is
causing an issue.

One thing I note from the readme file in the contributed port is the
phrase “As a note, there is no problem using EDS memory (i.e. >32k ram) in
the application, it just can’t be used by FreeRTOS nor by the stack.” Could
that be part of your problem, especially if you are adding the far
attribute to the ucHeap array?

Regards.

Running FreeRTOS on PIC24E
https://sourceforge.net/p/freertos/discussion/382005/thread/94286604/?limit=25#46f2

Sent from sourceforge.net because you indicated interest in
SourceForge.net: Log In to SourceForge.net

To unsubscribe from further messages, please visit
SourceForge.net: Log In to SourceForge.net

~~ _/) _/) _/) ``` _/) ~~

Tom Lafleur