Closed tyalie closed 2 years ago
That's an interesting bug...
First, you can't use (interrupt driven) peripherals before calling vTaskStartScheduler()
, because the system initialization isn't complete at this point (that's why the call to Serial7.flush()
never finishes). Using the usb serial (Serial
) is fine, because it is setup by a startup hook to allow some early debug printing. I think I have to add some documentation about that...
To handle it, you can move the initialization code in a setup task, that is called first, e.g.:
static void setup_task(void *)
{
pinMode(STO_KNEE, OUTPUT);
pinMode(LED_BUILTIN, OUTPUT);
Serial.begin(9600);
while (!Serial)
{
delay(50);
digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
}
#ifdef USE_SPI
test_spi();
#endif
#ifdef USE_UART
test_serial();
#endif
Serial.println("Done all");
#if __has_include("arduino_freertos.h")
xTaskCreate(led_task, "led_task", 128, nullptr, 2, nullptr);
vTaskDelete(nullptr);
#endif
}
void setup()
{
#if __has_include("arduino_freertos.h")
xTaskCreate(setup_task, "setup_task", 1024, nullptr, configMAX_PRIORITIES - 1, nullptr);
vTaskStartScheduler();
#else
setup_task(nullptr);
#endif
}
However, there seems to be a second problem: using LED_BUILTIN
in digitalWrite()
doesn't work when using SPI in the same program. If I change LED_BUILTIN
to another pin (not used by SPI), your example works for me. I don't have an explanation for that, except that LED_BUILTIN
is shared with SPI SCK. But this problem also exists for me in your without_freertos
environment, if I add some code that uses the LED comparable to the FreeRTOS version:
static void setup_task(void *)
{
pinMode(STO_KNEE, OUTPUT);
pinMode(LED_BUILTIN, OUTPUT);
Serial.begin(9600);
while (!Serial)
{
delay(50);
digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
}
#ifdef USE_SPI
test_spi();
#endif
#ifdef USE_UART
test_serial();
#endif
Serial.println("Done all");
#if __has_include("arduino_freertos.h")
xTaskCreate(led_task, "led_task", 128, nullptr, 2, nullptr);
vTaskDelete(nullptr);
#else
while (true)
{
digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
if (digitalRead(LED_BUILTIN))
Serial.println("Hey");
delay(250);
}
#endif
}
void setup()
{
#if __has_include("arduino_freertos.h")
xTaskCreate(setup_task, "setup_task", 1024, nullptr, configMAX_PRIORITIES - 1, nullptr);
vTaskStartScheduler();
#else
setup_task(nullptr);
#endif
}
Thank you so much for your help. I'll try using the setup task. It makes much more sense in many aspects to call all initialization after xTaskStartScheduler
. I actually thought that there wouldn't be a solution as freeRTOS also uses interrupts and those are naturally limited in the system.
But I think a mention in the docs, wouldn't be that bad 😅
Regarding the BUILTIN_LED: I noticed that too yesterday. The next iteration will put the SCK pin somewhere else than pin 13.
Since I don't like that limitation either, I'll see if it can be addressed in a future version. But the setup task workaround should work for most cases.
As far as I can debug when I use both the Serial UART devices like
Serial7
and SPI together, the program will not be able to send stuff over UART when using freertos.You can find a minimal example here: https://github.com/arandomliz/teensy-freertos-serial-test