Перейти к содержанию

Индивидуальное Запрещение/разрешение Прерываний


Рекомендуемые сообщения

Код пишу на С, компилятор AVRstudio, МК мега16. В программе нужно на время запретить внешнее прерывание int0, а по переполнению таймера 2, программа переходит в обработчик прерывания переполнения таймера. Здесь нужно очистить флаг прерывания int0 и затем разрешить прерывания int0. Т.е. это реализация антидребезга :)

Объясните, как индивидуально запрещать/разрешать прерывания. Ну, или совет, как бороться с антидребезгом :)

Ссылка на комментарий
Поделиться на другие сайты

Реклама: ООО ТД Промэлектроника, ИНН: 6659197470, Тел: 8 (800) 1000-321

Как вариант можно попробовать заносить 0x00 в регистры инициализации INT как по даташыту. А потом когда надо, заново инициализировать INT.

Изменено пользователем Krik99

Хочу AVR с тактовой частотой 100мгц.

Ну вот! Я же говорил - ноль... а ты единица... единица...

Ссылка на комментарий
Поделиться на другие сайты

20% скидка на весь каталог электронных компонентов в ТМ Электроникс!

Акция "Лето ближе - цены ниже", успей сделать выгодные покупки!

Плюс весь апрель действует скидка 10% по промокоду APREL24 + 15% кэшбэк и бесплатная доставка!

Перейти на страницу акции

Реклама: ООО ТМ ЭЛЕКТРОНИКС, ИНН: 7806548420, info@tmelectronics.ru, +7(812)4094849

Выбираем схему BMS для корректной работы литий-железофосфатных (LiFePO4) аккумуляторов

 Обязательным условием долгой и стабильной работы Li-FePO4-аккумуляторов, в том числе и производства EVE Energy, является применение специализированных BMS-микросхем. Литий-железофосфатные АКБ отличаются такими характеристиками, как высокая многократность циклов заряда-разряда, безопасность, возможность быстрой зарядки, устойчивость к буферному режиму работы и приемлемая стоимость. Но для этих АКБ, также как и для других, очень важен контроль процесса заряда и разряда, а специализированных микросхем для этого вида аккумуляторов не так много. Инженеры КОМПЭЛ подготовили список имеющихся микросхем и возможных решений от разных производителей. Подробнее>>

Реклама: АО КОМПЭЛ, ИНН: 7713005406, ОГРН: 1027700032161

Это изврат. Просто считывай состояние кнопок с частотой 50Гц, или меньше если это допустимо. никакого дребезга при этом не будет, кнопка будет распознана +0..20мс от её фактического нажатия, и поскольку изменения будут считываться гораздо реже импульсов дребезга, на сам дребезг прийдется лишь ОДНО считывание, результат которого не будет неопределен - он либо будет равен предыдущему состоянию, либо следующему(при переходе 0 в 1 промежуточное значение или 1 ил 0 роли не играет - просто нажатие будет зафиксировано либо раньше либо позже). Лишь кратковременное нажатие кнопки будет под вопросом(контроллер при этом может зарегестрировать только состояние приходящееся на момент дребезга а это либо 0 - тогда нажатие уйдет впустую либо 1 тогда следующее состояние будет 0 и зарегестрировано нажатие кнопки 1 раз), но раз это нажатие произошло оно всеравно должно быть зарегестрировано.

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

:blink: ЛИбо я прав , либо все время ( недавно начал ) которое занимаюсь МК неправильно думал , не знаю , но добавлю и я свои 5 копеек .

Наскоько я знаю как только призошло прерывание так сразуже запрещаются ВСЕ прерывания пока не закончится обработка этого . И по сути если кнопки висят на ножках прерывания то дребезг не страшен потомучто как только произошло прерывание то они запрещаются и все импульсы дребезга просто не воспринимаются ( если обработчик прерывания выполняется оч быстро то тогда дребезг может снова запустить прерывание . в таком слусае я делаю в обработчике прерывания небольшую паузу )

Помойму дребезг страшен когда опрашиваются кнопки с помощю обыкных портов а если использовать прерывания то МК автоматически не даст себе больше раз прерваться .

