I have been learning about the new multicore functionality using the examples found in the official Raspberry Pi Pico C SDK.
There is one example called multicore_runner.c which uses a function pointer.
I was having great problems getting it to work because of this line in the code:
int32_t (*func)() = (int32_t(*)()) multicore_fifo_pop_blocking();
The Arduino compiler did not like it.
Well with a bit of thought and some trial and error I figured out that this needs to be:
int32_t (*func)(int32_t) = (int32_t(*)(int32_t)) multicore_fifo_pop_blocking();
Now the code example works.
I created a fun example which includes blinking LED's (see below). Note this example was developed and tested on a Raspberry Pi Pico board rather than the RP2040 Connect.
Apologies to the purists as I tend to use a mix of Arduino and Mbed code. I also prefer to use Serial1 for my serial output as this avoids the hassle of the virtual serial USB port (Serial).
#include <stdio.h>
#include <mbed.h>
#include "pico/multicore.h"
mbed::DigitalOut led1(LED1, 0);
mbed::DigitalOut led2(p2, 0);
#define TEST_NUM 10
void core1_entry() {
uint32_t t_int = millis();
while (1) {
// Function pointer is passed to us via the FIFO
// We have one incoming int32_t as a parameter, and will provide an
// int32_t return value by simply pushing it back on the FIFO
// which also indicates the result is ready.
int32_t (*func)(int32_t) = (int32_t(*)(int32_t)) multicore_fifo_pop_blocking();
int32_t p = (int32_t)multicore_fifo_pop_blocking();
led2 = !led2;
int32_t result = (*func)(p);
multicore_fifo_push_blocking(result);
}
}
int32_t factorial(int32_t n) {
int32_t f = 1;
for (int i = 2; i <= n; i++) {
f *= i;
}
return f;
}
int32_t fibonacci(int32_t n) {
if (n == 0) return 0;
if (n == 1) return 1;
int n1 = 0, n2 = 1, n3;
for (int i = 2; i <= n; i++) {
n3 = n1 + n2;
n1 = n2;
n2 = n3;
}
return n3;
}
void setup() {
Serial1.begin(115200);
sleep_ms(100);
Serial1.println("\r\nHello, multicore_runner!");
// This example dispatches arbitrary functions to run on the second core
// To do this we run a dispatcher on the second core that accepts a function
// pointer and runs it
multicore_launch_core1(core1_entry);
}
void loop() {
int32_t res;
led1 = !led1;
sleep_ms(500);
multicore_fifo_push_blocking((int32_t) &factorial);
multicore_fifo_push_blocking((int32_t)TEST_NUM);
// We could now do a load of stuff on core 0 and get our result later
res = multicore_fifo_pop_blocking();
Serial1.println("Factorial " + String(TEST_NUM,DEC) + " is " + String(res, DEC));
// Now try a different function
led1 = !led1;
sleep_ms(500);
multicore_fifo_push_blocking((int32_t) &fibonacci);
multicore_fifo_push_blocking((int32_t)TEST_NUM);
res = multicore_fifo_pop_blocking();
Serial1.println("Fibonacci " + String(TEST_NUM,DEC) + " is " + String(res, DEC));
}