tdse-tf_3-02

Controlador PID para derretidor de miel con control local via botones y remoto via WiFi
Index Commits Files Refs Submodules README
commit 9fcef08dd8525c79f320d9509e9f1200a14debb0
parent f99407f923dfb59b92428da61df728733934cd61
Author: Martin Kloeckner <mjkloeckner@gmail.com>
Date:   Sun, 29 Mar 2026 01:54:26 -0300

Utilizar cola en lugar de FSM para comunicarse con sensor DS18B20

De esta forma es mas fácil interactuar con el sensor y el enfoque es más
parecido a lo realizado para el display con la interfaz i2c.

Diffstat:
Mfirmware/app/inc/ds18b20.h | 78++++--------------------------------------------------------------------------
Mfirmware/app/src/ds18b20.c | 430++++++++++++++++++++++++++++++++++++++++---------------------------------------
Mfirmware/app/src/task_temp_ctrl.c | 2+-
Mfirmware/app/src/task_temp_sensor.c | 26+++++++++++++++++++++-----
4 files changed, 244 insertions(+), 292 deletions(-)
diff --git a/firmware/app/inc/ds18b20.h b/firmware/app/inc/ds18b20.h
@@ -11,81 +11,11 @@
 extern "C" {
 #endif
 
-/* DS18B20 Non Blocking State Machine - Transition Table
- *
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * | Current state                   | [Guard]                             | Next state                      | Actions                           |
- * +=================================+=====================================+=================================+===================================+
- * | ST_READY                        | [g_DS18B20_tick == 0]               | ST_BUSY_SENDING_RESET           | Reset_DMA()                       |
- * |                                 |                                     |                                 | prev_state = ST_READY             |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * | ST_BUSY_SENDING_RESET           | [DMA_TX_done == true]               | ST_BUSY_SENDING_SKIP_ROM        | Write_DMA(SKIP_ROM_CMD)           |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [(DMA_TX_done == true)              | ST_BUSY_SENDING_CONV_T          | Write_DMA(CONV_T_CMD)             |
- * |                                 |   && (prev_state == ST_READY)]      |                                 |                                   |
- * | ST_BUSY_SENDING_SKIP_ROM        +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [(DMA_TX_done == true)              |                                 |                                   |
- * |                                 |   && (prev_state ==                 | ST_BUSY_SENDING_READ_SCRATCHPAD | Write_DMA(READ_SCRATCHPAD_CMD)    |
- * |                                 |         ST_BUSY_WAITING_CONV)]      |                                 |                                   |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * | ST_BUSY_SENDING_CONV_T          | [DMA_TX_done == true]               | ST_BUSY_WAITING_CONV            | tick = G_DS18B20_CONV_TIME_MS     |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [tick == 0]                         | ST_BUSY_SENDING_RESET           | Reset_DMA()                       |
- * |                                 |                                     |                                 | prev_state = ST_BUSY_WAITING_CONV |
- * | ST_BUSY_WAITING_CONV            +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 |                                     |                                 | tick--                            |
- * |                                 |                                     |                                 |                                   |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [DMA_TX_done == true]               | ST_BUSY_WAITING_LSB             | DS18B20_Read_DMA()                |
- * | ST_BUSY_SENDING_READ_SCRATCHPAD |                                     |                                 | DS18B20_Write_DMA(0xFF)           |
- * |                                 |                                     |                                 |                                   |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [DMA_RX_done == true]               | ST_BUSY_WAITING_MSB             | Temp_LSB = Get_RX_byte()          |
- * |                                 |                                     |                                 | DS18B20_Read_DMA()                |
- * |                                 |                                     |                                 | DS18B20_Write_DMA(0xFF)           |
- * | ST_BUSY_WAITING_LSB             +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [tick == 0]                         | ST_BUSY_WAITING_DMA             | prev_state = ST_BUSY_WAITING_LSB  |
- * |                                 |                                     |                                 | HAL_UART_AbortReceive(&huart1)    |
- * |                                 +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 |                                     | ST_BUSY_WAITING_LSB             | tick--                            |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [DMA_RX_done == true]               | ST_READY                        | Temp_MSB = Get_RX_byte()          |
- * |                                 |                                     |                                 | Temp = (Temp_MSB<<8) | Temp_LSB   |
- * |                                 |                                     |                                 | tick = G_TEMP_PERIOD_MS           |
- * | ST_BUSY_WAITING_MSB             +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 | [tick == 0]                         | ST_BUSY_WAITING_DMA             | prev_state = ST_BUSY_WAITING_MSB  |
- * |                                 |                                     |                                 | HAL_UART_AbortReceive(&huart1)    |
- * |                                 +-------------------------------------+---------------------------------+-----------------------------------+
- * |                                 |                                     | ST_BUSY_WAITING_MSB             | tick--                            |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- * | ST_BUSY_WAITING_DMA             | [(huart.State == HAL_DMA_READY) &&  | ST_DS18B20_READY                | tick = G_TEMP_PERIOD_MS           |
- * |                                 |  (huart.RxState == HAL_DMA_READY)]  |                                 |                                   |
- * +---------------------------------+-------------------------------------+---------------------------------+-----------------------------------+
- *
- *
- */
-
-#define DS18B20_SKIP_ROM_CMD                   0xCC
-#define DS18B20_CONVERT_T_CMD                  0x44
-#define DS18B20_READ_SCRATCHPAD_CMD            0xBE
-#define DS18B20_WRITE_SCRATCHPAD_CMD           0x4E
-#define DS18B20_WRITE_SCRATCHPAD_TO_EEPROM_CMD 0x48
-
-typedef enum {
-    ST_DS18B20_READY,
-    ST_DS18B20_BUSY_SENDING_RESET,
-    ST_DS18B20_BUSY_SENDING_SKIP_ROM,
-    ST_DS18B20_BUSY_SENDING_CONV_T,
-    ST_DS18B20_BUSY_SENDING_READ_SCRATCHPAD,
-    ST_DS18B20_BUSY_WAITING_CONV,
-    ST_DS18B20_BUSY_WAITING_LSB,
-    ST_DS18B20_BUSY_WAITING_MSB,
-    ST_DS18B20_BUSY_WAITING,
-    ST_DS18B20_BUSY_WAITING_DMA
-} ds18b20_st_t;
-
 void ds18b20_init(void);
-void ds18b20_update(void);
+void ds18b20_async_tick(void);
+void ds18b20_async_read_temp(void);
+bool ds18b20_async_temp_ready(void);
+int16_t ds18b20_async_get_temp(void);
 
 #ifdef __cplusplus
 }
