і
МИКРОКОНТРОЛЛЕРЫ
і
применяются специальные сущности (например, т.н.
се-
мафоры).
На уровне же микроконтроллера достаточ-
но будет запретить работу механизма прерываний на
время работы с очередью. Время работы фонового
процесса в режиме с запрещ енными прерываниями
должно быть
минимальным,
иначе нам вновь придет-
ся столкнуться с той же самой проблемой - потерей
прерываний, - от которой мы и стараемся всеми си-
лами убежать.
4. Собственно проверка очереди (есть ли в ней со-
общения). Процедура извещает о наличии (отсутствии)
сообщений в очереди через
код возврата
- флаг С
(про коды возврата см. статью “Автоматное програм-
мирование для микроконтроллеров”).
5. Если очередь пуста (первый раз после команды
wait
такого, конечно быть не может, но на этот учас-
ток программы мы попадаем не только после коман-
ды
wait),
- продолжить ожидание новых сообщений
6. Если же очередь не пуста, то необходимо начать
собственно обработку полученного сообщения, но вна-
чале необходимо вновь разрешить работу механизма пре-
mov
%аО,<мл.байт эадержки>
mov
%al,<ст.байт задержки>
Так вот, операцию занесения значения в виртуалы
ющим образом:
est
ООООІОООЬ
; Запретить
mov
%a0,<мл.байт задержки>
mov
%al,<ст.байт задержки>
sst
ООООІОООЬ
; Разрешить
Причина, теперь, думается, понятна читателю -
нет
никакой гарантии,
что между двумя командами
шоу
не возникнет сигнал тика таймера, и обработчик пре-
рываний от таймера не обработает такой “полузапол-
ненный” виртуальный таймер - естественно, на свой
манер. Безусловно, вероятность такого события не
слишком велика и легко списывается» на случайный
сбой аппаратуры или те же “кривые ручки” разработ-
чиков, но на самом деле причина здесь именно в том,
что не были учтены особенности работы с
разделяе-
мыми ресурсами
(в данном случае разделяемыми
между фоновым процессом и обработчиком прерыва-
ний от таймера). Если бы виртуальный таймер был 8-
битным, там такого рода проблем не возникло бы -
для занесения значения в 8-битный таймер требуется
всего одна команда, а механизм прерывания не мо-
жет прервать выполнение
команды,
он вклинивается
рываний, чтобы при возникновении новых прерываний
обработчики могли их корректно обработать и сохра-
нить информацию о них в очереди сообщений.
7. После завершения обработки одного сообщения
необходимо вновь проверить, не появилось ли в оче-
реди чего-нибудь новенького (такое вполне могло быть
- ведь во время обработки сообщения могли возни-
кать другие прерывания, и, следовательно, обработ-
чики прерывания могли пополнить очередь). Обрати-
те внимание - команда
jmp
передает управление не
на вызов testQueue, а снова на команду запрета рабо-
ты механизма прерываний!
Любая работа с разде-
ляемыми ресурсами
должна происходить в “скобках”
est // обработка // sst!
Это -
общее правило парал-
лельного программирования,
и нарушать его нельзя!
В статье, посвященной работе с виртуальными таймера-
ми, было вскользь сказано о “тонкости”, которую мы не учли
при работе с виртуальным таймером, и которую мы теперь
можем наконец-то разобрать. Напомним читателю, что для
занесения значения в 16-битный виртуальный таймер ис-
пользовалась примерно такая последовательность команд:
таймер на самом деле нужно было выполнять следу-
прерывания .
прерывания.
в работу микроконтроллера
между
командами. Ины-
ми словами, занесение значения в 8-битный виртуаль-
ный таймер является с этой точки зрения
атомарным
действием, и там проблемы параллельного програм-
мирования не возникают. А вот занесение значения в
16-битный виртуальный таймер требует уже два дей-
ствия (не является атомарным), и тут-то проблемы па-
раллельного программирования вылезают во всей
красе.
Еще одной проблемой, которая требует учета осо-
бенностей работы с разделяемыми ресурсами, явля-
ется управление сторожевым таймером. Предполо-
жим, что сторожевой таймер в программе использу-
ется в качестве “движущ его начала” динамической
индикации, т.е. всякий раз перезапускается заново
после одного цикла индикации. Простой, элементар-
ный вопрос - как его остановить?
Простой ответ (предполагаем, что регистр
#D
содержит
18h):
точ1
%<15, ОААЪ
; Выдать в регистр таймера характерный код.
точ!
%<15, ООххххххЬ
; Останов счета.
Правильно? Нет тут-то было!
Нет никакой гарантии,
что между двумя этими командами не произойдет
прерывание от сторожевого таймера, а тогда это код выполнится вот так
(см. следующую с границу):
38 [
I Радиолюбитель - 0 8 /2 0 0 6
предыдущая страница 37 Радиолюбитель 2006-08 читать онлайн следующая страница 39 Радиолюбитель 2006-08 читать онлайн Домой Выключить/включить текст