Если надо не запрещать остальные прерывания во время обработки внешнего это можно сделать , но это не есть айс . Представьте себе что во время обработкивнешнего прерывания произойдет прерывание таймера , бедный стек :(

Народ ответьте правильно ли я думаю или нет ?

Ссылка на комментарий
Поделиться на другие сайты

Это изврат. Просто считывай состояние кнопок с частотой 50Гц, или меньше если это допустимо. никакого дребезга при этом не будет, кнопка будет распознана +0..20мс от её фактического нажатия, и поскольку изменения будут считываться гораздо реже импульсов дребезга, на сам дребезг прийдется лишь ОДНО считывание, результат которого не будет неопределен - он либо будет равен предыдущему состоянию, либо следующему(при переходе 0 в 1 промежуточное значение или 1 ил 0 роли не играет - просто нажатие будет зафиксировано либо раньше либо позже). Лишь кратковременное нажатие кнопки будет под вопросом(контроллер при этом может зарегестрировать только состояние приходящееся на момент дребезга а это либо 0 - тогда нажатие уйдет впустую либо 1 тогда следующее состояние будет 0 и зарегестрировано нажатие кнопки 1 раз), но раз это нажатие произошло оно всеравно должно быть зарегестрировано.

Все правы, и в то же время, все не правы :)

Во первых, сигнал снимается не с кнопки, а с трамблера, т.е. частота "нажатий" колебрится от 1600/сек (ХХ ДВС) до 16000/сек (8000 об. коленвала).

Из расчетов, я определил время задержки. Оно равно 20мсек. Можно, конешно сделать задержку в прерывании на это время, но есть еще 1 проблема:

Значение частоты вращения КВ выводится на семисегментный индикатор. Кроме того, предусмотрено изменение яркости индикатора в зависимости от внешних факторов. Теперь, если делать задержку на 20мсек в каждом прерывании, то получается, что при более высокой частоте вращения КВ, яркость свечения индикатора не есть величина постоянная, а это мне не подходит.

Поэтому я решил по приходу сигнала запретить прерывание, и включить счетчик. Пока счентчик считает, мы показываем информацию на дисплей, потом очищаем флаг прерывания и тоключаем счетчик. Переходим снова в функцию индикации. :) Вот так :)

Ссылка на комментарий
Поделиться на другие сайты

внчале речь шла про кнопку. Но коли так, тогда и методы другие. но запрещать разрешать прерывания на некоторое время - не очень хороший вариант, ведь это будет мертвое время для основной программы. Возможно, будет лучше в прерывании запретить его и запустить таймер, а основная программа по признаку переполнения таймера разрешит прерывания, или же не запрещать их а анализировать состояние таймера, если признака переполнения нет - игнорировать поступившее прерывание. Это даст возможность во время задержки работать программе, и даже реагировать на другие прерывания.

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

:)

внчале речь шла про кнопку.
не-а :)
Возможно, будет лучше в прерывании запретить его и запустить таймер, а основная программа по признаку переполнения таймера разрешит прерывания

Вот так я и хочу! Ну, я уже в принципе разобрался - почитал ДШ:

Как я понимаю, нужно, в 6-й бит регистра GICR записать 0 для деактивации и 1 для активации прерывания инт0.

У меня есть вопрос, т.е. сомнение по поводу сдвига. Объясните, пожалуйста, а то недопонял как это правильно делается.

Вот, например, я хочу в PORTA.6 записать 1. На сколько битов нужно сдвинуть 1? На сколько я понимаю, то это нужно сделать так:

PORTA.6 |=(1<<7);

т.е. сдвигать нужно на 7 битов? Или на 6? Не пойму...

А если нужно туда вести 0, то как наложить маску?

Я читал по этой теме, но, так до конца недопонял эту тему со сдвигом и масками...

Ссылка на комментарий
Поделиться на другие сайты

ззачем сдвигать, записывай константу сразу. а если тебе надо сохранять другие, трогать только биты - для этого есть битовые операторы которые оперируют чисто битами.