diff --git a/firmware/app/src/ds18b20.c b/firmware/app/src/ds18b20.c
@@ -12,39 +12,78 @@
 #include "stm32f1xx_ll_usart.h"
 #include "logger.h"
 
-#define G_DS18B20_CONV_TIME_MS   100ul // ~188ms for 10 bit resolution
-#define G_TEMP_PERIOD_MS         1000ul
-#define G_DATA_BAUDRATE          96500
+#define DS18B20_SKIP_ROM_CMD                   0xCC
+#define DS18B20_CONVERT_T_CMD                  0x44
+#define DS18B20_READ_SCRATCHPAD_CMD            0xBE
+#define DS18B20_WRITE_SCRATCHPAD_CMD           0x4E
+#define DS18B20_WRITE_SCRATCHPAD_TO_EEPROM_CMD 0x48
+
+#define G_DS18B20_RESOLUTION_BITS 9
+#define G_DS18B20_CONV_TIME_MS    100ul // ~188ms for 9 bit resolution
+#define G_DS18B20_TICK_INI        0ul
+#define G_RESET_BAUDRATE          9600
+
+// TODO: Handle temp sensor not responding with 115200. Idea: Use first 115200
+//       until the sensor no longer responds, in thta case try with different
+//       speeds, such as 96500.
+#define G_DATA_BAUDRATE        96500
+
+#define G_DS18B20_ASYNC_QUEUE_LEN    256
+#define G_DS18B20_ASYNC_RESET_DEL_MS 100ul
+
+// Private data structures definition
+typedef enum {
+    DS18B20_QUEUE_BYTE_TX,
+    DS18B20_QUEUE_BYTE_RX,
+    DS18B20_QUEUE_READ_LSB,
+    DS18B20_QUEUE_READ_MSB,
+    DS18B20_QUEUE_SET_BAUD_SLOW,
+    DS18B20_QUEUE_SET_BAUD_FAST,
+    DS18B20_QUEUE_RESET,
+    DS18B20_QUEUE_DELAY,
+} ds18b20_data_type_e;
+
+typedef struct {
+    ds18b20_data_type_e type;
+    uint16_t data;
+} ds18b20_data_t;
+
+static struct {
+    uint8_t head;
+    uint8_t tail;
+    uint8_t count;
+    ds18b20_data_t queue[G_DS18B20_ASYNC_QUEUE_LEN];
+} ds18b20_async_queue;
 
 // Private global variables
