Гы. Почему? RTK тоже умеет HALT %))))halt в операционной системе- варварская пустая трата драгоценных тактов %)
Гы. Почему? RTK тоже умеет HALT %))))halt в операционной системе- варварская пустая трата драгоценных тактов %)
ну и о чем это говорит?Сообщение от Alex/AT
у меня тоже в макете был халт. один. в стартовой процедуре.
каждый халт в среднем теряет 36000 тактов. вот и считай что можно сделать полезного за это время. повторяю еще раз- синхронизация за счет процессов реального времени.
Итак, дабы 100% исключить пропуск прерывания, ни ОС, ни задачи не должны их выключать. (А если задачи и переключают, то это уже на свой страх и риск). Если в момент прихода работает задача - все в порядке, а вот если критическая секция ОСки - возникают серьезные проблемы.
К примеру, работает планировщик, переключает задачи...приходит прерывание с которым начинается новое прогнозирование и новое переключение...Жуть, вобщем.
Я это обходил следующим образом. В качестве критического семафора менял JP по адресу прерывания. Причем так, чтобы если int пришел до или после этого, ничего бы не случилось.
А альтернативный обработчик менял на стеке адрес возврата из критической процедуры и возвращал ей управление. По окончанию адрес возврата записывался в текущий PC текущей задачи и управление передавалось настоящему обработчику.
Изврата были полные помидоры. Но работало. А сейчас лежит на дискетах, которые я не могу на ПЦ считать . Но ничего, когда-нибудь я найду себе реал .
В RTK решено с помощью подобного семафора (только там - ячейка памяти). От запрета прерываний на ~40 тактов избавиться не удалось - переключается стек, если придет прерывание, будет ЖО... но шанс попадания прерывания в этот участок кода настолько мал, что его практически можно игнорировать.К примеру, работает планировщик, переключает задачи...приходит прерывание с которым начинается новое прогнозирование и новое переключение...Жуть, вобщем.
Эээээ. Речь шла о ситуации, когда все таски сделали RTK_TIDLE, и нет синхротасков. Тогда делать уже нечего.каждый халт в среднем теряет 36000 тактов. вот и считай что можно сделать полезного за это время.
планировщик висит на обработчике. фиксированно. и вызываться вне времени может только из процедуры пропуска кванта. тут да, есть проблема пропуска только в одном случае (кусок моего исхода, модифицированный):Сообщение от Looker
;somewhere in system
yield
di
ld a,(int_flag) ;beneath DI
or pended_interrupt
ld (int_flag),a
ei
когда прерывание приходит в момент запрещенных прерываний. тут возможнен пропуск одного прерывания с вероятностью (4+13+7+13+4)/72000~5.7е-4 невелика вероятность, но она есть. другой вариант:
set pended_int,(ix/iy+int_flg_offset)
более удачен. как компромисс, вполне подходит. возможные проблемы- приход прерывания перед данной командой, пропуск кванта принудительно и, после возврата, еще один пропуск добровольно. вероятность данного события еще меньше %)
С любовью к вам, Yandex.Direct
Размещение рекламы на форуме способствует его дальнейшему развитию
(пжалста используйте русский язык, не все ведь английский изучали)
должен восстановить счётчик команда, стек, и регистры общего назначения при переключении на новый поток.
При уходе со старого потока соответственно происходит сохранение его данных (стек, регистры, счётчик).
Т.о. суммарно тот переключатель контекста, который предложил Lvd полностью удовлетворяет указанным условиям...
Технические моменты с приходом прерывания решаются несколько иначе.
На самом деле, переключатель контекста находится где-то в полосе среднеприоритетных задач (самый высокий приоритет - обработчики прерываний, средний - менеджеры памяти/потоков, нижний - собственно сами потоки с их приоритетами от критического по времени до низкого = idle), поэтому если прерывание придёт на момент, когда работает перключатель контекста, то ничего страшного не произойдёт, просто отработает обработчик прерываний, затём опять будет работать перключатель контекста.
Все проблемы с переключением контекста связаны с тем, что авторы тредов нечётко представляют себе иерархию части ядра, обрабатывающей системные события.
Все проблемы связаны с отсутствием нормального контроллера прерываний. Если подумать - то становится ясно, что прерывание может прийти в момент переключения контекста, т.е., момента запрета прерываний. А еще от невозможности "отложенного" переключения задачи (это "де факто" на любой платформе) - ибо она может добровольно и не отдать такты планировщику. А значит переключать контекст надо сразу по приходу прерывания. А если так - значит надо проверить, не переключаем ли мы контекст переключателя контекстов (deadlock). А значит нужен семафор. А атомарных операций у нас нет, надо запрещать прерывания. Короче, все к одному.Все проблемы с переключением контекста связаны с тем, что авторы тредов нечётко представляют себе иерархию части ядра, обрабатывающей системные события.
Мне кажется ты опять не до конца прочитал что я написал, или не допонялСообщение от Alex/AT
Схема такая: имеется обработчик прерываний, имеется переключатель контекста.
Обработчик прерываний работает 50 раз в секунду, переключатель контекста когда угодно.
Переключатель контекста и обработчик прерываний есть две совершенно различные процедуры/подпрограммы.
Классический орбработчик прерываний начинается в DI: Push и т.д.
Диспетчер потоков (переключатель контекста) никогда не запрещает прерывания, он имеет средный приоритет, высокий приоритет имеет только обработчик прерываний.
Во время работы обработчика прерываний прерывание прийти не может (и не должно).
Во время работы диспетчера потоков прерывание может прийти и ничего болезного здесь нет.
Думаю всё ясно...
Так как многие любят на примерах, то поясню.
1. Обработчик прерываний
DI
LD (nn),SP ; сохраняем стек
LD SP,Stack_for_Inter_Route ; переключаем стек на свою область памяти
Push ; сохраняем используемые регистры
Push
.... ; здесь выполняется обработчик прерываний, в результате работы могут быть созданы предпосылки для перенастройки диспетчера потоков
Pop ; восстанавливаем регистры
Pop
Ld Sp,nn
Ei
Ret ; здесь так же может быть переход на какую нибудь дополнительную процедуру вместо просто возврата
2. Переключатель контекста
Он выглядит следующи образом:
Push ; сохраняем используемые регистры и всю память по контексту
Push
Push
....
Call Calc_Now_Run_Thread ; вычисляем какой процесс нам надо запустить, подготавливаем его данные
...
Pop ; восстанавливаем контекст
Pop
Pop
Ret
Примечание: в результате работы обработчика прерывания может быть изменены какие либо данные, касающиеся приоритета процессов и прочей важной для системы информации. Поэтому максимум один квант времени (если прерывание пришло на диспетчер потоков) система будет работать по старой рассчитанной уже схеме. В случае же, если прерывание пришло на тело процесса, то все данные будут уже приняты измененными диспетчером потоков.
Как видно из такой схемы никаких сложностей (кроме подавления желания "упростить") не возникает - прерывание отрабатывает по одной схеме, диспетчер потоков - по другой.
Эту тему просматривают: 1 (пользователей: 0 , гостей: 1)