Static member constructor call order issue

Status
Not open for further replies.
Hi, im building a large framework for arduino based projects and a big part of it is a scheduler system I built to automatically run tasks. This works fine on other microprocessors like the ESP32 but im getting problems on the Teensy 4.0 that the tasks arent being added to the scheduler on startup. Only after (I presume) int main() is called.
As the project is kinda huge I dont want to upload the source code and I cant seem to make a simpler version to replicate the issue. ill give an example of how it works:

Code:
//In headerfile

class Thread {
public:

    virtual void loop() = 0;

};


class Scheduler {
public:

    void addItem(Thread* threadPtr) {
        //Place pointer to thread in a list to run when runItems() is called.
        taskList.append(threadPtr);
    }

    void runItems();

    List taskList;

};


class Task_Abstract: public Thread {
public:

    Task_Abstract() {
        scheduler.addItem(this);
    }

    static void runScheduler() {
        scheduler.runItems();
    }

    static Scheduler scheduler;

};



//Following is in .cpp file that includes the header file.

Scheduler Task_Abstract::scheduler;


To use it, a class must inheret from Task_Abstract and implement the loop() function. Then calling Task_Abstract::runScheduler() will run all instantiated objects that inheret from Task_Abstract.
As mentioned this works fine on ESP32 but on the teensy the the task constructor calls successfully the addItem() but it does not add the item to the list. But weirdly enough i can add the item manually in the setup() function and they will run. But this kinda defeats the purpose of this scheduler.
I was able to fix this problem by adding a global scheduler object in the header file but this runs the chance of having multiple global schedulers. Ive tried extern scheduler in the header and defining it in the .cpp file but that gives the same results as a static member.
As far as i understand, the list member inside the scheduler isnt getting initialised before the tasks that are adding themselves to the list.

What could be causing this issue to come up on the teensy 4.0 and not esp32?
 
Sorry I am not a total expert on constructor ordering. Hopefully someone can/will give you a more definitive answer on it.

But in my experience, I have always found this to be pot luck. Maybe it depends on the order the system decides to build things or maybe different versions of compilers behave differently...

So my approach has typically been: Only use the constructors to initialize local stuff to the object. I then typically use something like a method: like begin or setup or init
That does all of the dirty work...

One exception to this, is classes that you can define with their constructor having the constexpr setting...

Example SPI has:
Code:
...
	constexpr SPIClass(uintptr_t myport, uintptr_t myhardware)
		: port_addr(myport), hardware_addr(myhardware) {
	}
So everything must be setup initialized or set by the constructors stuff before the {}.

In this way the compiler will define all of the data of the object and will be preset in memory before any constructors are called.

Not sure if that helps or not.
 
Status
Not open for further replies.
Back
Top