-ds18b20_st_t g_ds18b20_state, g_ds18b20_prev_state;
 uint32_t g_ds18b20_tick;
-uint16_t g_ds18b20_temp;
-uint8_t temp_lsb, temp_msb;
+uint16_t g_ds18b20_temp, g_ds18b20_update_count;
+uint8_t g_temp_lsb, g_temp_msb;
 uint8_t g_ds18b20_tx_buffer[8], g_ds18b20_rx_buffer[8];
-uint8_t g_ds18b20_reset_data_tx, g_ds18b20_reset_data_rx;
 bool b_ds18b20_dma_tx_done, b_ds18b20_dma_rx_done;
-
-// Public global variables
-uint16_t g_ds18b20_update_count, g_ds18b20_dma_error_count;
+bool b_ds18b20_rx_data_processed, b_ds18b20_async_temp_ready;
 
 // Private functions declaration
+//// Blocking calls
 void ds18b20_write(uint8_t data);
 void ds18b20_read_temp(void);
 void ds18b20_set_resolution(uint8_t resolution);
-
-void ds18b20_async_write(uint8_t data);
-void ds18b20_async_read(void);
-void ds18b20_async_reset(void);
-
 uint8_t ds18b20_get_rx_byte(void);
+void ds18b20_byte_to_array_of_bytes(uint8_t byte, uint8_t *array);
+//// Asynchronous calls
+void ds18b20_dma_write(ds18b20_data_t data);
+void ds18b20_async_reset(void);
+void ds18b20_async_enqueue(ds18b20_data_t data);
+ds18b20_data_t ds18b20_async_dequeue(void);
+ds18b20_data_t ds18b20_async_queue_head(void);
+ds18b20_data_t ds18b20_async_queue_tail(void);
 
 uint8_t ds18b20_reset(void)
 {
     uint8_t data = 0xF0;
 
     __HAL_UART_DISABLE(&huart1);
-    LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), 9600);
+    LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), G_RESET_BAUDRATE);
     __HAL_UART_ENABLE(&huart1);
 
     HAL_UART_Transmit(&huart1, &data, 1, 100);
@@ -61,18 +100,6 @@ uint8_t ds18b20_reset(void)
     return 0;
 }
 
