FreeRTOS. Сигналы.

Сигнал (в теории информации и связи) — носитель информации, используемый для передачи сообщений в системе связи. Сигнал может генерироваться, но его приём не обязателен, в отличие от сообщения, которое рассчитано на принятие принимающей стороной, иначе оно не является сообщением. Сигналом может быть любой физический процесс, параметры которого изменяются (или находятся) в соответствии с передаваемым сообщением. Фактически, сигнал — это асинхронное уведомление процесса о каком-либо событии. Когда сигнал послан процессу, операционная система прерывает выполнение процесса. Если процесс установил собственный обработчик сигнала, операционная система запускает этот обработчик, передав ему информацию о сигнале. Если процесс не установил обработчик, то выполняется обработчик по умолчанию.

Описание
Сигналы используются для запуска состояния выполнения между потоками. Функции управления сигнал в CMSIS-RTOS позволяет вам управлять или ждать сигнальных флагов. Каждый поток имеет до 31 назначенных сигнальных флагов. Максимальное количество сигнальных флагов определено в файле cmsis_os.h (#define) osFeature_Signals.

Поток
может ждать сигнала, который должен быть установлен (с использованием osSignalWait). Используя эту функцию, он переходит в состояние ожидания. Сигналы параметров osSignalWait определяет сигналы, которые необходимы, чтобы перевести поток обратно в состояние готовности. Так же, можно установить один или более флагов в любом другом потоке данных (с использованием osSignalSet). Можно очистить свои собственные сигналы или сигналы других потоков (с использованием osSignalClear).

Когда поток просыпается и возобновляет выполнение, его сигнал-флаги автоматически удаляются.
Работа с сигналами

Вот простой пример, который показывает, как два потока могут общаться друг с другом, используя сигналы:

Пример cвязи события простого сигнала
Следующие шаги необходимы чтобы использовать сигналы. Мы имеем поток 1 (tid_thread1), в нем ожидаем прихода сигнала,  вызываем функцию ожидания osSignalWait (0x0001, osWaitForever), ждем сигнала 0x0001. В другом потоке, поток 2, который предполагается, разбудить ожидание потока с помощью функции osSignalSet (tid_thread1, 0x0001), тем самым установив сигнал 0x0001 для потока 1 (tid_thread1).  После действия повторяются циклически, для тайм аута используем функцию osDelay (1000), ждать в течение 1 секунды.

Наш пример создает потоки, которые вызывают osSignalWait (поток ожидания сигнала), ждем установления бит 1, а затем бит 2 и переключаем состояние светодиода. SysTick_Handler вызывает функцию «Toggle_Leds». Toggle_Leds вызывает osSignalSet, чтобы послать сигнал = Бит 1 для потока 2, если статический счетчик > 400 и < 1000 и вызывает osSignalSet отправляя сигнал = Бит 1 | бит 2 для потока 2, если статический счетчик> = 1000. В результате поведение характеризуется следующим образом, светодиод LED переключаем каждые 800 мс.

Необходимо соблюдать осторожность при использовании HAL_Delay (), эта функция обеспечивает точное задержку (в миллисекундах) основная переменная увеличивается на единицу в SysTick ISR. Это означает, что если HAL_Delay () вызывается из периферийного процесса ISR, то прерывание SysTick должны иметь более высокий приоритет (численно меньше) чем окружные прерывания. В противном случае процесс ISR вызывающий будет заблокирован.

Чтобы изменить приоритет прерывания SysTick вы должны использовать функцию HAL_NVIC_SetPriority ().

Старт ARM. RTOS часть 1-ая. STM32F4 и SAM3N.
Старт ARM. RTOS часть 2-ая.
Старт ARM. RTOS часть 3-ая. Очереди.
Старт ARM. RTOS часть 4-ая. Семафоры.
Старт ARM. RTOS часть 5-ая. Мьютексы.
Старт ARM. RTOS часть 6-ая. Сопрограмма.
Старт ARM. RTOS часть 7-ая. Программный таймер.
Старт ARM. RTOS часть 8-ая. Программная очередь почты (mail queue).