Upcoming maintenance
Dear Customers and Partners.
This website will be undergoing scheduled maintenance on June 14, 2023. Please be aware there may be disruption to the developer portal website and associated services during the scheduled maintenance period.
This upgrade is essential to ensure the continued performance, reliability, and security of Developer World.
We apologize for any inconvenience.
How to synchronize all subcores? Can global variables be implemented?
-
Hello everyone,
do you know if there is a simple way to synchronize the operations between the subcores? Is it possible for example to create global variables shared between them?
If we look at the following simple LED blinking code, the subcore1 should wait for the subcore2 (slower) to end before executing again the "if" condition in its main loop, but this doesn't happen as the boolean variables "sub1_ended" and "sub2_ended" are not shared...
#include <MP.h> bool sub1_ended = TRUE; bool sub2_ended = TRUE; #if !SUBCORE // SETUP void setup(){ // Boot SubCores int ret = 0; int subid; for (subid = 1; subid <= 2; subid++) { ret = MP.begin(subid); if (ret < 0) { MPLog("MP.begin(%d) error = %d\n", subid, ret); } } } void loop(){ } #elif (SUBCORE == 1) void setup(){ MP.begin(); } void loop(){ if(sub1_ended && sub2_ended){ delay(10); sub1_ended = FALSE; // tasks... digitalWrite(LED0,HIGH); delay(1000); digitalWrite(LED0,LOW); delay(1000); sub1_ended = TRUE; } } #elif (SUBCORE == 2) void setup(){ MP.begin(); } void loop(){ if(sub1_ended && sub2_ended){ delay(10); sub2_ended = FALSE; // tasks... digitalWrite(LED1,HIGH); delay(2000); digitalWrite(LED1,LOW); delay(2000); sub2_ended = TRUE; } } #endif
Any idea on how to create a synchronization between multiple cores in order to execute part of operations at the same time?
P.S. I actually found a way to do it, by writing/reading on the GPIO (as it's shared between all the cores), but I think it's a little bit an overkill method.
Thank you very much.
Cheers,Ivan
-
Hi @ivan
Please see the code below. I have modified your code to make it easier for you to understand what I did. The solution is that the main core sends the address to the variables to the sub cores, so they have access to the same variable.
#include <MP.h> typedef struct { bool *sub1_ended; bool *sub2_ended; } sub_ended_t; #if !SUBCORE bool sub1_ended = TRUE; bool sub2_ended = TRUE; // SETUP void setup(){ // Boot SubCores int ret = 0; int subid; sub_ended_t sub_ended; sub_ended.sub1_ended = &sub1_ended; sub_ended.sub2_ended = &sub2_ended; for (subid = 1; subid <= 2; subid++) { ret = MP.begin(subid); if (ret < 0) { MPLog("MP.begin(%d) error = %d\n", subid, ret); } ret = MP.Send(0, &sub_ended, subid); if (ret < 0) { MPLog("MP.Send error = %d\n", ret); } } } void loop(){ } #elif (SUBCORE == 1) bool *sub1_ended; bool *sub2_ended; void setup(){ int ret = 0; MP.begin(); /* Timeout 1000 msec */ MP.RecvTimeout(1000); uint8_t msgid; sub_ended_t *sub_ended; ret = MP.Recv(&msgid, &sub_ended); if (ret < 0) { printf("MP.Recv error = %d\n", ret); } sub1_ended = sub_ended->sub1_ended; sub2_ended = sub_ended->sub2_ended; } void loop(){ if(*sub1_ended && *sub2_ended){ delay(10); *sub1_ended = FALSE; // tasks... digitalWrite(LED0,HIGH); delay(1000); digitalWrite(LED0,LOW); delay(1000); *sub1_ended = TRUE; } } #elif (SUBCORE == 2) bool *sub1_ended; bool *sub2_ended; void setup(){ int ret = 0; MP.begin(); /* Timeout 1000 msec */ MP.RecvTimeout(1000); uint8_t msgid; sub_ended_t *sub_ended; ret = MP.Recv(&msgid, &sub_ended); if (ret < 0) { printf("MP.Recv error = %d\n", ret); } sub1_ended = sub_ended->sub1_ended; sub2_ended = sub_ended->sub2_ended; } void loop(){ if(*sub1_ended && *sub2_ended){ delay(10); *sub2_ended = FALSE; // tasks... digitalWrite(LED1,HIGH); delay(2000); digitalWrite(LED1,LOW); delay(2000); *sub2_ended = TRUE; } } #endif
I hope it will help.
Best Regards,
Kamil Tomaszewski -
@kamiltomaszewski thank you very much, it's exactly what I was looking for