-void ds18b20_async_reset(void)
-{
-    __HAL_UART_DISABLE(&huart1);
-    LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), 9600);
-    __HAL_UART_ENABLE(&huart1);
-
-    b_ds18b20_dma_tx_done = b_ds18b20_dma_rx_done = false;
-    HAL_UARTEx_ReceiveToIdle_DMA(&huart1, &g_ds18b20_reset_data_rx, 1);
-    g_ds18b20_reset_data_tx = 0xF0;
-    HAL_UART_Transmit_DMA(&huart1, &g_ds18b20_reset_data_tx, 1);
-}
-
 void ds18b20_set_resolution(uint8_t resolution)
 {
     uint8_t config;
@@ -105,230 +132,207 @@ void ds18b20_init(void)
     {
         LOGGER_INFO("Temperature sensor initialized successfully");
     }
-    ds18b20_set_resolution(9);
-    g_ds18b20_state = g_ds18b20_prev_state = ST_DS18B20_READY;
-    g_ds18b20_tick = G_TEMP_PERIOD_MS;
+    ds18b20_set_resolution(G_DS18B20_RESOLUTION_BITS);
+
+    g_ds18b20_tick = G_DS18B20_TICK_INI;
     g_ds18b20_update_count = 0;
-    g_ds18b20_dma_error_count = 0;
-    temp_lsb = temp_msb = 0xFF;
+    g_temp_lsb = g_temp_msb = 0xFF;
+
+    b_ds18b20_dma_tx_done = true;
+    b_ds18b20_dma_rx_done = true;
+    b_ds18b20_rx_data_processed = true;
+    b_ds18b20_async_temp_ready = false;
+    ds18b20_async_queue.head = 0;
+    ds18b20_async_queue.tail = 0;
+    ds18b20_async_queue.count = 0;
 }
 
 void ds18b20_write(uint8_t data)
 {
     uint8_t buffer[8];
-
-    for (uint8_t i = 0; i < 8; ++i)
-    {
-        if (data & (1 << i))
-        {
-            buffer[i] = 0xFF;
-        }
-        else
-        {
-            buffer[i] = 0x00;
-        }
-    }
-
+    ds18b20_byte_to_array_of_bytes(data, buffer);
     HAL_UART_Transmit(&huart1, buffer, 8, 100);
 }
 
-void ds18b20_async_write(uint8_t data)
+void ds18b20_async_reset(void)
 {
-    for (uint8_t i = 0; i < 8; ++i)
+    ds18b20_async_enqueue((ds18b20_data_t){DS18B20_QUEUE_SET_BAUD_SLOW});
+    ds18b20_async_enqueue((ds18b20_data_t){DS18B20_QUEUE_RESET});
+    ds18b20_async_enqueue((ds18b20_data_t){DS18B20_QUEUE_SET_BAUD_FAST});
+}
+
+void ds18b20_dma_write(ds18b20_data_t data)
+{
+    switch (data.type)
     {
-        if (data & (1 << i))
-        {
-            g_ds18b20_tx_buffer[i] = 0xFF;
-        }
-        else
-        {
-            g_ds18b20_tx_buffer[i] = 0x00;
-        }
-    }
+        case DS18B20_QUEUE_BYTE_TX:
+            ds18b20_byte_to_array_of_bytes(data.data, g_ds18b20_tx_buffer);
+            b_ds18b20_dma_tx_done = false;
+            HAL_UART_Transmit_DMA(&huart1, g_ds18b20_tx_buffer, 8);
+        break;
+
+        case DS18B20_QUEUE_BYTE_RX:
+            memset(g_ds18b20_rx_buffer, 0, sizeof(g_ds18b20_rx_buffer));
+            b_ds18b20_dma_rx_done = false;
+            HAL_UARTEx_ReceiveToIdle_DMA(&huart1, g_ds18b20_rx_buffer, 8);
+        break;
+
+        case DS18B20_QUEUE_READ_LSB:
+        case DS18B20_QUEUE_READ_MSB:
+            b_ds18b20_dma_tx_done = false;
+            b_ds18b20_dma_rx_done = false;
+            b_ds18b20_rx_data_processed = false;
+            memset(g_ds18b20_rx_buffer, 0, sizeof(g_ds18b20_rx_buffer));
+            ds18b20_byte_to_array_of_bytes(0xFF, g_ds18b20_tx_buffer);
+
+            HAL_UARTEx_ReceiveToIdle_DMA(&huart1, g_ds18b20_rx_buffer, 8);
+            HAL_UART_Transmit_DMA(&huart1, g_ds18b20_tx_buffer, 8);
+        break;
+
+        case DS18B20_QUEUE_DELAY:
+            g_ds18b20_tick = data.data;
+        break;
+
+        case DS18B20_QUEUE_SET_BAUD_SLOW:
+            __HAL_UART_DISABLE(&huart1);
+            LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), G_RESET_BAUDRATE);
+            __HAL_UART_ENABLE(&huart1);
+        break;
+
+        case DS18B20_QUEUE_SET_BAUD_FAST:
+            __HAL_UART_DISABLE(&huart1);
+            LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), G_DATA_BAUDRATE);
+            __HAL_UART_ENABLE(&huart1);
+        break;
+
+        case DS18B20_QUEUE_RESET:
+            b_ds18b20_dma_tx_done = false;
+            b_ds18b20_dma_rx_done = true;
+            b_ds18b20_rx_data_processed = false;
+            memset(g_ds18b20_rx_buffer, 0, sizeof(g_ds18b20_rx_buffer));
+            g_ds18b20_tx_buffer[0] = 0xF0;
+            HAL_UARTEx_ReceiveToIdle_DMA(&huart1, g_ds18b20_rx_buffer, 1);
+            HAL_UART_Transmit_DMA(&huart1, g_ds18b20_tx_buffer, 1);
+        break;
 
