Выход из прерывания

Программирование микроконтроллеров AVR, PIC, ARM.
Разработка и изготовление печатных плат для модулей.

Выход из прерывания

Сообщение Master » 28 май 2008, 22:57

Есть вопросы:
1. Если программа обрабатывает команду delay_ms(60000), и в этот момент срабатывает внешнее прерывание от INT0, то оно будет обработано только по истечении 60 секунд или раньше?
2. После исполнения команд прописанных в прерывании INT0 можно ли выйти не в точку входа в прерывание, а с помощью goto перейти в другое место программы?
Аватара пользователя
Master
 
Сообщения: 4468
Зарегистрирован: 21 дек 2006, 19:56
Откуда: Украина, г.Одесса
прог. языки: Delphi и С

Re: Выход из прерывания

Сообщение rig » 29 май 2008, 09:43

1. зачем так жестоко тормозить процессор? можно же 60 раз по 1000 мс делать, или в другой пропорции. По теме не скажу, проведи эксперимент, поделись результатом.
2. думаю можно, но в стеке отстанется адрес точки возврата из прерывания возможно еще какая то служебная инфа, если его в ручную почистить тогда стек не переполнится.
Аватара пользователя
rig
 
Сообщения: 1437
Зарегистрирован: 03 авг 2007, 19:43
Откуда: Екатеринбург
прог. языки: Си, асм со словарем

Re: Выход из прерывания

Сообщение Victorovych » 29 май 2008, 10:29

Мужики, учите асм :D
Аватара пользователя
Victorovych
 
Сообщения: 491
Зарегистрирован: 20 сен 2007, 11:44
Откуда: Харьков
Skype: Victorovych_FF
прог. языки: ASM
ФИО: Иван ВикторОвич

Re: Выход из прерывания

Сообщение Master » 29 май 2008, 10:42

Мне нада на С.
Аватара пользователя
Master
 
Сообщения: 4468
Зарегистрирован: 21 дек 2006, 19:56
Откуда: Украина, г.Одесса
прог. языки: Delphi и С

Re: Выход из прерывания

Сообщение rig » 29 май 2008, 10:53

2. еще надо будет флаг прерывания снимать, иначе больше ни когда INT0 не сработает.
флаг автоматом снимается при выходе из прерывания, но мы то знает что значит автоматом :wink:
Аватара пользователя
rig
 
Сообщения: 1437
Зарегистрирован: 03 авг 2007, 19:43
Откуда: Екатеринбург
прог. языки: Си, асм со словарем

Re: Выход из прерывания

Сообщение MiBBiM » 29 май 2008, 11:39

Насколько я понимаю, надо ещё будет глобально разрешить прерывания. Вот выдержка из курса:
В конце функции обработчика прерывания компилятор ставит инструкцию RETI после выполнения которой бит7 в регистре SREG становится "1" - т.е. прерывания опять ГЛОБАЛЬНО разрешаются и программа продолжает выполняться с того места где она была в момент возникновения прерывания.

И ещё:
При возникновении события которое может вызвать разрешенное в данный момент времени прерывание и при ГЛОБАЛЬНОМ разрешении прерываний (бит7 в регистре SREG "установлен"), выполнение программы МК останавливается, сохраняются (запоминаются) место остановки и некоторые нужные данные, бит7 в регистре SREG обнуляется, очищается флаг сработавшего прерывания и затем происходит вызов и выполнение функции обработчика данного прерывания.

Т.е. флаг прерывания очищается уже при переходе в прерывание(извините за тавтологию). Впрочем, я не уверен.
И чтобы добить тему:
Если при глобальном разрешении прерываний обнаружится установленный флаг разрешенного прерывания, то будет вызвана функция- обработчик этого прерывания(такая ситуация может возникнуть если во время выполнения обработчика прерывания возникло другое прерывание - т.е. установился его флаг).
Соответственно по мере отработки накопившихся и разрешенных прерываний их флаги будут очищаться.
Флаги неразрешенных прерываний не очистятся пока программа этого не сделает записью в них числа 1.
Tomorrow will be. Better
Аватара пользователя
MiBBiM
 
Сообщения: 1866
Зарегистрирован: 29 окт 2007, 18:11
Откуда: Пермь
прог. языки: Brainfuck/Basic/Delphi/C++/Lisp/x86asm/JavaScript

Re: Выход из прерывания

Сообщение Vooon » 29 май 2008, 12:39

  1. То основной код прервется и будет выполнено прерывание.
    Если ты конечно не делаешь:
    Код: Выделить всё
    #asm("cli");
    delay_ms(60000);
    #asm("sei");
  2. Применять goto стоит лишь в исключительных случаях!
    Рекомендую почитать "Веревку достаточной длинны, чтобы... выстрелить себе в ногу"

Добавлено спустя 2 минуты 53 секунды:
да, и на сколько помню goto не позволяет выйти из функции.
Linux user | Firefox user
Аватара пользователя
Vooon
Site Admin
 
Сообщения: 3339
Зарегистрирован: 09 фев 2006, 15:36
Откуда: Москва
Skype: vooon341
прог. языки: Python, C, Bash, JavaScript, C++, PHP
ФИО: Владимир Ермаков

Re: Выход из прерывания

Сообщение SSG » 29 май 2008, 12:57

А удобно будет поинтересоваться что за устройство и зачем такая пауза? Может более другой подход придумается?
I live My life!
Аватара пользователя
SSG
 
