Страница 3 из 4

Добавлено: 26 ноя 2010, 12:37
koolhatcker
delay_us(13);
Если в этот момент больше ничего делать не нужно(МК только генерит прямоугольник и больше ничем не занимается), то похоже на правду.
И ещё...
Почему TCNT0+=0x06; а не TCNT0=0x06;?
Ведь нужно загрузить в таймер новое значение, а не увеличивать имеющееся на 6.
P.S. Для флага не обязательно занимать 16 бит.
Сделайте его хотя бы Unsigned Char, если с битовым массивом возиться не хотите.:)

Добавлено: 26 ноя 2010, 12:52
xumuk
koolhatcker, я думал TCNT0 неприрвыно инкрементируется, даже во время обработки прерывания %)
А если я присвою 6, то выходит сбросится все что он
насчитал к моменту присвоения?

О, а как работать с битовым массивом? Мне для флага одного бита хватит :)

Добавлено: 26 ноя 2010, 13:00
Germie
xumuk писал(а):

Код: Выделить всё

int light = 0;

interrupt [TIM0_OVF] void timer0_ovf_isr(void){

    if(light==1){
        PORTB.3=1;
        delay_us(13);
        PORTB.3=0;
    }
    TCNT0+=0x06;
}
Похоже на правду?
(light это флаг, установкой которого я включаю или выключаю генерацию импульсов. Хотел сделать его булевым, но компилятор ругется :(, пришлось инт делать)
Полностью согласен с koolhatcker.
1 Надо присвоить TCNT0 новое значение, а не прибавлять к нему 6.
2 Крайне нежелательно использовать в прерываниях какие-либо временные задержки, если МК еще чем-либо в это время должен заниматься. Я так понимаю, 13 мкс - это длительность импульса при частоте 38 кГц и скважности 2? В этом случае лучше увеличить частоту таймера в два раза. И при каждом входе в прерывание менять состояние выхода на противоположное. А если генерация последовательности не нужна, просто запрещать прерывание по таймеру или обнулять его предделитель.
xumuk писал(а):я думал TCNT0 неприрвыно инкрементируется, даже во время обработки прерывания %)
А если я присвою 6, то выходит сбросится все что он
насчитал к моменту присвоения?
Все верно, непрерывно инкрементируется. Поэтому нужно менять его содержимое сразу при входе в прерывание и, еще раз, не использовать в прерывании никаких временных задержек. Но, даже в этом случае, порядка четырех тактов при входе в прерывание будут потеряны и частота не будет точно соответствовать установленной. Если точность частоты генерации важна, можно воспользоваться 16-тиразрядным таймером и увеличить значение предделителя.

Удачи :).

Добавлено: 26 ноя 2010, 14:49
xumuk
Понял, спасибо, переделаю :)

Вот только непонятен один момент
порядка четырех тактов при входе в прерывание будут потеряны и частота не будет точно соответствовать установленной
Почему частота не будет соответствовать?

Добавлено: 26 ноя 2010, 14:55
TK-15
как работать с битовым массивом?
С битами работают с помощью логических операций
AND - для сброса бита
OR - для установки
XOR - для переключения
в unsigned char соответственно можно хранить 8 флагов

Добавлено: 26 ноя 2010, 14:58
TK-15
Почему частота не будет соответствовать?
вход в прерывание требует минимум 4 такта - почитай справочник. Лучшее из доступного ИМХО книжки по AVR Евстифеева.

Добавлено: 26 ноя 2010, 15:06
Germie
xumuk писал(а):Понял, спасибо, переделаю :)

Вот только непонятен один момент
порядка четырех тактов при входе в прерывание будут потеряны и частота не будет точно соответствовать установленной
Почему частота не будет соответствовать?
На вход в прерывание МК, в общем случае, тратит четыре такта. То есть, к моменту входа в прерывание твой таймер, работающий на частоте МК (без предделителя) насчитает уже четыре. Можно, в принципе вносить поправку, как ты это делал. А можно просто учитывать это дело и загружать в TCNT не 6, а 10. Но, имхо, не красиво :). И, все равно, не точно. А если в программе появятся еще прерывания, отнимающие процессорное время, погрешность установки частоты еще увеличится.

Удачи :).