-    b_ds18b20_dma_tx_done = false;
-    HAL_UART_Transmit_DMA(&huart1, g_ds18b20_tx_buffer, 8);
+        default: break;
+    }
 }
 
-void ds18b20_async_read(void)
+void ds18b20_byte_to_array_of_bytes(uint8_t byte, uint8_t *array)
 {
-    memset(g_ds18b20_rx_buffer, 0, sizeof(g_ds18b20_rx_buffer));
-    b_ds18b20_dma_rx_done = false;
-    HAL_UARTEx_ReceiveToIdle_DMA(&huart1, g_ds18b20_rx_buffer, 8);
+    for (uint8_t i = 0; i < 8; ++i)
+    {
+        array[i] = ((byte & (1 << i)) ? 0xFF : 0x00);
+    }
 }
 
 uint8_t ds18b20_get_rx_byte(void)
 {
-    // Process received byte
     uint8_t received_value = 0;
+
     for (uint8_t i = 0; i < 8; ++i)
     {
-        if (g_ds18b20_rx_buffer[i] == 0xFF)
-        {
-            received_value |= (1 << i);
-        }
+        received_value |= (((g_ds18b20_rx_buffer[i] == 0xFF) ? 1 : 0) << i);
     }
+
     return received_value;
 }
 
-void ds18b20_update(void)
+void ds18b20_async_tick(void)
 {
-    switch (g_ds18b20_state)
+    if (!b_ds18b20_rx_data_processed)
     {
-        case ST_DS18B20_READY:
-            if (0 == g_ds18b20_tick)
-            {
-                g_ds18b20_prev_state = g_ds18b20_state;
-                g_ds18b20_state = ST_DS18B20_BUSY_SENDING_RESET;
-                ds18b20_async_reset();
-            }
-            else
-            {
-                g_ds18b20_tick--;
-            }
+        b_ds18b20_rx_data_processed = true;
+        switch(ds18b20_async_queue_tail().type)
+        {
+            case DS18B20_QUEUE_READ_LSB:
+                g_temp_lsb = ds18b20_get_rx_byte();
             break;
-        case ST_DS18B20_BUSY_SENDING_RESET:
-            // TODO: Check received value (presence byte)
-            if (true == b_ds18b20_dma_tx_done)
-            {
-                __HAL_UART_DISABLE(&huart1);
-                LL_USART_SetBaudRate(USART1, HAL_RCC_GetPCLK2Freq(), G_DATA_BAUDRATE);
-                __HAL_UART_ENABLE(&huart1);
-                g_ds18b20_state = ST_DS18B20_BUSY_SENDING_SKIP_ROM;
-                ds18b20_async_write(DS18B20_SKIP_ROM_CMD);
-            }
+            case DS18B20_QUEUE_READ_MSB:
+                g_temp_msb = ds18b20_get_rx_byte();
+                g_ds18b20_temp = ((g_temp_msb << 8) | g_temp_lsb) / 16;
+                b_ds18b20_async_temp_ready = true;
+                g_ds18b20_update_count++;
             break;
-        case ST_DS18B20_BUSY_SENDING_SKIP_ROM:
-            if (true == b_ds18b20_dma_tx_done)
-            {
-                switch (g_ds18b20_prev_state)
-                {
-                    case ST_DS18B20_READY:
-                        g_ds18b20_prev_state = g_ds18b20_state;
-                        g_ds18b20_state = ST_DS18B20_BUSY_SENDING_CONV_T;
-                        ds18b20_async_write(DS18B20_CONVERT_T_CMD);
-                    break;
-                    case ST_DS18B20_BUSY_WAITING_CONV:
-                        g_ds18b20_prev_state = g_ds18b20_state;
-                        g_ds18b20_state = ST_DS18B20_BUSY_SENDING_READ_SCRATCHPAD;
-                        ds18b20_async_write(DS18B20_READ_SCRATCHPAD_CMD);
-                    break;
-                    default: 
-                        g_ds18b20_state = ST_DS18B20_READY;
-                    break;
-                }
-            }
+            case DS18B20_QUEUE_RESET:
+                // TODO: Read presence byte
             break;
-        case ST_DS18B20_BUSY_SENDING_CONV_T:
-            if (true == b_ds18b20_dma_tx_done)
-            {
-                g_ds18b20_state = ST_DS18B20_BUSY_WAITING_CONV;
-                g_ds18b20_tick = G_DS18B20_CONV_TIME_MS;
-            }
-            break;
-        case ST_DS18B20_BUSY_WAITING_CONV:
-            if (0 == g_ds18b20_tick)
-            {
-                // Start reading sensor data
-                g_ds18b20_prev_state = g_ds18b20_state;
-                g_ds18b20_state = ST_DS18B20_BUSY_SENDING_RESET;
-                ds18b20_async_reset();
-            }
-            else
+            default: break;
+        }
+    }
+    else
+    {
+        if (0 == g_ds18b20_tick)
+        {
+            if ((0 != ds18b20_async_queue.count)
+                    && b_ds18b20_dma_tx_done
+                    && b_ds18b20_dma_rx_done)
             {
-                g_ds18b20_tick--;
+                ds18b20_dma_write(ds18b20_async_dequeue());
             }
-            break;
+        }
+        else
+        {
+            g_ds18b20_tick--;
+        }
+    }
+}
 
