ЖУРНАЛ СТА 2/1997

а)время от возникновения запроса на прерывание до передачи управления по вектору прерывания; б)или включая время сохранения кон- текста текущей задачи и передачи уп- равления подпрограмме обработки прерывания; в)или дополнительно к этому еще и время до завершения подпрограммы обработки прерывания и передачи сообщения связанной с прерывани- ем задаче; г) или дополнительно к этому время до момента, когда эта задача наконец получит управление (в предположе- нии, что она является наиболее при- оритетной) и начнет реальную об- работку события. Безотносительно к тому, какой ва- риант рассматривается, необходимо помнить, что 1)если наряду с разработанными вами программами используется програм- мное обеспечение третьих фирм, вы не застрахованы от того, что там не встретятся участки кода, где преры- вания запрещены; 2)практически любая ОС РВ имеет в своих недрах участки такого кода. Нам остается только надеяться, что разработчики ОС старались делать их как можно меньше; 3)всё ядро ОС РВ или его участки мо- гут быть «невытесняемыми»; 4)интеллектуальные контроллеры ввода/вывода типа SCSI могут ини- циировать в системе различные служебные операции, которые спо- собны отразиться на ее характерис- тиках; 5)многое зависит от применяемой системы кэширования. Поэтому, если ваше событие про- изошло в «неподходящее» время, ре- альные показатели быстродействия могут сильно отличаться от реклами- руемых. Перефразируя классика, самое вре- мя воскликнуть: «Тестировать, тести- ровать и еще раз тестировать!!!» ЗАКЛЮЧЕНИЕ Хотя, как мы увидели, ОС РВ пре- доставляют много полезных и удоб- ных средств для написания программ, основной груз ответственности лежит на плечах рядового труженикапро- граммиста. Ведь стоит ему перемес- тить переменную из категории ло- кальных в категорию глобальных и за- быть надлежащим образом оформить критические секции, как станут падать космические корабли, взрываться неф- теперерабатывающие заводы, исто- чать радиоактивность атомные стан- ции. Так воспоем гимн этому великому труженику. Крепче держать знамя со- циалистического соревнования за по- беду над инверсией приоритетов. ● С. А. Сорокин — Генеральный директор фирмы ProSoft 117313 Москва, а/я 81 Телефон: (095) 234-0636 Факс: (095) 234-0640 E-mail: root@prosoftmpc.msk.su ОБЗОР Программное обеспечение 29 2/97 МОЖНО ЛИ ОБОЙТИСЬ БЕЗ ОС РВ? Как любую вычислительную систему можно создать только из элементов 2И-НЕ, так и все, что может делать ОС РВ, реализуемо и без нее. Тем не менее, давайте все-таки попробуем разобраться, когда ОС РВ реально нужна, а когда нет. Предположим, нам надо не реже 10 раз в секунду опросить три переклю- чателя и в зависимости от их положения включить или выключить соответствую- щий насос. Программа может выглядеть следующим образом: void main (void) { int i; for (;;) { for (i=0;i<3;i++) { if (switch_was_changed(i)) change_Pump(i); } } } Заметьте, что никаких проверок по времени не производится, так как даже самые медленные процессоры могут сканировать переключатели чаще 10 раз в секунду. Программа адекватна поставленной задаче. Если требуется опрашивать переключатели ровно 10 раз в секунду, про- грамма может быть изменена: for (;;) { if (100msec_passed) { for (i=0;i<3;i++) { if (switch_was_changed(i) change_Pump(i); } 100msec_passed=0; } } Глобальная переменная 100msec_passed устанавливается в «1» каждые 100 мс с помощью подпрограммы обработки прерываний от таймера. Теперь допустим, что нам дополнительно нужно каждые 200 мс измерять давление и открывать вентиль, если давление больше 20 атм. Если при открытом вентиле давление падает ниже 15 атм, вентиль необходимо закрыть. Для выполнения этой задачи в тело цикла может быть добавлен следующий фрагмент: if (200msec_passed) { switch (valve_status) { case CLOSED: if (pressure_value()>20){ open_valve(); valve_status=OPEN; } case OPEN: if (pressure_value()<15){ close_valve(); valve_status=CLOSED; } } 200msec_passed=0; } Глобальная переменная 200msec_passed устанавливается в 1 каждые 200 мс. Так как тело цикла for (;;) стало большим, удобно вынести функции в отдельные подпрограммы и переписать основную программу следующим образом: for (;;) { process_pump_switches(); process_pressure_regulation(); } По мере того как добавляются новые «задачи», их можно оформлять от- дельными подпрограммами и включать соответствующие вызовы в тело главной программы. Однако по мере добавления новых функций время выполнения основного цикла увеличивается, в результате чего может на- ступить момент, когда требование о сканировании переключателей 10 раз в секунду перестанет выполняться. Давайте еще немного усложним задачу. Пусть система должна отобра- жать тренды на основе пакетов данных, получаемых через быстродейст- вующий последовательный порт. В этом случае основная программа может выглядеть как for (;;) { process_pump_switches(); process_pressure_regulation(); show_trend(); } Если функция show_trend вызывается с запаздыванием, то пакет данных может быть потерян. Решением этой проблемы может быть вынос коммуни- кационных функций из show_trend и организация очереди, куда при обра- ботке прерываний последовательного порта помещается очередной запол- ненный пакет для последующей обработки с помощью show_trend. Приведенный здесь пример иллюстрирует циклический (round robin) механизм выполнения задач, вполне подходящий для многих применений. Однако этот же пример показывает, что по мере роста числа и сложности функций, которые необходимо выполнять, наличие стандартных средств организации параллельного выполнения задач, работы с таймером, межза- дачного обмена информацией и т. п. могут существенно повысить произ- водительность программистов и уменьшить число ошибок. Именно здесь могут проявить свои положительные стороны ядра и операционные сис- темы реального времени, как раз такие средства и предлагающие. В общем случае решение о применении какого-либо коммерческого ПО реального времени зависит от множества факторов, в том числе и от таких, как время, отпущенное на разработку, наличие и квалификация специалис- тов, объемы финансирования проекта и т. п.

RkJQdWJsaXNoZXIy MTQ4NjUy