потом, если масками - для уст.1 - делаешь операцию OR с константой у которой стоит 1 в нужном месте.

Если нужно обнулить бит - делаешь операцию AND с инверсией аналогичной маски.

Понавыучивают тут С, и не знают таких простых приемов ....

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

Скажите, а разве для защиты от "дребезга" не поможет просто конденсатор и резистор ?

Вот я тут нарисовал, : ))))

post-31908-1258922700_thumb.jpg

В те несколько микросекунд, когда имеет место собственно дребезг, конденсатор заряжается/сглаживает... короче, потенциал на ноге МК возрастет до нужного значения уже после дребезга. Это не правильно ?

*******************************************

Извиняюсь, сам понял глупость: когда кнопку отожмут конденсатор будет поддерживать единицу на МК... Но как-то же можно на железе это устранить ?

Изменено пользователем Cavalryman
Ссылка на комментарий
Поделиться на другие сайты

то что он будет держать 1 то не проблема, решается резистором паралельным. Проблема в том что конденсатор будучи заряженным до порога срабатывания подводит логический вход до того состояния когда он обладает максимальной чувствительностью к переключению, даже гистерезис в этот момент не поможет. Ну и недостаток - инерционность всей схемы... пока зарядится, пока разрядится....

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

Но как-то же можно на железе это устранить ?

Ну, дак вот так, собвственно и устраняют...

Просто МК не важно, будет ли лог 1 присудствовать на ноге после выхода из ф-и обработчика прерываний, или просто произойдет 2-е нажатие еще во время ф-и обрабоютчика.

На сколько я понял, то флаг (запрос) на прерывание устанавливается как только на ноге устанавливается нужный уровень напряжения (например лог1). Потом программа, как можно скорее переходит в ф-ю обработчик. Когда она туда попадает, то сразу глобально запрещаются прерывания (чтобы не скакать из 1-го прерывания в другое) и сбрасывается флаг (запрос) на это прерывание. Т.е. как только сброшен флаг, то, если опять на ноге появится напряжение, вызывающее прерывание, флаг выставится снова и при выходе из обработчика прерываний, мы опять попадем в этот же обработчик прерываний, т.к. флаг установлен. Это и есть дребезг.

Для устранения дребезга в обработчике прерывания применяют (иногда и это не совсем правильно) задержку. Т.е. попали в обработчик, сделали то, что надо, потом задержка, потом сбросили флаг этого прерывания и пошли дальше по программе.

Моя же задача стояла так, чтобы:

1. Не делать задержка в прерывании

2. Не делать глобального запрета прерываний, а запретить только это прерывание.

Это планирую сделать так: Входим в обработчик прерывания, делаем то, что нужно, запрещаем это прерывание (Заносим в бит 6 регистра GICR 0), затем активируем таймер и идем по программе. Как только таймер переполнится, вызовется другое прерывание, вызванное таймером. В нем, мы снимаем флаг прерывания, который мог установиться при дребезге, опять разрешаем это прерывание, отключаем таймер, чтобы дальше не сбивал нас с толку :)

2Alexeyslav:

ззачем сдвигать, записывай константу сразу

Ну, иногда возникает необходимость выставить 1 сразу в несколько битов :)

Писать каждый в отдельности, это как-то по-колхозному :)

Если нужно обнулить бит - делаешь операцию AND с инверсией аналогичной маски.

мм.. не совсем понял, что значит "аналогичной маски?"

Кароче мона пример реальный)))

Ссылка на комментарий
Поделиться на другие сайты

<...> Проблема в том что конденсатор будучи заряженным до порога срабатывания подводит логический вход до того состояния когда он обладает максимальной чувствительностью к переключению, даже гистерезис в этот момент не поможет. <...>

Тоесть, опять же, возможно "метание" воспринимаемого логического уровня из единицы в ноль и обратно ? Остается транзисторный ключ поставить :)

Дмитрий.

Для устранения дребезга в обработчике прерывания применяют (иногда и это не совсем правильно) задержку. Т.е. попали в обработчик, сделали то, что надо, потом задержка, потом сбросили флаг этого прерывания и пошли дальше по программе.

