Причина, по которой удаление задач из uCOS не должно происходить во время ISR
Я изменяю некоторые функции (в основном, планирование) uCos-ii.
И я обнаружил, что функция OSTaskDel ничего не делает, когда она вызывается ISR.
Хотя я изучил некоторые основные функции ОС, я действительно не понимаю, почему это должно быть запрещено.
Все, что он делает, - это вычитание из readylist и освобождение полученных ресурсов, таких как TCB или семафоры...
Есть ли какая-то причина для их запрета при обработке прерываний?
2 ответа
Из документации не ясно, почему это запрещено в этом случае, но OSTaskDel()
явно вызывает OS_Sched()
и в ISR это должно происходить, только когда существует самый внешний вложенный обработчик прерываний (обрабатывается OSIntExit()
).
Я не думаю, что следующее целесообразно, потому что могут быть другие причины, почему это запрещено, но вы можете удалить:
if (OSIntNesting > 0) {
return (OS_TASK_DEL_ISR);
}
затем сделать OS_Sched()
Вызовите условно следующим образом:
if (OSIntNesting == 0) {
OS_Sched();
}
Если это умирает ужасно, помните, я сказал, что это было опрометчиво!
Эта операция продлит ваше время обработки прерываний в любом случае, поэтому, вероятно, это плохая идея, хотя бы по этой причине.
В общем, плохая идея (не только из ISR) - асинхронно удалять другую задачу независимо от состояния этих задач или использования ресурсов. ОК / ОС-II обеспечивает OSTaskDelReq()
функция управления удалением задачи таким образом, чтобы задача могла удалять себя по запросу и, следовательно, иметь возможность правильно высвобождать все свои ресурсы. Даже без этого отправка запроса через обычные механизмы IPC задачи обычно лучше (и более переносима).
Если задача не предназначена для самостоятельного удаления по требованию, вы можете просто использовать OSSuspend().
Как правило, вы не можете сделать несколько вещей в ISR:
- блок на семафор и тому подобное
- блокировать при получении спин-блокировки, если это однопроцессорная система
- вызвать ошибку страницы, которая должна быть устранена подсистемой виртуальной памяти (то есть с виртуальной дисковой памятью)
Если вы сделаете что-либо из вышеперечисленного в ISR, у вас будет тупик.
OSTaskDel()
вероятно, делает некоторые из этих вещей.