FreeRTOS with C++: Writing a class with a task as a method

Hey there! It’s my first post here so I hope I’m follwing all rules! First of all, I do have quite a bit of experience writing C code, but not so much in C++. I’m writing a class that’s suppoused to represent a functionality of my program and ideally I’d want to keep most of its inner functionality contained to the class, as private methods and parameters. Now, the problem is that this class should start a task and ideally I’d want that task to be a private member of the class, so it’s able to access the private members of the object. However, I find out as I’m coding that this isn’t possible, at least not directly, as I can’t pass a method as a function pointer to the vTaskCreate function. I can, however, call a “normal” function outside of the class, and have that recieve the class pointer as parameter, and just call the method inside the task function. Such as:

void TaskFunction(void Parameters)
{
((ClassName
) Parameters)->ClassTask();
}

and just code ClassTask method as if it was the task function. Is there another way of doing this? Honestly it’s just adding 4 lines of code but I wonder if there’s a more proper way of solving this problem. Thanks!

Yes, it isn’t actually that hard to do.

First, to be totally correct, your task function should be declared as:

extern “C” {
void TaskFunction(void* parm) {
static_cast<ClassName*>->ClassTaskFunction();
}

And the class needs to name TaskFunction as a friend of the class.

The extern “C” bit ensures that TaskFunction uses the C calling convention, which a normal C++ function might not use (it will for most major ABIs, but that is just safeguarding).

I prefer to use the longer-named C++ cast operators instead of the C cast operator, as they are more limited in what they do, and so they better document the action.

Here is the code a little more elaborated:


extern “C” void TaskFunction( void * pvParameter );

void TaskFunction( void * pvParameter )
{
    ClassName * myObject = static_cast<ClassName*> ( pvParameter );

    // Any safety checks on myObject if you like.

    // Run the code.
    myObject->ClassTaskFunction();

    // In case ClassTaskFunction() ever returns:

    // Depending on the ownership, delete the object
    delete myObject;

    vTaskDelete( NULL );
}

// Start the task

TaskHandle_t xCreatedTask;
ClassName * myObject = new ClassName;
BaseType_t rc = xTaskCreate(
    TaskFunction,         // The code
    "C++task",            // Name of the task
    1024U,                // Size of stack in words
    ( void * ) myObject,  // The parameter passed to TaskFunction()
    tskIDLE_PRIORITY + 2, // Priority of new task
    &xCreatedTask );      // Store the task handle

Wish you fun writing the C++ code.

Thank you so much! It wouldn’t be wise to delete the object in my case but I understand the methodology!

Thank you! I never used the C++ class operators but I should read about it.

As a small plug, you might want to look at a set of C++ wrappers I made that are up on GitHub at GitHub - richard-damon/FreeRTOScpp: FreeRTOS C++ Wrappers