А, ну точно. Получается, что за время выполнения прерывания плюс время задержки дребезг уж точно угомонится и повторно в прерывание мы не войдем.

Изменено пользователем Cavalryman
Ссылка на комментарий
Поделиться на другие сайты

А, ну точно. Получается, что за время выполнения прерывания плюс время задержки дребезг уж точно угомонится и повторно в прерывание мы не войдем.

да

Ссылка на комментарий
Поделиться на другие сайты

Собственно, мы изначально усложнили задачу. Обычно в таких случаях проще сделать внешний подавитель дребезга - обыкновенный перезапускаемый одновибратор на NE555 - и ничего с прерываниями химичить не надо, будет четко одно прерывание на один импульс. и точка.

насчет битов... пример:

порт установлен в 11110111 надо сбросить 2 и 3 биты - делаем операцию AND с числом 11110011 получаем результат 11110011, не очень наглядно конечно но понятно -аналогично можешь поиграться с другими значениями.

еще интересна операция XOR - можно проинвертировать значение бита...

1) 00000000 XOR 00000100 = 00000100

2) 00000100 XOR 00000100 = 00000000

Изменено пользователем Alexeyslav

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

Спасибо, все понял.

Еще на счет сдвига:

Например, бит 5 регистра Reg нужно установить в 1. Какая из инструкций правильная:

Reg|=(1<<5);

или

Reg|=(1<<6);

? Я думаю, что 1-я инструкция правильная. Да или нет?

Я никак не пойму это момент потому, что, во внешнем хидере (m8_128.h), содержатся определения битов регистров следующим образом:

#define REFS1 7

#define REFS0 6

#define ADLAR 5

#define MUX4 4

#define MUX3 3

#define MUX2 2

#define MUX1 1

#define MUX0 0

И, получается, что операция

ADMUX|=(1<<MUX0);

Равносильна операции:

ADMUX|=(1<<0);

? Получается сдвиг на 0 битов? Т.е. при сдвиге номерация позиций, на которые нужно сдвинуть единицу, ведется с 0 а не с 1?

Изменено пользователем Дмитрий Андреевич
Ссылка на комментарий
Поделиться на другие сайты

Для работы с регистром SREG, наверное удобней будет ассемблерная вставка:

SEx - установка флага

CLx - сброс флага

, где x - имя флага регистра SREG (C, N, Z, I, S, V, T, H)

Для примера: SEZ - установка флага нуля, а CLZ - сброс флага нуля.

Ссылка на комментарий
Поделиться на другие сайты

Моя же задача стояла так, чтобы:

1. Не делать задержка в прерывании

2. Не делать глобального запрета прерываний, а запретить только это прерывание.

Это планирую сделать так: Входим в обработчик прерывания, делаем то, что нужно, запрещаем это прерывание (Заносим в бит 6 регистра GICR 0), затем активируем таймер и идем по программе. Как только таймер переполнится, вызовется другое прерывание, вызванное таймером. В нем, мы снимаем флаг прерывания, который мог установиться при дребезге, опять разрешаем это прерывание, отключаем таймер, чтобы дальше не сбивал нас с толку :)

Иногда "жонглирование" с прерываниями (разрешение/запрещение) может привести к нежелательным результатам. Может сделать проще? А именно...

В начале обработчика прерывания (INT0) сделать проверку флага нажатия (или одноразового выпонения прерывания - как угодно) и если он поднят (поднимается при первом проходе обработчика, в конце тела) условным переходом проходить "насквозь" в конец обработчика (к RETI), ничего не делая. В мэйне, по поднятию флага, запустить таймер или организовать программный таймер/счетчик, если аппаратные все используются, по истечению времени которого сбросить флаг нажатия, что приведет к однократному срабатывания прерывания при следующем событии. Еще лучше запускать его при условии снятия уровня со входа INT0. В таком случае никаких запретов (для данной операции) вообще не потребуется, а наращивание счетчика будет происходить либо аппаратно, либо программно (один раз за один полный оборот Мэйна), что никак не повлияет на длительность общего цикла и не внесет заметной погрешности при включении/отключении таймера/счетчика.

