Библиотека сайта rus-linux.net
ОС реального времени FreeRTOS
Глава 3 из книги "Архитектура приложений с открытым исходным кодом", том 2.
Оригинал: FreeRTOS
Автор: Christopher Svec
Перевод: Н.Ромоданов
3.2. Обзор архитектуры
Система FreeRTOS является относительно небольшим приложением. Минимальный вариант ядра системы FreeRTOS состоит всего лишь из трех файлов исходного кода (.c) и горстка файлов заголовков, общий размер которых составляет чуть менее 9000 строк кода, включая комментарии и пустые строки. Размер типичного образа системы в исполняемом коде меньше 10 КБ.
Код FreeRTOS подразделяется на три основные части: выполнение задач, коммуникация и интерфейс с аппаратным обеспечением.
- Задачи: Почти половина кода ядра FreeRTOS связана с с центральной проблемой, решаемой во многих операционных системах: управление задачами. Задачей является определяемая пользователем функция на языке C с заданным приоритетом. В
tasks.c
иtask.h
делается вся тяжелая работа по созданию, планированию и обслуживанию задач. - Коммуникации: Задачи хороши, но задачи, которые могут общаться друг с другом, еще лучше! Это подводит нас ко второй части работ, выполняемых FreeRTOS: коммуникации. Около 40% кода ядра системы FreeRTOS связано с коммуникациями. Обработка коммуникаций в системе FreeRTOS осуществляется в файлах
queue.c
иqueue.h
. Задачи и прерывания используют очереди для передачи данных друг другу, а для того, чтобы сигнализировать об использовании критических ресурсов, применяются семафоры (semaphore) и и мютексы (mutexe). - Подключение к оборудованию: Около 9000 строк кода, которые составляют базу системы FreeRTOS, являются аппаратно-независимыми; один и тот же код выполняется независимо от того, работает ли система на скромной процессоре 8051 или на новейшем сияющим ядре ARM. Около 6% код ядра системы FreeRTOS представляют собой прослойку между аппаратно-независимым ядром системы FreeRTOS и аппаратно-зависимым кодом. Мы обсудим аппаратно-зависимый кода в следующем разделе.
Об аппаратном обеспечении
Аппаратно-независимый слой системы FreeRTOS находится поверх аппаратно-зависимого слоя. В этом аппаратно-зависимом слое известно, как взаимодействовать с архитектурой, построенной на любом чипе, который вы выберете. На рис.3.1 показаны слои системы FreeRTOS.
Рис.3.1: Слои программного обеспечения системы FreeRTOS
Система FreeRTOS поставляемый со всем аппаратно-независимым, а также с аппаратно-зависимым кодом, который вы должны получить для того, чтобы настроить и запустить систему. Поддерживается большое количество компиляторов (CodeWarrior, GCC, IAR и т.д.), а также большое количество архитектур процессоров (ARM7, ARM Cortex-M3, различные PIC, Silicon Labs 8051, x86 и т.д.). Список поддерживаемых архитектур и компиляторов смотрите на сайте системы FreeRTOS.
Дизайн системы FreeRTOS позволяет ее легко настраивать в широких пределах. Система FreeRTOS может собрана как для одного процессора, для выполнения только основных функций и поддержки только нескольких задач, либо она может быть собрана для работы на многоядерном железе с TCP/IP, файловой системой и USB.
Параметры конфигурации выбираются в файле с помощью задания различных значений #defines
. В этом файле можно выбрать тактовую частоту, размер кучи, мютексы и подмножество API, а также многие другие параметры. Ниже приведено несколько примеров, в которых устанавливается максимальное количество уровней приоритетов задач, частота процессора, тактовая частота системы, минимальный размер стека и общий размер кучи:
#define configMAX_PRIORITIES ( ( unsigned portBASE_TYPE ) 5 ) #define configCPU_CLOCK_HZ ( 12000000UL ) #define configTICK_RATE_HZ ( ( portTickType ) 1000 ) #define configMINIMAL_STACK_SIZE ( ( unsigned short ) 100 ) #define configTOTAL_HEAP_SIZE ( ( size_t ) ( 4 * 1024 ) )
Аппаратно-зависимую код для каждого инструментального набора компиляции и для каждой архитектуры процессора располагается в отдельных файлах. Например, если вы работаете с компилятором IAR на чипе ARM Cortex-M3, то аппаратно-зависимый код будет находиться в каталоге FreeRTOS/Source/portable/IAR/ARM_CM3
/. В файле portmacro.h
объявляются все аппаратно-зависимые функции, а в файлах port.c
и portasm.s
находится весь фактически используемый аппаратно-зависимый код. Во время компиляции аппаратно-независимые заголовки #include
файла portable.h
заменяются файлом portmacro.h
. Система FreeRTOS вызывает аппаратно-зависимые функции с помощью функций #define
, объявленных в файле portmacro.h
.
Давайте посмотрим на пример того, как система FreeRTOS вызывает аппаратно-зависимую функцию. Для того, чтобы войти в критическую секцию кода для предотвращения вытеснения, часто требуется аппаратно-независимый файл tasks.c
. В различных архитектурах вход в критическую секцию происходит по-разному, и, желательно, чтобы аппаратно-независимый файл tasks.c
не касался деталей, связанных с аппаратной зависимостью. Поэтому tasks.c
вызывает глобальный макрос portENTER_CRITICAL()
, радуясь тому, что не требуется знать как и что на самом деле работает. Предположим, что мы используем компилятор IAR на чипе ARM Cortex-M3, система FreeRTOS будет собираться с заголовками FreeRTOS/Source/portable/IAR/ARM_CM3/portmacro.h
, в который макрос portENTER_CRITICAL()
определяется следующим образом:
#define portENTER_CRITICAL() vPortEnterCritical()
На самом деле vPortEnterCritical()
определяется в файле FreeRTOS/Source/portable/IAR/ARM_CM3/port.c
. Файл port.c
является аппаратно-зависимым и содержит код, который понятен компилятору IAR и чипу Cortex-M3. vPortEnterCritical()
выполняет переход в критическую секцию, используя знания, касающиеся конкретного оборудования, и возвращает управление аппаратно-независимому файлу tasks.c
.
В файле portmacro.h
также определяются базовые типы данных для используемой архитектуры. Ниже приведен пример типов данных для базовых целочисленных переменных, указателей и данные тактовой частоты системы для компилятора IAR на чипе ARM Cortex-M3:
#define portBASE_TYPE long // Тип базовой целочисленной переменной #define portSTACK_TYPE unsigned long // Указатели на позиции в памяти typedef unsigned portLONG portTickType; // Тип тактовой частоты системы
Такой метод использования типов данных и функций через тонкие слои определений #defines
может показаться несколько сложным, но он позволяет перекомпилировать систему FreeRTOS для архитектуры с совершенно другой системой, изменив только аппаратно-зависимые файлы. И если вы хотите запустить систему FreeRTOS на архитектуре, которая в настоящее время не поддерживается, вам потребуется реализовать только аппаратно-зависимую функциональность, которая значительно меньше, чем аппаратно-независимая часть системы FreeRTOS.
Как мы уже видели, система FreeRTOS реализует аппаратно-зависимую функциональность с помощью макросов #define
препроцессора языка C. В системе FreeRTOS определения #define
также используются большей части аппаратно-независимого кода. Для невстраиваемых приложений такое частое использование определений #define
является кардинальным недостатком, но во многих небольших встроенных системах накладные расходы на вызов функции не дают преимуществ в сравнении с использованием «реальных» функций.
Продолжение статьи: Планирование задач: Краткий обзор