-        case ST_DS18B20_BUSY_SENDING_READ_SCRATCHPAD:
-            if (true == b_ds18b20_dma_tx_done)
-            {
-                // Read sensor LSB of data
-                ds18b20_async_read();
-                ds18b20_async_write(0xFF);
-                g_ds18b20_state = ST_DS18B20_BUSY_WAITING_LSB;
-            }
-            break;
+void ds18b20_async_read_temp(void)
+{
+    b_ds18b20_async_temp_ready = false;
+
+    ds18b20_async_reset();
+    ds18b20_async_enqueue((ds18b20_data_t){
+            DS18B20_QUEUE_BYTE_TX, DS18B20_SKIP_ROM_CMD});
+    ds18b20_async_enqueue((ds18b20_data_t){
+            DS18B20_QUEUE_BYTE_TX, DS18B20_CONVERT_T_CMD});
+    ds18b20_async_enqueue((ds18b20_data_t){
+            DS18B20_QUEUE_DELAY, G_DS18B20_CONV_TIME_MS});
+
+    ds18b20_async_reset();
+    ds18b20_async_enqueue((ds18b20_data_t){
+            DS18B20_QUEUE_BYTE_TX, DS18B20_SKIP_ROM_CMD});
+    ds18b20_async_enqueue((ds18b20_data_t){
+            DS18B20_QUEUE_BYTE_TX, DS18B20_READ_SCRATCHPAD_CMD});
+    ds18b20_async_enqueue((ds18b20_data_t){DS18B20_QUEUE_READ_LSB});
+    ds18b20_async_enqueue((ds18b20_data_t){DS18B20_QUEUE_READ_MSB});
+}
 