Добавлено: 26 ноя 2010, 15:10
xumuk
С битовым массивом понятно, буду пользовать :trumbsup:
вход в прерывание требует минимум 4 такта
Да, но непонятно куда эти 4 такта прицепить и почему они влияют на чатсоту %)
TCNT0 ведь продолжает увеличиваться пока идет вход в прерывание ? Выходит когда вход будет выполнен в TCNT0 уже будет 0х04?

Добавлено: 26 ноя 2010, 15:13
Germie
xumuk писал(а):С битовым массивом понятно, буду пользовать :trumbsup:
вход в прерывание требует минимум 4 такта
Да, но непонятно куда эти 4 такта прицепить и почему они влияют на чатсоту %)
TCNT0 ведь продолжает увеличиваться пока идет вход в прерывание ? Выходит когда вход будет выполнен в TCNT0 уже будет 0х04?
Да, уже будет 4. А ты меняешь в обработчике значение TCNT0. В твоем случае, конечно же, можно просто прибавлять к TCNT0 6, но так можно сделать далеко не всегда и, обычно, так не делают.

Добавлено: 28 ноя 2010, 01:28
xumuk
Урра! Заработало :crazy:
Спасибо всем за помощь, особенно Germie, помогавшему мне исправлять ошибки вчера до часу ночи :company:
Показать/Спрятать
Вот такой ИК пульт получился для фотокамер Nikon.
Изображение
Теперь берусь за тахометр :)

Добавлено: 28 ноя 2010, 17:26
Dj_smart
  Не в тему:   koolhatcker, глянь, это стоит внимания, или нет? http://www.freeduino.ru/arduino/lang.html

Добавлено: 28 ноя 2010, 17:31
Germie
Dj_smart писал(а):
  Не в тему:   koolhatcker, глянь, это стоит внимания, или нет? http://www.freeduino.ru/arduino/lang.html
И я, и я... С вашего разрешения вклинюсь :).
Ардуино - ново- (почти ново-, точнее :) ) модное увлечение молодых западных эмбеддеров.
Особого внимания, в смысле надо ли платить за эту платформу денег, не стоит. А в качестве пособия для новичков использовать можно. В принципе, платформа не предлагает ничего принципиально нового, чего нельзя бы было сделать на любой грамотно спроектированной макетке под AVR.

Добавлено: 28 ноя 2010, 17:58
koolhatcker
Dj_smart, я согласен с Germie, ничего там такого нет, обычная макетка. Из плюсов - язык больше похож на бейсик, чем на Си :) и готовых приложений под это железо тьма написана.

Добавлено: 28 ноя 2010, 18:02
Dj_smart
Да макетка меня меньше всего... Понравилось это: Согласитесь, очень удобно начать работу с последовательным портом на
скорости 9600 бит в секунду, сделав вызов одной строчкой:

Serial.begin(9600);

Просто очень. А на бейсик действительно похоже.

Добавлено: 28 ноя 2010, 18:08
Germie
Dj_smart писал(а):Да макетка меня меньше всего... Понравилось это: Согласитесь, очень удобно начать работу с последовательным портом на
скорости 9600 бит в секунду, сделав вызов одной строчкой:

Serial.begin(9600);

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

Добавлено: 28 ноя 2010, 18:12
TK-15
Согласитесь, очень удобно начать работу с последовательным портом на
скорости 9600 бит в секунду, сделав вызов одной строчкой:
Dj_smart - "просто так" ничего не бывает :). За всю эту простоту идет оплата размером кода. В С и так полно библиотек, так что использовать ни чуть не сложнее.
в качестве пособия для новичков использовать можно
наверное это основное ....

Добавлено: 03 янв 2011, 22:20
xumuk
Не совсем в тему, но т.к. я новичок в этом деле, решил написать сюда.

Как зависит у AVR частота встроенного генератора и напряжение встроенного источника опорного напряжения (2,56 в) от напряжения питания?
Т.е. можно ли запитывать МК напрямую от Li-ion аккумулятора?

Добавлено: 03 янв 2011, 23:48
Germie
Зависимость частоты внутреннего генератора от напряжения примерно такая

Изображение .