Изменено пользователем Геннадий
Ссылка на комментарий
Поделиться на другие сайты

чета не понял про мейн. Чем в нем запускать таймер, так может из обработчика сразу его и запускать? Я так планировал делать.

пока мейн (или другие ф-и) будут выполнятся, таймер считает. Как досчитал - сбросил флаг, разрешил прерывание и все. Мне кажется, вариан наиболее простой :)

Ссылка на комментарий
Поделиться на другие сайты

При свободных таймерах простой. Но! Дребезг контактов бывает не только при нажатии, но и при отпускании кнопки (если используется вариант с кнопкой вообще), все зависит от состояния (изношенности) контактов. Поэтому я и предложил в Мэйн вставить функцию, которая проверяла состояние линии INT0 и при снятии сигнала "нажатия", только тогда запускала бы таймер, который опустит флаг нажатия. Это защитит лишний раз от сбоев программы при длительном (более периода таймера) нажатии на кнопку. Получится "как досчитал - сбросил флаг", а прерывания можно и не запрещать, если грамотно обработать флаг. Это еще проще.

Ссылка на комментарий
Поделиться на другие сайты

Что-то мне кажется, что простой буфер с диодом Шотки решит вашу проблему. А дальше просто по прерыванию от Int0 (если уж вы так хотите его использовать), обрабатываете событие On Level Change. Как по мне то такое должно работать.

Ссылка на комментарий
Поделиться на другие сайты

Буффер не решит, только уменьшит вероятность сбоя. А вот любой одновибратор с перезапуском - да. И не надо будет мучить прерывания и делать сложную программу.

Всегда нужно находить более простое решение - добавление одного внешнего элемента значительно упрощает программу.

Учение - изучение правил. Опыт - изучение исключений.

Ссылка на комментарий
Поделиться на другие сайты

Присоединяйтесь к обсуждению

Вы публикуете как гость. Если у вас есть аккаунт, авторизуйтесь, чтобы опубликовать от имени своего аккаунта.
Примечание: Ваш пост будет проверен модератором, прежде чем станет видимым.

Гость
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Ответить в этой теме...

×   Вставлено с форматированием.   Восстановить форматирование

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