-        case ST_DS18B20_BUSY_WAITING_LSB:
-            if (true == b_ds18b20_dma_rx_done)
-            {
-                temp_lsb = ds18b20_get_rx_byte();
-                g_ds18b20_state = ST_DS18B20_BUSY_WAITING_MSB;
-                ds18b20_async_read();
-                ds18b20_async_write(0xFF);
-            }
-            else if (0 == g_ds18b20_tick)
-            {
-                // Try again readying scratchpad
-                g_ds18b20_dma_error_count++;
-
-                HAL_UART_AbortReceive(&huart1);
-                __HAL_UART_CLEAR_OREFLAG(&huart1);
-                __HAL_UART_CLEAR_FEFLAG(&huart1);
-                __HAL_UART_CLEAR_NEFLAG(&huart1);
-                __HAL_UART_CLEAR_PEFLAG(&huart1);
-                __HAL_UART_CLEAR_IDLEFLAG(&huart1);
-
-                g_ds18b20_prev_state = g_ds18b20_state;
-                g_ds18b20_state = ST_DS18B20_BUSY_WAITING_DMA;
-            }
-            else
-            {
-                g_ds18b20_tick--;
-            }
-            break;
+bool ds18b20_async_temp_ready(void)
+{
+    return b_ds18b20_async_temp_ready;
+}
 
-        case ST_DS18B20_BUSY_WAITING_MSB:
-            if (true == b_ds18b20_dma_rx_done)
-            {
-                temp_msb = ds18b20_get_rx_byte();
-                g_ds18b20_temp = ((temp_msb << 8) | temp_lsb) / 16;
-                g_ds18b20_state = ST_DS18B20_READY;
-                g_ds18b20_tick = G_TEMP_PERIOD_MS;
-                g_ds18b20_update_count++;
-            }
-            else if (0 == g_ds18b20_tick)
-            {
-                // Try again readying scratchpad
-                g_ds18b20_dma_error_count++;
-
-                HAL_UART_AbortReceive(&huart1);
-                __HAL_UART_CLEAR_OREFLAG(&huart1);
-                __HAL_UART_CLEAR_FEFLAG(&huart1);
-                __HAL_UART_CLEAR_NEFLAG(&huart1);
-                __HAL_UART_CLEAR_PEFLAG(&huart1);
-                __HAL_UART_CLEAR_IDLEFLAG(&huart1);
-
-                g_ds18b20_prev_state = g_ds18b20_state;
-                g_ds18b20_state = ST_DS18B20_BUSY_WAITING_DMA;
-            }
-            else
-            {
-                g_ds18b20_tick--;
-            }
-            break;
+int16_t ds18b20_async_get_temp(void)
+{
+    return g_ds18b20_temp;
+}
 
-        case ST_DS18B20_BUSY_WAITING_DMA:
-            if ((huart1.hdmarx->State == HAL_DMA_STATE_READY) &&
-                    (huart1.RxState == HAL_UART_STATE_READY))
-            {
-                switch (g_ds18b20_prev_state)
-                {
-                    case ST_DS18B20_BUSY_WAITING_LSB:
-                    case ST_DS18B20_BUSY_WAITING_MSB:
-                        g_ds18b20_state = ST_DS18B20_READY;
-                        g_ds18b20_tick = G_TEMP_PERIOD_MS;
-                        break;
-                    default: break;
-                }
-            }
-            break;
+void ds18b20_async_enqueue(ds18b20_data_t data)
+{
+    ds18b20_async_queue.count++;
+    ds18b20_async_queue.queue[ds18b20_async_queue.head++] = data;
+}
 
-        default: break;
-    }
+ds18b20_data_t ds18b20_async_dequeue(void)
+{
+    ds18b20_async_queue.count--;
+    return ds18b20_async_queue.queue[ds18b20_async_queue.tail++];
 }
 
