I think I found two reasons for the status bar occasionally getting corrupted?
1. Both cores updating same buffer
If both cores are executing the ui_statusbar_update() function at the same time, this can lead to corruption of the status bar contents.
Here’s a copy of the details in github issue #126:
this is clearly possible in the code...
The function ui_statusbar_update() is called from four locations:
- Core1: when
lcd_update_requestwas set totrue - Core0: when configuration file exists, at terminal connect
- Core0: when user configures to use ANSI toolbar
- Core0: when
clscommand is handled
The primary location where the status bar contents are
updated is from Core1, when the flag lcd_update_request
is set to true. This flag is set to true in all the
following scenarios:
- Inter-core message
BP_ICM_ENABLE_LCD_UPDATESprocessed - Inter-core message
BP_ICM_FORCE_LCD_UPDATEprocessed - Every 500ms by the lcd_timer_callback() function
However, the function is ALSO called from Core0 in
the above three locations.
Therefore, if Core0 is handling the user command cls, and
Core1 simultaneously is looping just after the 500ms timer
fired, both cores could call into the function simultaneously.
2. Buffer can be modified while it’s in use
As a second issue, after preparing the status bar with ui_statusbar_update(), Core1 will eventually handle actually sending the updated status bar characters to the terminal. Nothing prevent Core0 from causing the statusbar to be updated AGAIN, even in the midst of Core1 sending the buffer across the USB port.
Early thoughts on a fix
The simplest fix is to have core1 be the only core which updates the buffer.
Perhaps, if the ui_statusbar_update() function is called from Core0, it should instead send inter-core message BP_ICM_FORCE_LCD_UPDATE?
void ui_statusbar_update(uint32_t update_flags) {
// new lines for the function...
uint core = get_core_num();
if (core == 0) {
icm_core0_send_message_synchronous(BP_ICM_FORCE_LCD_UPDATE);
return;
}
// ... and then the existing functionality.
This would appear to cause UI_UPDATE_ALL, which seems functionally equivalent to the existing code, except that it also re-enables the LCD refresh IRQ. So, maybe adding a new ICM_ message specifically for ensuring the function is handled in Core1?