Загрузка...
  • Последние посетители   0 пользователей онлайн

    • Ни одного зарегистрированного пользователя не просматривает данную страницу
  • Сообщения

    • А здесь всё о том как и чем делать ...
    • "Приходит мужик в магазин одежды, чтоб подобрать себе шляпу. Надевает первую попавшуюся, а она ему - как раз." А вообще не понятно. Он ему дает говорить, даже матюкаться, а анекдот не дает рассказать. Почему? (сори, если вопрос тупой, я просто не в теме радиосвязи и радиохулиганства)
    • Там на примерах видос уже с задержкой писанный, дропов нет.   уже предлагалось 
    • БОРОДА ! я там все верно написал. Просто так резисторы не горят !!! Вы видимо то же дуб дубом в этом деле как и ФАЛКОНИСТ модератор.
    • Можно скрин с программы  Victoria по проверки диска "С"  и флэшки? С диска "с" воспроизводится как? Если так же, то можно эту же флэшку вставить в телефон/фотоаппарат и проверить, с качеством записи не хуже чем на вашей камере? Если копировать видео с камеры которая подключена к компьютеру, то за сколько копируется файл например гигабайтной длинны? А если его же записать?  
    • В ГДР-овских швейных машинах позднего периода линейки Famula присутствуют модели с т.н. автоматическими функциями, они отличаются от остальных словом Electronic в названии, индексом 51 в номере модели, и наличием трёх кнопок справа: левая кнопка: положение иглы (в нажатом состоянии - игла всегда будет возвращаться вниз, в отжатом - уходить наверх) средняя: одиночный прокол - при нажатой кнопке и нажатии на педаль отрабатывается один цикл опускания и подъёма иглы правая: пониженная скорость - при нажатой кнопке, скорость ограничена фиксированным значением Электронная часть состоит из модуля Управления скоростью, модуля Позиционирования иглы и мотора с педалью. Вот схемы из той документации, что удалось добыть:     Указанные функции реализованы в модуле Позиционирования иглы (схема на стр. 22), позиция иглы отслеживается по герконовому датчику на маховике, подключенного непосредственно к модулю позиционирования (разъём X5). Модуль модуль управления скоростью (стр. 21) подключен к сети 220 через выключатель, к мотору (стр.18) и к одному из выводов педали. Модуль позиционирования подключен к модулю управления скорости (X4.2, X4.3, X4.4) и второму выводу педали (X4.1), к первому выводу педали - через X4.4.   Педаль представляет собой угольный реостат, в нажатом положении сопротивление стремится к нулю. Проблема: Не работает позиционирование иглы в крайних точках, в зависимости от положения левой кнопки (S1) - после отпускания педали игла останавливается в произвольном положении. Не работает функция т.н. Одиночного прокола - когда нажата кнопка S2, по нажатию педали маховик стоит на месте и не двигается. Не учитывая функционал этих кнопок, всё остальное исправно работает, включая функцию пониженной скорости - при нажатии правой кнопки (S3). Что было сделано: Визуальный осмотр, чистка контактов и замена электролитических конденсаторов на всех платах. Замена симистора на Модуле оборотов и всех транзисторов и микросхемы логики на Модуле позиционирования на полные аналоги. Прозвонка герконового датчика положения иглы, кнопочных переключателей S1, S2, S3, прозвонка дорожек. Эксперименты по замене сдвоенного операционного усилителя B2761 на имеющийся в наличии сдвоенный компаратор LM393 (неудачные). После этого была получена в распоряжение полностью рабочая машина аналогичной модели, используемая в дальнейшем, как референсная, и окончательно выявлен неисправный модуль - м. позиционирования. Методом кросс-замены были проверены и исключены все активные элементы: сдвоенный операционный усилитель B2761 (N1), микросхема логики D1, транзисторы V1 и V8, а также диодные сборки V2 и V7, и конденсаторы. При очередной выпайке и запайке транзистора V8 начало наблюдаться такое поведение: после включения машина отрабатывает функцию одиночного прокола (при нажатой кнопке S2), но только один раз, иногда не до конца; дальнейшие повторные нажатия педали ни к чему не приводят. При выключении питания и последующем включении, функция одиночного прокола может снова отработать один раз. После этого были пропаяны и прозвонены все элементы и дорожки по периметру, находящиеся рядом с транзистором V8, без положительного результата.     Дальнейшая работа по поиску неисправности осложняется тем, что я не очень хорошо понимаю, как работает схема Модуля позиционирования и не могу даже приблизительно сформулировать фазы её работы, в силу своей квалификации: мне непонятно подключение второго операционного усилителя N1.2 - его выход упирается в диоды V4 и V6, и его функция в этой схеме (компаратор?) работа AND-логики, в особенности элементов D1.1 и D1.2 в контексте подключения к усилителю и транзистору V8 Для прояснения ситуации, с некоторых контрольных точек, обозначенных номерами в кружках на принципиальной схеме модуля, были сняты осциллограмы на рабочем аппарате, вот они на плате: Замеры производились на прибор Fnirsi DPOX180H. Здесь канал 1 (жёлтый) - датчик позиции (геркон), точка №6, негативный контакт - X4.3 Выводы: Предположительно, управляющее напряжение на контакте X4.2. Контакты X4.1 и X4.4 соединены с соответствующими выводами реостата педали. Следующим шагом планирую последовательное выпаивание и проверку всех диодов и резисторов на плате Модуля позиционирования. Буду признателен за помощь и советы. Сам я по уровню начинающий радиолюбитель, мой опыт ограничен сборкой / мелким ремонтом и доработками БПЛА и работой с несложными схемами на базе микроконтроллеров ATMega и ESP, со схемотехникой советского периода знаком только по опыту с радиоконтрукторами и простыми транзисторными приёмниками, но очень бы хотелось разобраться, поэтому буду признателен также за ссылки на конкретные обучающие материалы по теме и методикам работы.
×
×
  • Создать...