Ограничения
при использовании сопрограмм
Платой за уменьшение объема потребляе-
мой оперативной памяти при использовании
сопрограмм вместо задач является то, что
программирование сопрограмм сопряжено
с рядом ограничений. В целом реализация
сопрограмм сложнее, чем реализация задач.
Использование локальных переменных
Особенность сопрограмм в том, что когда
сопрограмма переходит в блокированное со-
стояние, стек сопрограммы не сохраняется.
То есть если переменная находилась в стеке
в момент, когда сопрограмма перешла в бло-
кированное состояние, то по выходу из него
значение переменной, вероятно, будет дру-
гим. Эта особенность объясняется тем фак-
том, что все сопрограммы в программе ис-
пользуют один и тот же стек.
Чтобы избежать потери значения пере-
менных, не следует размещать их в стеке,
то есть нельзя использовать локальные пере-
менные в сопрограммах. Все переменные,
используемые в сопрограмме, должны быть
глобальными либо объявлены статическими
(ключевое слово static). Рассмотрим пример
функции, реализующей сопрограмму:
// Глобальная переменная:
unsigned int uGlobalVar;
// Функция, реализующая сопрограмму
void vACoRoutineFunction( xCoRoutineHandle xHandle, unsigned
portBASE_TYPE uxIndex )
{
// Статическая переменная:
static unsigned int uStaticVar;
// Локальная переменная — В СТЕКЕ!!!
unsigned int uLocalVar = 10L;
crSTART( xHandle );
for(;; )
{
uGlobalVar = 1;
uStaticVar = 10;
uLocalVar = 100;
// Вызов блокирующей API-функции
crDELAY( xHandle, 10 );
// После вызова блокирующей API-функции
// значение глобальной и статической переменной
// uGlobalVar и uStaticVar гарантированно сохранится.
// Значение же локальной переменной uLocalVar
// может оказаться не равным 100!!!
}
crEND();
}
Достарыңызбен бөлісу: |