Однако, следует заметить, что у многих МК серии AVR имеется один или несколько регистров OSCCAL (регистр калибровки частоты внутренних генераторов), которые позволять подстроить частоту при отличном от 5 В напряжении питания.

Образцовое напряжение АЦП от напряжения питания практически не зависит (на то оно же и образцовое :) ).

Так что, никто не мешает питать МК от твоего аккума.

Удачи :).

Добавлено: 04 янв 2011, 00:12
xumuk
Понял, спасибо :)

Придется повесить кварц.

Добавлено: 09 янв 2011, 15:44
xumuk
Подскажите пожалуйста как из char сделать и вывести на экран float в формате x.xx

Чар получаю с двух каналов АЦП. Опорное напряжение 2,56.

Пробовал так

Код: Выделить всё

sprintf(lcd_buffer,"%4u\n%4u", ((float)read_adc(0))/100, ((float)read_adc(1))/100);
На экран выводятся 4хзначные числа без точки.

Добавлено: 09 янв 2011, 15:58
okan_vitaliy
sprintf(lcd_buffer,"%1.2f %1.2f", ((float)read_adc(0))/100, ((float)read_adc(1))/100);

Добавлено: 09 янв 2011, 17:06
xumuk
okan_vitaliy, заработало! :goodtime: Спасибо :company:

Вот только пришлось помучаться с CVAVR, сначала выводило просто 2f 2f
Оказалось надо полезть в Project -> Configure -> C Compiler ->
и в выпадающем списке (s)printf Features выбрать "float, width, precision" (по умолчанию только "int, width").

У меня тут еще вопрос назрел - могу ли я использовать прерывания ацп (250 КГц) еще и как таймер? Хочу туда положить счетчик чтобы засекать время между появлением сигнала на первом и втором канале АЦП.

Добавлено: 09 янв 2011, 17:16
okan_vitaliy
Можно, только поделите частоту на 13(за 13 тактов происходит преобразование).

Добавлено: 23 мар 2011, 14:37
vzgherea
В контроллерах, описанных на этом сайте, сигнал STEP подаётся на ножку МК которая поддерживает внешнее прерывание. Можно ли для STEP использовать другие ноги и ловить на них изменения уровня сигнала или всё-таки первый вариант предпочтительнее?

Добавлено: 23 мар 2011, 14:44
koolhatcker
Можно, но первый вариант предпочтительнее, т.к. если длительность импульса будет меньше частоты опроса входа, то импульс пройдёт незамеченным.

Добавлено: 23 мар 2011, 14:52
vzgherea
koolhatcker писал(а):если длительность импульса будет меньше частоты опроса входа, то импульс пройдёт незамеченным
А разве при использовании других ног в качестве входа МК не вызывает обработчик прерывания как и в случае с ножкой INT?

Добавлено: 23 мар 2011, 14:59
koolhatcker
Не все МК это могут делать и не со всеми ногами.

Добавлено: 24 мар 2011, 09:18
okan_vitaliy
vzgherea писал(а): А разве при использовании других ног в качестве входа МК не вызывает обработчик прерывания как и в случае с ножкой INT?
Все современные Меги (AVR) поддерживают прерывание по перепаду сигнала почти на всех лапках. Тут главное что бы в прерываниях почти ничего не обрабатывалось, а обрабатывалось в маине. Тогда пропусков не будет.

Добавлено: 24 мар 2011, 11:13
koolhatcker
Тут главное что бы в прерываниях почти ничего не обрабатывалось, а обрабатывалось в маине
И чтобы время обработки в маине было меньше, чем частота входных импульсов :).

Добавлено: 27 мар 2011, 08:44
okan_vitaliy
koolhatcker писал(а): И чтобы время обработки в маине было меньше, чем частота входных импульсов :).
Это совсем не обязательно. В прерываниях задача не пропустить входные импульсы, а вот в майне Вы их обрабатывать можете как хотите. Тут все зависит от алгоритма. Причем не обязательно что бы майн выполнялся быстрее чем один импульс. Просто обработчик в майне должен быть готов к тому что в счетчике импульсов будет не один, а несколько импульсов и корректно эту ситуацию обработать. У меня в контроллере так и сделано. И помимо обработчика шагов в майне еще крутится дофига других обработчиков.