Сообщения: 1058
Зарегистрирован: 15 янв 2007, 19:23
Откуда: Беларусь, Барановичи
прог. языки: С для МК, Delphi для ПК

Re: Выход из прерывания

Сообщение Victorovych » 29 май 2008, 13:32

Master писал(а):...
2. После исполнения команд прописанных в прерывании INT0 можно ли выйти не в точку входа в прерывание, а с помощью goto перейти в другое место программы?


Если сишный goto - это аналог асмовского jmp, то нужно стек обнулять, а то произойдет переполнение, и программа вывалится в reset
Аватара пользователя
Victorovych
 
Сообщения: 491
Зарегистрирован: 20 сен 2007, 11:44
Откуда: Харьков
Skype: Victorovych_FF
прог. языки: ASM
ФИО: Иван ВикторОвич

Re: Выход из прерывания

Сообщение Master » 29 май 2008, 14:00

SSG писал(а):А удобно будет поинтересоваться что за устройство и зачем такая пауза? Может более другой подход придумается?

От чего же нельзя, устройство управляет двигателем реле Р1 и еще одно реле Р2 для управления еще чем-нибудь. Так вот все это безобразие управляется 1 кнопкой, нажал, сработали оба реле и работают пока не отпустишь кнопку, отпустил - через паузу (скажем 10 сек) выключаются, так вот нада чтобы в момент этой паузы при повторном нажатии кнопки все заново включалось. Вот, это если упрощенно, а на самом деле там еще есть ШИМ, АЦП, потенциометр для управления ШИМом и 7-сег индикатор.
Кнопка у меня опрашивается в основном цикле вот так
Код: Выделить всё
while (1)
      {
      // Place your code here
      Display();  //Вывод на 7-сегм 
      if (PIND.2==0) {pusk();}  //ПУСК
      else {stop();}  //СТОП

      };


Добавлено спустя 5 минут 57 секунд:
Если я повешу кнопку на прерывание и задам параметр паузаРеле2 = 0, он же все равно будет после возврата в точку входа досчитывать те 10 сек? Можно как вариант использовать таймер, но как-то не очень хочица.
Аватара пользователя
Master
 
Сообщения: 4468
Зарегистрирован: 21 дек 2006, 19:56
Откуда: Украина, г.Одесса
прог. языки: Delphi и С

Re: Выход из прерывания

Сообщение MiBBiM » 29 май 2008, 16:37

По идее да, будет досчитывать.
А почему не разбить всю паузу на мелкие? Допустим, кнопку вы держите более 2 мс. Тогда(извините за Делфи вперемешку с Си):
Код: Выделить всё
const d=4800;
...
      // Place your code here
while true do
begin
display;
if PIND.2=0 then pusk else begin stop; for i:=1 to d do begin if PIND.2=0 then break; delay_ms(2) end  end;
end;

Таким образом, вы осуществляете задержу и, если в это время кнопочка оказалось нажатой, осуществляете запуск. Конечно, желательно бы это завернуть в ф-ию stop и в качестве параметра передавать кнопочку, за которой надо следить.
Т.к. внутри цикла вы осуществляете(помимо задержки) другие операторы, то надо конструкцию прогнать в симуляторе и опытным путем определить значение d.
И все-таки, использование таймера было бы лучшим решением, поскольку стопорить мк на 10(!) секунд просто кощунство какое-то. Освободившееся время можно пустить, например, на перерисовку дисплея.
А реле может держать ШИМ? Что-то мне подсказывает, что релюшка способна держать лишь ограниченную частоту, причем довольно низкую.
Tomorrow will be. Better
Аватара пользователя
MiBBiM
 
Сообщения: 1866
Зарегистрирован: 29 окт 2007, 18:11
Откуда: Пермь
прог. языки: Brainfuck/Basic/Delphi/C++/Lisp/x86asm/JavaScript

Re: Выход из прерывания

Сообщение Master » 29 май 2008, 20:35

А реле может держать ШИМ?

Ну так ШИМ выдает силовой транзистор, а реле только подает питание.
Аватара пользователя
Master
 
Сообщения: 4468
Зарегистрирован: 21 дек 2006, 19:56
Откуда: Украина, г.Одесса
прог. языки: Delphi и С

Re: Выход из прерывания

Сообщение MiBBiM » 29 май 2008, 21:10

Ну мало ли :)
Tomorrow will be. Better
Аватара пользователя
MiBBiM
 
Сообщения: 1866
Зарегистрирован: 29 окт 2007, 18:11
Откуда: Пермь
прог. языки: Brainfuck/Basic/Delphi/C++/Lisp/x86asm/JavaScript

Re: Выход из прерывания

Сообщение SSG » 31 май 2008, 09:07

Если без таймеров, то можно и на более мелкие паузы разбить. Только я бы while использовал и сравнивал значение глобальной переменной с заданным, например 100. А в прерывании глобальную переменную обнулял-бы, а в теле while был бы мелка пауза 0.6с увеличивал. Выход из цикла - переменная больше 100.
I live My life!
Аватара пользователя
SSG
 
Сообщения: 1058
Зарегистрирован: 15 янв 2007, 19:23
Откуда: Беларусь, Барановичи
прог. языки: С для МК, Delphi для ПК


Вернуться в Микроконтроллеры

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 16