From b397856366e107cf3fddf753f0a4ceeb867b3d08 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ond=C5=99ej=20Hru=C5=A1ka?= Date: Fri, 17 Mar 2023 00:41:35 +0100 Subject: [PATCH] add safety system, stub of new gui task --- Core/Inc/main.h | 2 + Core/Src/app_buzzer.c | 2 +- Core/Src/app_gui.c | 83 +++++++++++- Core/Src/app_heater.c | 23 +++- Core/Src/app_main.c | 271 +++++++++++++++++++--------------------- Core/Src/app_oled.c | 3 + Core/Src/app_safety.c | 64 ++++++++++ Core/Src/app_safety.h | 30 +++++ Core/Src/app_temp.c | 13 +- Core/Src/main.c | 227 +++++++++++++++++---------------- Core/Src/stm32f1xx_it.c | 181 +++++++++++++-------------- Makefile | 7 +- 12 files changed, 546 insertions(+), 360 deletions(-) create mode 100644 Core/Src/app_safety.c create mode 100644 Core/Src/app_safety.h diff --git a/Core/Inc/main.h b/Core/Inc/main.h index 3c7b8aa..a88c7f4 100644 --- a/Core/Inc/main.h +++ b/Core/Inc/main.h @@ -51,6 +51,8 @@ extern "C" { /* Private includes ----------------------------------------------------------*/ /* USER CODE BEGIN Includes */ +extern void app_emergency_stop(void); + #define __weak __attribute__((weak)) /* USER CODE END Includes */ diff --git a/Core/Src/app_buzzer.c b/Core/Src/app_buzzer.c index ec61f8f..e453da1 100644 --- a/Core/Src/app_buzzer.c +++ b/Core/Src/app_buzzer.c @@ -19,8 +19,8 @@ void app_buzzer_init() { /* Enable buzzer PWM */ LL_TIM_OC_SetCompareCH1(TIM_BUZZER, 0); - LL_TIM_EnableCounter(TIM_BUZZER); LL_TIM_CC_EnableChannel(TIM_BUZZER, LL_TIM_CHANNEL_CH1); + LL_TIM_EnableCounter(TIM_BUZZER); // HAL_TIM_PWM_Start(&htim2, TIM_CHANNEL_1); // s_timer = xTimerCreate("beep", 50, 0, NULL, app_beep_end); diff --git a/Core/Src/app_gui.c b/Core/Src/app_gui.c index 75f171d..b4d9229 100644 --- a/Core/Src/app_gui.c +++ b/Core/Src/app_gui.c @@ -4,19 +4,90 @@ #include #include "app_gui.h" +#include "app_heater.h" +#include "app_buzzer.h" +#include "app_temp.h" #include "FreeRTOS.h" #include "task.h" #include "queue.h" +#include "ufb/framebuffer.h" +#include "ufb/fb_text.h" + +#define MAX_TEMP 400 + +static struct State { + float oven_temp; + float soc_temp; + int set_temp; + int set_temp_wheel; + bool heater_enabled; +} s_app = {}; + +static void calc_set_temp() { + int clamped = s_app.set_temp_wheel; + if (clamped < 0) { + clamped = 0; + } + s_app.set_temp = (clamped / 2) * 5; + if (s_app.set_temp > MAX_TEMP) { + s_app.set_temp = MAX_TEMP; + } + + app_heater_set_target((float) s_app.set_temp); +} void app_task_gui(void *argument) { - PRINTF("app_task_gui\r\n"); + // Wait until inited + ulTaskNotifyTake(pdTRUE, portMAX_DELAY); + PUTS("GUI task starts\r\n"); + + char tmp[100]; + while (1) { - uint8_t message = 0; - bool suc = osMessageQueueGet(guiEventQueHandle, &message, NULL, pdMS_TO_TICKS(1000)); + s_app.oven_temp = app_temp_read_oven(); + s_app.soc_temp = app_temp_read_soc(); - if (suc == osOK && (message != GUI_NOTIFY_TEMP_CHANGE)) { - // input events - PRINTF("Event %d\r\n", message); + uint32_t message = GUI_EVENT_NONE; + osMessageQueueGet(guiEventQueHandle, &message, NULL, pdMS_TO_TICKS(1000)); + + switch (message) { + case GUI_NOTIFY_KNOB_PLUS: + s_app.set_temp_wheel++; + calc_set_temp(); + break; + case GUI_NOTIFY_KNOB_MINUS: + s_app.set_temp_wheel--; + calc_set_temp(); + break; + case GUI_NOTIFY_KNOB_PRESS: + break; + case GUI_NOTIFY_KNOB_RELEASE: + s_app.heater_enabled ^= 1; + app_heater_enable(s_app.heater_enabled); + app_buzzer_beep(); + break; + default: + break; } + + fb_clear(); + + SPRINTF(tmp, "T=%.1f°C", s_app.oven_temp); + fb_text(3, 3, tmp, FONT_5X7, 1); + + SPRINTF(tmp, "Cil=%d°C", s_app.set_temp); + fb_text(3, 11, tmp, FONT_5X7, 1); + + SPRINTF(tmp, "Stav=%s", s_app.heater_enabled ? "ZAP" : "VYP"); + fb_text(3, 19, tmp, FONT_5X7, 1); + + SPRINTF(tmp, "Tsoc=%.1f°C", s_app.soc_temp); + fb_text(3, 27, tmp, FONT_5X7, 1); + + if (s_app.heater_enabled) { + fb_frame(0, 0, FBW, FBH, 2, 1); + } + + fb_blit(); } } diff --git a/Core/Src/app_heater.c b/Core/Src/app_heater.c index e464c67..2e3b7c3 100644 --- a/Core/Src/app_heater.c +++ b/Core/Src/app_heater.c @@ -9,6 +9,7 @@ #include "tim.h" #include "queue.h" #include "app_gui.h" +#include "app_safety.h" extern osMutexId_t heaterMutexHandle; @@ -81,16 +82,31 @@ void app_heater_set_target(float target) { heaterExitCritical(); } +// emergency shutdown, this must not block use RTOS since it can be called from fault handlers or interrupt void app_heater_emergency_shutdown() { - PID_SetCtlMode(&state.pid, PID_MANUAL); - - // TODO check if this really turns the channel off! + // Stop pwm LL_TIM_OC_SetCompareCH1(TIM_HEATER, 0); LL_TIM_CC_DisableChannel(TIM_HEATER, LL_TIM_CHANNEL_CH1); + LL_TIM_DisableCounter(TIM_HEATER); + + // Also kill the GPIO PWM output + LL_GPIO_InitTypeDef GPIO_InitStruct = {}; + GPIO_InitStruct.Pin = PWM_HEATER_Pin; + GPIO_InitStruct.Mode = LL_GPIO_MODE_OUTPUT; + GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_LOW; + GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_PUSHPULL; + LL_GPIO_Init(PWM_HEATER_GPIO_Port, &GPIO_InitStruct); + + // Output zero + LL_GPIO_ResetOutputPin(PWM_HEATER_GPIO_Port, PWM_HEATER_Pin); } void app_task_heater(void *argument) { + // Wait until inited + ulTaskNotifyTake(pdTRUE, portMAX_DELAY); + PUTS("Heater task starts\r\n"); + heater_pwm_init(); heaterEnterCritical(); @@ -110,6 +126,7 @@ void app_task_heater(void *argument) xQueueSend(guiEventQueHandle, &ev, pdMS_TO_TICKS(100)); heaterEnterCritical(); + app_safety_pass_reg_loop_running(); PID_Compute(&state.pid, state.oven_temp); if (state.pid.ctlMode == PID_AUTOMATIC) { PRINTF("temp %d, output %d\r\n", (int) state.oven_temp, (int) state.pid.Output); diff --git a/Core/Src/app_main.c b/Core/Src/app_main.c index 69b8372..20101c3 100644 --- a/Core/Src/app_main.c +++ b/Core/Src/app_main.c @@ -12,101 +12,88 @@ #include "ufb/framebuffer.h" #include "iwdg.h" #include "app_oled.h" -#include "ufb/fb_text.h" -#include "ufb/fb_7seg.h" +//#include "ufb/fb_text.h" +//#include "ufb/fb_7seg.h" #include "app_temp.h" #include "app_knob.h" #include "app_buzzer.h" -#include "app_heater.h" -#include "cmsis_os2.h" +//#include "app_heater.h" +//#include "cmsis_os2.h" #include "eeprom_emul.h" +#include "app_safety.h" +#include "cmsis_os2.h" -static struct App { - float oven_temp; - int16_t set_temp; - int16_t wheel_normed; - uint16_t wheel; - bool run; -} s_app = {}; - -static void redraw_display() { - fb_clear(); - - char tmp[100]; - - SPRINTF(tmp, "T=%d°C", (int) s_app.oven_temp); - fb_text(3, 3, tmp, FONT_5X7, 1); - - SPRINTF(tmp, "Cil=%d°C", s_app.set_temp); - fb_text(3, 11, tmp, FONT_5X7, 1); - - SPRINTF(tmp, "Stav=%s", s_app.run ? "ZAP" : "VYP"); - fb_text(3, 19, tmp, FONT_5X7, 1); - - if (s_app.run) { - fb_frame(0, 0, FBW, FBH, 2, 1); - } - - // some funny effects to showcase responsiveness and circle drawing - - fb_circle(FBW / 2, 70, 18, 1, 1); - - for (int i = 0; i < 6; i++) { - float x = FBW / 2; - float y = 70; - - int ii = i; - - float angle = (float) ii * (M_PI / 3.0) - s_app.wheel_normed * (M_PI / 24); - - x = x + sinf(angle) * 10; - y = y + cosf(angle) * 10; - - fb_circle((fbpos_t) x, (fbpos_t) y, 4, i==0?4:1, 1); - } - - fb_text(0, s_app.wheel_normed, ":3 :3", FONT_4X5, 1); - - fb_7seg_number( - 2, FBH - 20, - 10, 16, - 2, // th - 2, // spacing - 1, // color - s_app.wheel, - 4, // places - 2);// decimals - - - - fb_blit(); -} +extern osThreadId_t heaterTskHandle; +extern osThreadId_t mainTskHandle; +extern osThreadId_t guiTskHandle; + +//static struct App { +// float oven_temp; +// int16_t set_temp; +// int16_t wheel_normed; +// uint16_t wheel; +// bool run; +//} s_app = {}; + +//static void redraw_display() { +// fb_clear(); +// +// char tmp[100]; +// +// SPRINTF(tmp, "T=%d°C", (int) s_app.oven_temp); +// fb_text(3, 3, tmp, FONT_5X7, 1); +// +// SPRINTF(tmp, "Cil=%d°C", s_app.set_temp); +// fb_text(3, 11, tmp, FONT_5X7, 1); +// +// SPRINTF(tmp, "Stav=%s", s_app.run ? "ZAP" : "VYP"); +// fb_text(3, 19, tmp, FONT_5X7, 1); +// +// if (s_app.run) { +// fb_frame(0, 0, FBW, FBH, 2, 1); +// } +// +// // some funny effects to showcase responsiveness and circle drawing +// +// fb_circle(FBW / 2, 70, 18, 1, 1); +// +// for (int i = 0; i < 6; i++) { +// float x = FBW / 2; +// float y = 70; +// +// int ii = i; +// +// float angle = (float) ii * (M_PI / 3.0) - s_app.wheel_normed * (M_PI / 24); +// +// x = x + sinf(angle) * 10; +// y = y + cosf(angle) * 10; +// +// fb_circle((fbpos_t) x, (fbpos_t) y, 4, i==0?4:1, 1); +// } +// +// fb_text(0, s_app.wheel_normed, ":3 :3", FONT_4X5, 1); +// +// fb_7seg_number( +// 2, FBH - 20, +// 10, 16, +// 2, // th +// 2, // spacing +// 1, // color +// s_app.wheel, +// 4, // places +// 2);// decimals +// +// +// +// fb_blit(); +//} void app_task_main(void *argument) { PUTS("Main task\r\n"); - /* test the persistent storage */ EE_Init(EE_CONDITIONAL_ERASE); - uint32_t cnt = 0; - EE_Status eest = EE_ReadVariable32bits(1, &cnt); - - PRINTF("EE rd status %d, cnt %d\r\n", eest, cnt); - - cnt++; - - eest = EE_WriteVariable32bits(1, cnt); - PRINTF("EE wr status %d\r\n", eest); - if (eest == EE_CLEANUP_REQUIRED) { - eest = EE_CleanUp(); - PRINTF("EE cleanup status %d\r\n", eest); - } - - - - - app_analog_init(); app_buzzer_init(); app_knob_init(); @@ -115,74 +102,78 @@ void app_task_main(void *argument) oled_init(); fb_clear(); + /* all inited */ + + // notify threads that we are ready + xTaskNotifyGive(guiTskHandle); + xTaskNotifyGive(heaterTskHandle); + // while(1) { // LL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin); // vTaskDelay(pdMS_TO_TICKS(250)); // LL_IWDG_ReloadCounter(IWDG); // } +// /* Infinite loop */ +// bool old_pushed = app_knob_pushed(); +// +// bool any_change = true; +// uint32_t last_redraw = osKernelGetTickCount(); - - /* Infinite loop */ - bool old_pushed = app_knob_pushed(); - - bool any_change = true; - uint32_t last_redraw = osKernelGetTickCount(); - - PUTS("Loop\r\n"); + PUTS("Main loop\r\n"); for (;;) { // sampling is done in the heater loop - s_app.oven_temp = app_temp_read_oven(); - - uint16_t old_wheel = s_app.wheel; - s_app.wheel = app_knob_get_raw(); - - // TODO do this with interrupt and/or debouncing - bool pushed = app_knob_pushed(); - if (pushed && !old_pushed) { - s_app.run ^= 1; - app_heater_enable(s_app.run); - app_buzzer_beep(); - any_change = true; - } - old_pushed = pushed; - - - int16_t wheel_change = (int16_t)(s_app.wheel - old_wheel); - if (wheel_change != 0) { - s_app.wheel_normed += wheel_change; - if (s_app.wheel_normed < 0) { - s_app.wheel_normed = 0; - } - if (s_app.wheel_normed > 500) { - s_app.wheel_normed = 500; - } - - int16_t old_temp = s_app.set_temp; - - s_app.set_temp = (s_app.wheel_normed / 2) * 5; - - if (old_temp != s_app.set_temp) { - app_buzzer_beep(); - app_heater_set_target((float) s_app.set_temp); - any_change = true; - } - } - - uint32_t now = osKernelGetTickCount(); - if (any_change || (now - last_redraw > pdMS_TO_TICKS(500))) { - last_redraw = now; - redraw_display(); - any_change = false; - - // Blink - LL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin); - } - - vTaskDelay(pdMS_TO_TICKS(10)); +// s_app.oven_temp = app_temp_read_oven(); +// +// uint16_t old_wheel = s_app.wheel; +// s_app.wheel = app_knob_get_raw(); +// +// // TODO do this with interrupt and/or debouncing +// bool pushed = app_knob_pushed(); +// if (pushed && !old_pushed) { +// s_app.run ^= 1; +// app_heater_enable(s_app.run); +// app_buzzer_beep(); +// any_change = true; +// } +// old_pushed = pushed; +// +// +// int16_t wheel_change = (int16_t)(s_app.wheel - old_wheel); +// if (wheel_change != 0) { +// s_app.wheel_normed += wheel_change; +// if (s_app.wheel_normed < 0) { +// s_app.wheel_normed = 0; +// } +// if (s_app.wheel_normed > 500) { +// s_app.wheel_normed = 500; +// } +// +// int16_t old_temp = s_app.set_temp; +// +// s_app.set_temp = (s_app.wheel_normed / 2) * 5; +// +// if (old_temp != s_app.set_temp) { +// app_buzzer_beep(); +// app_heater_set_target((float) s_app.set_temp); +// any_change = true; +// } +// } +// +// uint32_t now = osKernelGetTickCount(); +// if (any_change || (now - last_redraw > pdMS_TO_TICKS(500))) { +// last_redraw = now; +// redraw_display(); +// any_change = false; +// +// // Blink +// +// } + + vTaskDelay(pdMS_TO_TICKS(100)); // feed dogs - LL_IWDG_ReloadCounter(IWDG); + app_safety_poll(); } } diff --git a/Core/Src/app_oled.c b/Core/Src/app_oled.c index 615c062..71d0c17 100644 --- a/Core/Src/app_oled.c +++ b/Core/Src/app_oled.c @@ -9,6 +9,7 @@ #include "gpio.h" #include "spi.h" #include "FreeRTOS.h" +#include "app_safety.h" #define SSD1309_HEIGHT 64 @@ -236,6 +237,8 @@ void oled_data(uint8_t *data, int len) void fb_blit() { + app_safety_pass_display_updating(); + #if 0 oled_data(fb, FB_LEN); #else diff --git a/Core/Src/app_safety.c b/Core/Src/app_safety.c new file mode 100644 index 0000000..9419e45 --- /dev/null +++ b/Core/Src/app_safety.c @@ -0,0 +1,64 @@ +/** + * TODO file description + */ + +#include "app_safety.h" +#include "app_heater.h" +#include "snprintf.h" +#include "stm32f1xx_ll_iwdg.h" +#include "stm32f1xx_ll_gpio.h" +#include "main.h" + +#define HB_FLAG_TEMP_NORMAL (1 << 0) +#define HB_FLAG_ADC_SAMPLING (1 << 1) +#define HB_FLAG_TEMP_CALCULATION (1 << 2) +#define HB_FLAG_REG_LOOP (1 << 3) +#define HB_FLAG_DISPLAY_UPDATING (1 << 4) +#define HB_FLAG_SOC_TEMP_OK (1 << 5) + +#define HB_FLAG_ALL (0b111111) + +static volatile uint32_t heartbeat_flags = 0; + +void app_safety_pass_temp_normal() { + heartbeat_flags |= HB_FLAG_TEMP_NORMAL; +} + +void app_safety_pass_adc_sampling() { + heartbeat_flags |= HB_FLAG_ADC_SAMPLING; +} + +void app_safety_pass_temp_calculation() { + heartbeat_flags |= HB_FLAG_TEMP_CALCULATION; +} + +void app_safety_pass_reg_loop_running() { + heartbeat_flags |= HB_FLAG_REG_LOOP; +} + +void app_safety_pass_display_updating() { + heartbeat_flags |= HB_FLAG_DISPLAY_UPDATING; +} + +void app_safety_pass_soc_temp_ok() { + heartbeat_flags |= HB_FLAG_SOC_TEMP_OK; +} + +void app_safety_poll() { + if ((heartbeat_flags & HB_FLAG_ALL) == HB_FLAG_ALL) { + LL_IWDG_ReloadCounter(IWDG); + LL_GPIO_TogglePin(LED_GPIO_Port, LED_Pin); + heartbeat_flags = 0; + } +} + +// emergency shutdown, this must not block use RTOS since it can be called from fault handlers or interrupt +void __attribute__((noreturn)) app_emergency_stop() { + app_heater_emergency_shutdown(); + + PUTS("\r\n*** EMERGENCY STOP ***\r\n"); + + while (1) { + // wait for the watchdog to bite + } +} diff --git a/Core/Src/app_safety.h b/Core/Src/app_safety.h new file mode 100644 index 0000000..54f6a25 --- /dev/null +++ b/Core/Src/app_safety.h @@ -0,0 +1,30 @@ +/** + * TODO file description + */ + +#ifndef BLUEPILLTROUBA_APP_SAFETY_H +#define BLUEPILLTROUBA_APP_SAFETY_H + +/** + * Check the pass flags. If all are set, reset the WD and clear flags. + * + * This effectively makes the WD bite when either of the subsystems fails. + */ +void app_safety_poll(); + +void app_emergency_stop() +__attribute__((noreturn)); + +void app_safety_pass_temp_normal(); + +void app_safety_pass_adc_sampling(); + +void app_safety_pass_temp_calculation(); + +void app_safety_pass_reg_loop_running(); + +void app_safety_pass_display_updating(); + +void app_safety_pass_soc_temp_ok(); + +#endif //BLUEPILLTROUBA_APP_SAFETY_H diff --git a/Core/Src/app_temp.c b/Core/Src/app_temp.c index 0f88f74..0bba73f 100644 --- a/Core/Src/app_temp.c +++ b/Core/Src/app_temp.c @@ -10,6 +10,7 @@ #include "app_temp.h" #include "adc.h" #include "snprintf.h" +#include "app_safety.h" /* DMA dest */ static volatile uint16_t adc_values[4]; @@ -233,6 +234,16 @@ void app_temp_sample() sum /= depth; } s_analog.oven_temp = sum; + + app_safety_pass_temp_calculation(); + + if (s_analog.oven_temp >= 5.0 && s_analog.oven_temp <= 455.0) { + app_safety_pass_temp_normal(); + } + + if (s_analog.soc_temp >= 5.0 && s_analog.soc_temp <= 80.0) { + app_safety_pass_soc_temp_ok(); + } } float app_temp_read_oven() @@ -247,7 +258,7 @@ float app_temp_read_soc() void app_temp_adc_eos() { - //PUTCHAR('a'); + app_safety_pass_adc_sampling(); // notify memcpy((void *) &s_analog.adc_averagebuf[s_analog.averagebuf_ptr * 4], (const void *) adc_values, 4 * sizeof(uint16_t)); diff --git a/Core/Src/main.c b/Core/Src/main.c index ae4f373..1bf3415 100644 --- a/Core/Src/main.c +++ b/Core/Src/main.c @@ -59,6 +59,7 @@ /* Private function prototypes -----------------------------------------------*/ void SystemClock_Config(void); + void MX_FREERTOS_Init(void); /* USER CODE BEGIN PFP */ @@ -75,74 +76,74 @@ void MX_FREERTOS_Init(void); */ int main(void) { - /* USER CODE BEGIN 1 */ + /* USER CODE BEGIN 1 */ - /* USER CODE END 1 */ + /* USER CODE END 1 */ - /* MCU Configuration--------------------------------------------------------*/ + /* MCU Configuration--------------------------------------------------------*/ - /* Reset of all peripherals, Initializes the Flash interface and the Systick. */ - LL_APB2_GRP1_EnableClock(LL_APB2_GRP1_PERIPH_AFIO); - LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_PWR); + /* Reset of all peripherals, Initializes the Flash interface and the Systick. */ + LL_APB2_GRP1_EnableClock(LL_APB2_GRP1_PERIPH_AFIO); + LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_PWR); - /* System interrupt init*/ - NVIC_SetPriorityGrouping(NVIC_PRIORITYGROUP_4); + /* System interrupt init*/ + NVIC_SetPriorityGrouping(NVIC_PRIORITYGROUP_4); - /* PendSV_IRQn interrupt configuration */ - NVIC_SetPriority(PendSV_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),15, 0)); - /* SysTick_IRQn interrupt configuration */ - NVIC_SetPriority(SysTick_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(),15, 0)); + /* PendSV_IRQn interrupt configuration */ + NVIC_SetPriority(PendSV_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 15, 0)); + /* SysTick_IRQn interrupt configuration */ + NVIC_SetPriority(SysTick_IRQn, NVIC_EncodePriority(NVIC_GetPriorityGrouping(), 15, 0)); - /** NOJTAG: JTAG-DP Disabled and SW-DP Enabled - */ - LL_GPIO_AF_Remap_SWJ_NOJTAG(); - - /* USER CODE BEGIN Init */ - - /* USER CODE END Init */ - - /* Configure the system clock */ - SystemClock_Config(); - - /* USER CODE BEGIN SysInit */ - - MX_DMA_Init(); - /* USER CODE END SysInit */ - - /* Initialize all configured peripherals */ - MX_GPIO_Init(); - MX_IWDG_Init(); - MX_USART1_UART_Init(); - MX_ADC1_Init(); - MX_DMA_Init(); - MX_TIM4_Init(); - MX_TIM2_Init(); - MX_TIM3_Init(); - MX_SPI2_Init(); - MX_TIM1_Init(); - MX_CRC_Init(); - /* USER CODE BEGIN 2 */ - - PUTS("Start.\r\n"); - /* USER CODE END 2 */ - - /* Init scheduler */ - osKernelInitialize(); /* Call init function for freertos objects (in freertos.c) */ - MX_FREERTOS_Init(); - - /* Start scheduler */ - osKernelStart(); - - /* We should never get here as control is now taken by the scheduler */ - /* Infinite loop */ - /* USER CODE BEGIN WHILE */ - while (1) - { - /* USER CODE END WHILE */ - - /* USER CODE BEGIN 3 */ - } - /* USER CODE END 3 */ + /** NOJTAG: JTAG-DP Disabled and SW-DP Enabled + */ + LL_GPIO_AF_Remap_SWJ_NOJTAG(); + + /* USER CODE BEGIN Init */ + + /* USER CODE END Init */ + + /* Configure the system clock */ + SystemClock_Config(); + + /* USER CODE BEGIN SysInit */ + + MX_DMA_Init(); + /* USER CODE END SysInit */ + + /* Initialize all configured peripherals */ + MX_GPIO_Init(); + MX_IWDG_Init(); + MX_USART1_UART_Init(); + MX_ADC1_Init(); + MX_DMA_Init(); + MX_TIM4_Init(); + MX_TIM2_Init(); + MX_TIM3_Init(); + MX_SPI2_Init(); + MX_TIM1_Init(); + MX_CRC_Init(); + /* USER CODE BEGIN 2 */ + + PUTS("Start.\r\n"); + /* USER CODE END 2 */ + + /* Init scheduler */ + osKernelInitialize(); /* Call init function for freertos objects (in freertos.c) */ + MX_FREERTOS_Init(); + + /* Start scheduler */ + osKernelStart(); + + /* We should never get here as control is now taken by the scheduler */ + /* Infinite loop */ + /* USER CODE BEGIN WHILE */ + app_emergency_stop(); + while (1) { + /* USER CODE END WHILE */ + + /* USER CODE BEGIN 3 */ + } + /* USER CODE END 3 */ } /** @@ -151,46 +152,41 @@ int main(void) */ void SystemClock_Config(void) { - LL_FLASH_SetLatency(LL_FLASH_LATENCY_2); - while(LL_FLASH_GetLatency()!= LL_FLASH_LATENCY_2) - { - } - LL_RCC_HSI_SetCalibTrimming(16); - LL_RCC_HSI_Enable(); - - /* Wait till HSI is ready */ - while(LL_RCC_HSI_IsReady() != 1) - { - - } - LL_RCC_LSI_Enable(); - - /* Wait till LSI is ready */ - while(LL_RCC_LSI_IsReady() != 1) - { - - } - LL_RCC_PLL_ConfigDomain_SYS(LL_RCC_PLLSOURCE_HSI_DIV_2, LL_RCC_PLL_MUL_16); - LL_RCC_PLL_Enable(); - - /* Wait till PLL is ready */ - while(LL_RCC_PLL_IsReady() != 1) - { - - } - LL_RCC_SetAHBPrescaler(LL_RCC_SYSCLK_DIV_1); - LL_RCC_SetAPB1Prescaler(LL_RCC_APB1_DIV_2); - LL_RCC_SetAPB2Prescaler(LL_RCC_APB2_DIV_1); - LL_RCC_SetSysClkSource(LL_RCC_SYS_CLKSOURCE_PLL); - - /* Wait till System clock is ready */ - while(LL_RCC_GetSysClkSource() != LL_RCC_SYS_CLKSOURCE_STATUS_PLL) - { - - } - LL_Init1msTick(64000000); - LL_SetSystemCoreClock(64000000); - LL_RCC_SetADCClockSource(LL_RCC_ADC_CLKSRC_PCLK2_DIV_8); + LL_FLASH_SetLatency(LL_FLASH_LATENCY_2); + while (LL_FLASH_GetLatency() != LL_FLASH_LATENCY_2) { + } + LL_RCC_HSI_SetCalibTrimming(16); + LL_RCC_HSI_Enable(); + + /* Wait till HSI is ready */ + while (LL_RCC_HSI_IsReady() != 1) { + + } + LL_RCC_LSI_Enable(); + + /* Wait till LSI is ready */ + while (LL_RCC_LSI_IsReady() != 1) { + + } + LL_RCC_PLL_ConfigDomain_SYS(LL_RCC_PLLSOURCE_HSI_DIV_2, LL_RCC_PLL_MUL_16); + LL_RCC_PLL_Enable(); + + /* Wait till PLL is ready */ + while (LL_RCC_PLL_IsReady() != 1) { + + } + LL_RCC_SetAHBPrescaler(LL_RCC_SYSCLK_DIV_1); + LL_RCC_SetAPB1Prescaler(LL_RCC_APB1_DIV_2); + LL_RCC_SetAPB2Prescaler(LL_RCC_APB2_DIV_1); + LL_RCC_SetSysClkSource(LL_RCC_SYS_CLKSOURCE_PLL); + + /* Wait till System clock is ready */ + while (LL_RCC_GetSysClkSource() != LL_RCC_SYS_CLKSOURCE_STATUS_PLL) { + + } + LL_Init1msTick(64000000); + LL_SetSystemCoreClock(64000000); + LL_RCC_SetADCClockSource(LL_RCC_ADC_CLKSRC_PCLK2_DIV_8); } /* USER CODE BEGIN 4 */ @@ -203,17 +199,16 @@ void SystemClock_Config(void) */ void Error_Handler(void) { - /* USER CODE BEGIN Error_Handler_Debug */ - /* User can add his own implementation to report the HAL error return state */ - __disable_irq(); - PUTS("Error_Handler\r\n"); - while (1) - { - } - /* USER CODE END Error_Handler_Debug */ + /* USER CODE BEGIN Error_Handler_Debug */ + /* User can add his own implementation to report the HAL error return state */ + __disable_irq(); + PUTS("Error_Handler\r\n"); + app_emergency_stop(); + /* USER CODE END Error_Handler_Debug */ } #ifdef USE_FULL_ASSERT + /** * @brief Reports the name of the source file and the source line number * where the assert_param error has occurred. @@ -223,10 +218,12 @@ void Error_Handler(void) */ void assert_failed(uint8_t *file, uint32_t line) { - /* USER CODE BEGIN 6 */ - PRINTF("assert_failed %s:%d", (const char *) file, (int) line); - /* User can add his own implementation to report the file name and line number, - ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */ - /* USER CODE END 6 */ + /* USER CODE BEGIN 6 */ + PRINTF("assert_failed %s:%d", (const char *) file, (int) line); + app_emergency_stop(); + /* User can add his own implementation to report the file name and line number, + ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */ + /* USER CODE END 6 */ } + #endif /* USE_FULL_ASSERT */ diff --git a/Core/Src/stm32f1xx_it.c b/Core/Src/stm32f1xx_it.c index 859f531..2f90d89 100644 --- a/Core/Src/stm32f1xx_it.c +++ b/Core/Src/stm32f1xx_it.c @@ -74,18 +74,19 @@ bool EE_NMI_Callback(); */ void NMI_Handler(void) { - /* USER CODE BEGIN NonMaskableInt_IRQn 0 */ - - if (EE_NMI_Callback()) { - return; - } - - /* USER CODE END NonMaskableInt_IRQn 0 */ - /* USER CODE BEGIN NonMaskableInt_IRQn 1 */ - while (1) - { - } - /* USER CODE END NonMaskableInt_IRQn 1 */ + /* USER CODE BEGIN NonMaskableInt_IRQn 0 */ + + if (EE_NMI_Callback()) { + return; + } + + app_emergency_stop(); + + /* USER CODE END NonMaskableInt_IRQn 0 */ + /* USER CODE BEGIN NonMaskableInt_IRQn 1 */ + while (1) { + } + /* USER CODE END NonMaskableInt_IRQn 1 */ } /** @@ -93,15 +94,15 @@ void NMI_Handler(void) */ void HardFault_Handler(void) { - /* USER CODE BEGIN HardFault_IRQn 0 */ - PUTS("HardFault_Handler\r\n"); - - /* USER CODE END HardFault_IRQn 0 */ - while (1) - { - /* USER CODE BEGIN W1_HardFault_IRQn 0 */ - /* USER CODE END W1_HardFault_IRQn 0 */ - } + /* USER CODE BEGIN HardFault_IRQn 0 */ + PUTS("HardFault_Handler\r\n"); + app_emergency_stop(); + + /* USER CODE END HardFault_IRQn 0 */ + while (1) { + /* USER CODE BEGIN W1_HardFault_IRQn 0 */ + /* USER CODE END W1_HardFault_IRQn 0 */ + } } /** @@ -109,15 +110,15 @@ void HardFault_Handler(void) */ void MemManage_Handler(void) { - /* USER CODE BEGIN MemoryManagement_IRQn 0 */ - PUTS("MemManage_Handler\r\n"); - - /* USER CODE END MemoryManagement_IRQn 0 */ - while (1) - { - /* USER CODE BEGIN W1_MemoryManagement_IRQn 0 */ - /* USER CODE END W1_MemoryManagement_IRQn 0 */ - } + /* USER CODE BEGIN MemoryManagement_IRQn 0 */ + PUTS("MemManage_Handler\r\n"); + app_emergency_stop(); + + /* USER CODE END MemoryManagement_IRQn 0 */ + while (1) { + /* USER CODE BEGIN W1_MemoryManagement_IRQn 0 */ + /* USER CODE END W1_MemoryManagement_IRQn 0 */ + } } /** @@ -125,15 +126,15 @@ void MemManage_Handler(void) */ void BusFault_Handler(void) { - /* USER CODE BEGIN BusFault_IRQn 0 */ - PUTS("BusFault_Handler\r\n"); - - /* USER CODE END BusFault_IRQn 0 */ - while (1) - { - /* USER CODE BEGIN W1_BusFault_IRQn 0 */ - /* USER CODE END W1_BusFault_IRQn 0 */ - } + /* USER CODE BEGIN BusFault_IRQn 0 */ + PUTS("BusFault_Handler\r\n"); + app_emergency_stop(); + /* USER CODE END BusFault_IRQn 0 */ + + while (1) { + /* USER CODE BEGIN W1_BusFault_IRQn 0 */ + /* USER CODE END W1_BusFault_IRQn 0 */ + } } /** @@ -141,15 +142,15 @@ void BusFault_Handler(void) */ void UsageFault_Handler(void) { - /* USER CODE BEGIN UsageFault_IRQn 0 */ - PUTS("UsageFault_Handler\r\n"); - - /* USER CODE END UsageFault_IRQn 0 */ - while (1) - { - /* USER CODE BEGIN W1_UsageFault_IRQn 0 */ - /* USER CODE END W1_UsageFault_IRQn 0 */ - } + /* USER CODE BEGIN UsageFault_IRQn 0 */ + PUTS("UsageFault_Handler\r\n"); + app_emergency_stop(); + /* USER CODE END UsageFault_IRQn 0 */ + + while (1) { + /* USER CODE BEGIN W1_UsageFault_IRQn 0 */ + /* USER CODE END W1_UsageFault_IRQn 0 */ + } } /** @@ -157,12 +158,12 @@ void UsageFault_Handler(void) */ void DebugMon_Handler(void) { - /* USER CODE BEGIN DebugMonitor_IRQn 0 */ + /* USER CODE BEGIN DebugMonitor_IRQn 0 */ - /* USER CODE END DebugMonitor_IRQn 0 */ - /* USER CODE BEGIN DebugMonitor_IRQn 1 */ + /* USER CODE END DebugMonitor_IRQn 0 */ + /* USER CODE BEGIN DebugMonitor_IRQn 1 */ - /* USER CODE END DebugMonitor_IRQn 1 */ + /* USER CODE END DebugMonitor_IRQn 1 */ } /** @@ -170,20 +171,19 @@ void DebugMon_Handler(void) */ void SysTick_Handler(void) { - /* USER CODE BEGIN SysTick_IRQn 0 */ + /* USER CODE BEGIN SysTick_IRQn 0 */ - /* USER CODE END SysTick_IRQn 0 */ - #if (INCLUDE_xTaskGetSchedulerState == 1 ) - if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) - { + /* USER CODE END SysTick_IRQn 0 */ +#if (INCLUDE_xTaskGetSchedulerState == 1) + if (xTaskGetSchedulerState() != taskSCHEDULER_NOT_STARTED) { #endif /* INCLUDE_xTaskGetSchedulerState */ - xPortSysTickHandler(); -#if (INCLUDE_xTaskGetSchedulerState == 1 ) - } + xPortSysTickHandler(); +#if (INCLUDE_xTaskGetSchedulerState == 1) + } #endif /* INCLUDE_xTaskGetSchedulerState */ - /* USER CODE BEGIN SysTick_IRQn 1 */ + /* USER CODE BEGIN SysTick_IRQn 1 */ - /* USER CODE END SysTick_IRQn 1 */ + /* USER CODE END SysTick_IRQn 1 */ } /******************************************************************************/ @@ -198,18 +198,18 @@ void SysTick_Handler(void) */ void DMA1_Channel1_IRQHandler(void) { - /* USER CODE BEGIN DMA1_Channel1_IRQn 0 */ + /* USER CODE BEGIN DMA1_Channel1_IRQn 0 */ - if (LL_DMA_IsActiveFlag_TC1(DMA1)) { - app_temp_adc_eos(); - LL_DMA_ClearFlag_TC1(DMA1); - } + if (LL_DMA_IsActiveFlag_TC1(DMA1)) { + app_temp_adc_eos(); + LL_DMA_ClearFlag_TC1(DMA1); + } - /* USER CODE END DMA1_Channel1_IRQn 0 */ + /* USER CODE END DMA1_Channel1_IRQn 0 */ - /* USER CODE BEGIN DMA1_Channel1_IRQn 1 */ + /* USER CODE BEGIN DMA1_Channel1_IRQn 1 */ - /* USER CODE END DMA1_Channel1_IRQn 1 */ + /* USER CODE END DMA1_Channel1_IRQn 1 */ } /** @@ -217,22 +217,21 @@ void DMA1_Channel1_IRQHandler(void) */ void EXTI9_5_IRQHandler(void) { - /* USER CODE BEGIN EXTI9_5_IRQn 0 */ - bool state = LL_GPIO_IsInputPinSet(KNOB_PUSH_GPIO_Port, KNOB_PUSH_Pin); + /* USER CODE BEGIN EXTI9_5_IRQn 0 */ + bool state = LL_GPIO_IsInputPinSet(KNOB_PUSH_GPIO_Port, KNOB_PUSH_Pin); - /* USER CODE END EXTI9_5_IRQn 0 */ - if (LL_EXTI_IsActiveFlag_0_31(LL_EXTI_LINE_8) != RESET) - { - LL_EXTI_ClearFlag_0_31(LL_EXTI_LINE_8); - /* USER CODE BEGIN LL_EXTI_LINE_8 */ + /* USER CODE END EXTI9_5_IRQn 0 */ + if (LL_EXTI_IsActiveFlag_0_31(LL_EXTI_LINE_8) != RESET) { + LL_EXTI_ClearFlag_0_31(LL_EXTI_LINE_8); + /* USER CODE BEGIN LL_EXTI_LINE_8 */ - app_knob_push_isr(0 == state); + app_knob_push_isr(0 == state); - /* USER CODE END LL_EXTI_LINE_8 */ - } - /* USER CODE BEGIN EXTI9_5_IRQn 1 */ + /* USER CODE END LL_EXTI_LINE_8 */ + } + /* USER CODE BEGIN EXTI9_5_IRQn 1 */ - /* USER CODE END EXTI9_5_IRQn 1 */ + /* USER CODE END EXTI9_5_IRQn 1 */ } /** @@ -240,19 +239,19 @@ void EXTI9_5_IRQHandler(void) */ void TIM4_IRQHandler(void) { - /* USER CODE BEGIN TIM4_IRQn 0 */ + /* USER CODE BEGIN TIM4_IRQn 0 */ - if (LL_TIM_IsActiveFlag_CC1(TIM4) || LL_TIM_IsActiveFlag_CC2(TIM4)) { - LL_TIM_ClearFlag_CC1(TIM4); - LL_TIM_ClearFlag_CC2(TIM4); - app_knob_turn_isr(); - } + if (LL_TIM_IsActiveFlag_CC1(TIM4) || LL_TIM_IsActiveFlag_CC2(TIM4)) { + LL_TIM_ClearFlag_CC1(TIM4); + LL_TIM_ClearFlag_CC2(TIM4); + app_knob_turn_isr(); + } - /* USER CODE END TIM4_IRQn 0 */ - /* USER CODE BEGIN TIM4_IRQn 1 */ + /* USER CODE END TIM4_IRQn 0 */ + /* USER CODE BEGIN TIM4_IRQn 1 */ - /* USER CODE END TIM4_IRQn 1 */ + /* USER CODE END TIM4_IRQn 1 */ } /* USER CODE BEGIN 1 */ diff --git a/Makefile b/Makefile index 2bb949e..ccc629c 100644 --- a/Makefile +++ b/Makefile @@ -1,5 +1,5 @@ ########################################################################################################################## -# File automatically-generated by tool: [projectgenerator] version: [3.16.0] date: [Tue Mar 14 20:49:50 CET 2023] +# File automatically-generated by tool: [projectgenerator] version: [3.16.0] date: [Tue Mar 14 20:49:50 CET 2023] ########################################################################################################################## # ------------------------------------------------ @@ -52,6 +52,7 @@ Core/Src/app_temp.c \ Core/Src/app_knob.c \ Core/Src/app_buzzer.c \ Core/Src/app_heater.c \ +Core/Src/app_safety.c \ Core/Src/uart_stdout.c \ Core/Src/stm32f1xx_it.c \ Core/Src/system_stm32f1xx.c \ @@ -244,10 +245,10 @@ build: all size: $(BUILD_DIR)/$(TARGET).elf $(SZ) $< -flash-stlink: $(BUILD_DIR)/$(TARGET).bin +flash: $(BUILD_DIR)/$(TARGET).bin st-flash write $< 0x8000000 -flash: $(BUILD_DIR)/$(TARGET).bin +flash-pico: $(BUILD_DIR)/$(TARGET).bin pico-openocd -f target/stm32f1x.cfg -c "program $< 0x08000000 verify reset exit" analyze: $(BUILD_DIR)/$(TARGET).elf