Перейти к содержанию
    

Концепция сброса сторожевого таймера во FreeRTOS

38 minutes ago, simark1979 said:

Если честно, я не в теме, что такое TCB,

https://doc.micrium.com/display/kernel304/Task+Control+Blocks+TCBs

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Сейчас вот на что нарвался https://www.freertos.org/xEventGroupWaitBits.html

Может можно будет и прикрутить.
Кто-нибудь сталкивался с этими функциями?

Изменено пользователем simark1979

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

После открытия для себя функций по работе с группами бит, вот что придумалось:
В потоке вызываем xEventGroupWaitBits() с бесконечным ожиданием.
Чтобы проскочить эту функцию, нужно выставить все биты в группе.
Каждый контролируемый поток с помощью xEventGroupSetBits должен выставить свой уникальный бит в группе.
Перед возвратом из xEventGroupWaitBits(), все биты в группе сбросятся автоматом.

Таким образом нужно, чтобы все функции: (watchdog_taskAlive__ui(), watchdog_taskAlive__ph_sensor_reader(), watchdog_taskAlive__rx_sensor_reader())
были вызваны хотя бы один раз. Чем чаще будут вызовы этих функций, тем сильнее можно сократить реакцию на зависание.

В зависимости от конфига FreeRTOS, в одну группу можно запихать до 32-х бит. по умолчанию CubeMx так и делает, если этого недостаточно, делайте иерархию из групп.


Код не оптимизирован для наглядности)
#include "watchdog.h"
#include "stm32f2xx_hal.h"
#include "stm32f2xx.h"
#include "stm32f2xx_it.h"
#include "cmsis_os.h"
#include "string.h"

#define BIT_0    ( 1 << 0 )
#define BIT_1    ( 1 << 1 )
#define BIT_2    ( 1 << 2 )

EventGroupHandle_t xTasksWatchdogEventGroup;

void task_Watchdog_control(void const * argument)

  MX_IWDG_Init();
  xTasksWatchdogEventGroup = xEventGroupCreate();

  for(;;)
  {
    xEventGroupWaitBits(
                        xTasksWatchdogEventGroup,   /* The event group being tested. */
                        BIT_0 | BIT_1 | BIT_2,      /* Здесь перечисляем какие биты ждем */
                        pdTRUE,                           /* Указываем, что при выходе из функции, биты нужно сбросить */
                        pdTRUE,                           /* Указываем, что возврат из функции произойдет, только после выставления всех битов*/
                        portMAX_DELAY );         /* Выставление битов ждем бесконечно долго */

    HAL_IWDG_Refresh(&hiwdg);

  }
}

void watchdog_taskAlive__ui() {  xEventGroupSetBits(xTasksWatchdogEventGroup, BIT_0);}

void watchdog_taskAlive__ph_sensor_reader(){  xEventGroupSetBits(xTasksWatchdogEventGroup, BIT_1);}

void watchdog_taskAlive__rx_sensor_reader(){  xEventGroupSetBits(xTasksWatchdogEventGroup, BIT_2);}

 

Изменено пользователем simark1979

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А у меня такая концепция:

Задача, отвечающая за какой-то локальный процесс (например, сложный обмен данными с неизвестным исходом) создаётся и удаляется по мере необходимости. Т.е. новый обмен запускается гарантированно заново.

Над всеми задачами есть одна задача-арбитр : она при помощи очередей раздаёт команды что-кому делать и принимает результаты. Т.е. это верхний уровень логики приложения.
Этот верхний уровень работает так, что если какого-то ответа нет или какая-то очередь занята- зависает. И вот в ней WDT.
Т.е. зависание чего-то локального => зависание верхнего уровня = > перезагрузка.
Ну и вокруг этого  рюшечки вроде перезапуска / отмены зависшей локальной задачи, и т.п.

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

5 hours ago, MiklPolikov said:

создаётся и удаляется по мере необходимости.

А как  решаете проблемы фрагментации памяти динамической?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

3 hours ago, haker_fox said:

А как  решаете проблемы фрагментации памяти динамической?

либо у всех задач одинаковый размер стека, либо размер памяти вдвое больше чем займут задачи.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Есть и другой способ - при создании самостоятельно выделять области для стека каждой задачи (не обязательно одинакового размера) и при ее перезапуске использовать те же самые области. Практически во всех RTOS есть такая возможность.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы можете написать сейчас и зарегистрироваться позже. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...