+ds18b20_data_t ds18b20_async_queue_tail(void)
+{
+    return ds18b20_async_queue.queue[(ds18b20_async_queue.tail) - 1];
+}
+
+ds18b20_data_t ds18b20_async_queue_head(void)
+{
+    return ds18b20_async_queue.queue[ds18b20_async_queue.head];
+}
+
+// Callbacks definition
 void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart)
 {
     if (huart->Instance == USART1)
@@ -360,3 +364,5 @@ void HAL_UART_ErrorCallback(UART_HandleTypeDef *huart)
         ;
     }
 }
+
+
diff --git a/firmware/app/src/task_temp_ctrl.c b/firmware/app/src/task_temp_ctrl.c
@@ -29,7 +29,7 @@ void task_temp_ctrl_init(void *parameters)
     g_task_temp_ctrl_tick = G_TASK_CTRL_TICK_CNT_INI;
 
     shared_data_type *p_shared_data = (shared_data_type *)parameters;
-    p_shared_data->temp_controller_pwm_dc = 10;
+    p_shared_data->temp_controller_pwm_dc = 0;
     TIM1->CCR1 = p_shared_data->temp_controller_pwm_dc;
     HAL_TIM_PWM_Start(&htim1, TIM_CHANNEL_1);
 
diff --git a/firmware/app/src/task_temp_sensor.c b/firmware/app/src/task_temp_sensor.c
@@ -18,7 +18,8 @@
 
 #include "ds18b20.h"
 
-#define G_TASK_SEN_TICK_CNT_INI  0ul
+#define G_TASK_TEMP_SEN_TICK_INI            0ul
+#define G_TASK_TEMP_SEN_TEMP_UPDATE_RATE_MS 1000ul
 
 uint32_t g_task_temp_sensor_tick;
 
@@ -32,7 +33,7 @@ void task_temp_sensor_init(void *parameters)
 
     LOGGER_INFO("Initializing `task_temp_sensor`...");
 
-    g_task_temp_sensor_tick = G_TASK_SEN_TICK_CNT_INI;
+    g_task_temp_sensor_tick = G_TASK_TEMP_SEN_TICK_INI;
     ds18b20_init();
 
     LOGGER_INFO("Done initializing `task_temp_sensor`");
@@ -44,7 +45,7 @@ void task_temp_sensor_update(void *parameters)
     shared_data_type *p_shared_data = (shared_data_type *)parameters;
 
     __asm("CPSID i");
-    if (G_TASK_SEN_TICK_CNT_INI < g_task_temp_sensor_tick_cnt)
+    if (G_TASK_TEMP_SEN_TICK_INI < g_task_temp_sensor_tick_cnt)
     {
         g_task_temp_sensor_tick_cnt--;
         b_time_update_required = true;
@@ -54,7 +55,7 @@ void task_temp_sensor_update(void *parameters)
     while (b_time_update_required)
     {
         __asm("CPSID i");
-        if (G_TASK_SEN_TICK_CNT_INI < g_task_temp_sensor_tick_cnt)
+        if (G_TASK_TEMP_SEN_TICK_INI < g_task_temp_sensor_tick_cnt)
         {
             g_task_temp_sensor_tick_cnt--;
             b_time_update_required = true;
@@ -65,6 +66,21 @@ void task_temp_sensor_update(void *parameters)
         }
         __asm("CPSIE i");
 
-        ds18b20_update();
+        ds18b20_async_tick();
+
+        if (0 == g_task_temp_sensor_tick)
+        {
+            g_task_temp_sensor_tick = G_TASK_TEMP_SEN_TEMP_UPDATE_RATE_MS;
+            ds18b20_async_read_temp();
+        }
+        else
+        {
+            g_task_temp_sensor_tick--;
+        }
+
+        if (ds18b20_async_temp_ready())
+        {
+            p_shared_data->temp_sensor = ds18b20_async_get_temp();
+        }
     }
 }