да с этим я еще в 36 сообщении разобрался. кто же знал что еще порт в низкий уровень перевести нужно
НАЮХА??????????????????
Простите, ну уже с катушек слетаю, ... полсотни сообщений ... ну сколько можно тупить-то! Ну, поставьте же Вы, наконец, скобки в выражении "~ 1<<2" !!! Чтобы оно сначала сдвигало, а потом инвертировало, а не наоборот, как у Вас сейчас!
Кстати, 2 мкс получил реакцию на прерывание. Чисто ради спортивного интереса.)
Реакцию Вы получите и на полумикросекундное прерывание. Только измерить его длительность не сможете. А в случае PCINT, не сможете и определить, по какой ноге оно пришло.
Причем в прерывании таймер не стартует. Только флаг. Затем бог весть сколько ползем по лупу до места, где этот флаг проверится и только потом стартуем таймер. Код в топку.
И обработчик прерывания с push r24 выглядит многообещающе ))) Откуда уверенность что необходимо и достаточно r24?
Если уж так хочется чего померить - пишем buf[i++] = TCNT2; именно в обработчике. Прерывания по изменению уровня. Обнулять таймер не обязательно. Когда буфер кончится - из лупа вывод.
Опять же, подсчет длительности Вы осуществляете аппаратным таймером, а не прерыванием либо основной программой.
Я ничего не перепутал.) У ТС минимальная длительность 0-го импульса 3 мкс. Я привёл пример его измерения с помощью INT0. При минимальном времени обработчика.
Если уж так хочется чего померить - пишем buf[i++] = TCNT2; именно в обработчике. Прерывания по изменению уровня. Обнулять таймер не обязательно. Когда буфер кончится - из лупа вывод.
подскажите пожалуйста почему ардуино ide не содержит различных вспомогательных функций (того же автокомплита)? и есть ли какой нибудь более функциональный аналог для mac os? (типа phpstorm)
представляю вариант кода (в виде картинки потому что комментарии сбиваются)
потому что не надо пытаться запихнуть в комментарии "Войну и мир". Пишите коротко. Длина строки кода вместе с комментариями не должна превышать 80 символов, а лучше - если 50-60
Не смущай человека. Идея читать в прерывании верная. Только так можно мерить время точно. Почему - я выше писал. В прерывании можно все. Но быстро. И аккуратно. Могу показать много разного кода, где в прерывании чего только не делается. И запускается другое прерывание и даже сортировка списка. Не говоря уже о том чтоб таймер прочитать.
Не смущай человека. Идея читать в прерывании верная. Только так можно мерить время точно. Почему - я выше писал. В прерывании можно все. Но быстро. И аккуратно.
ну-ну... посмотрите на код ТС. "Быстро и аккуратно" - это про него, как думаете?
Не хочу подробно обсуждать, пока он код нормально не вставит, но ему явно не стоит говорить то, что вы выше написали. Он из того абзаца услышит только то, что ему удобно - мол, "в прерывании можно все"... и так и будет писать - всю программу в прерывание. как сейчас.
Нет, в прерывании, конечно, можно все. Только сперва надо выключить все прерывания, а у ТС как он включил в setup, так они и продолжают работать. А если продолжают работать, цикл while в этом случае категорически противопоказан.
Ну ту "картинку" действительно обсуждать не стоит. Но похоже она в любом случае завершится за 100-200мксек. Терпимо вполне. Особенно по сравнению, например, с софтовым UART. Работать будет (по крайней мере может работать при правильной реализации), остальному тоже мешать не будет. Меня больше смущает в таких случаях системные прерывания. Если они "тикнут" немного раньше чем прийдет старт - будет пропуск данных. Но это не часто, к счастью.
uint8_t readbytes(){
DDRD &= ~_BV (2); //set D2 on input
uint8_t count=0; //here count gets byte
uint8_t maxTries1 = 40; //count tries to catch high level
while( (PIND & _BV(2)) == 0 ) //spin cycle while line in low level
if(!--maxTries1) return count; //if device dont answer pullup line
while(1) {//dont know count started endless cycle
uint8_t result = 0; //here put bits
for (uint8_t i = 0; i < 8; i++) { //cycle for read 1 byte
PORTD &= ~_BV (2); //set low level on D2
uint16_t maxTries = 500; //count tries to catch low level
while( (PIND & _BV(2)) == 4 ) //spin cycle while line in high level
if(!--maxTries) return count;//if device dont answer pulldown line - bytes ended
_delay_us(5); //wait for catch middle
result |= ((PIND & _BV(2)) == 4) << i;//find out what in middle - 0 or 1
_delay_us(2); //wait for skip second part bit
}
temp[count++] = result;
}
}
Посмотри дизасемблированый код строки 15. Думаю удивит ;)
Параметры для _delay_us(...); ставь меньше расчетных. 1мксек - 16 тактов, грубо 10 процессорных команд. Потому сишные операторы сами по себе забирают время близкое к тем что требуются. Это надо учитывать.
Параметры для _delay_us(...); ставь меньше расчетных. 1мксек - 16 тактов, грубо 10 процессорных команд. Потому сишные операторы сами по себе забирают время близкое к тем что требуются. Это надо учитывать.
Вообще-то это учитывается. Так что ставить меньше расчетных не нужно. другое дело, что рассчитывать нужно правильно - с учетом тех операторов, что используются помимо delay.
Расчетная - в смысле ту которую рассчитываем получить))
//рассчитывать нужно правильно
Сомневаюсь что автор такты считал. Иначе бы знал, что строка 15 скомпилируется в цикл, проходящий переменное кол-во раз. От 0 до 7. И длительность ее соответственно меняется очень заметно.
Кроме того, учитывая точность процесса, не стоит просто от стартового мерить. Лучше отслеживать фронты на каждом бите и по ним работать. Хотя это похоже пытается делать местами, например стр 12.
пытаюсь понять как это сделать. как минимум одно там должно остаться
подумал логически - прерывание сработало, значит нам не нужно оно больше как минимум до тех пор пока мы не выясним идут ли за ним данные. потому я решил его просто отключить - cli()
пытаюсь понять как это сделать. как минимум одно там должно остаться
подумал логически - прерывание сработало, значит нам не нужно оно больше как минимум до тех пор пока мы не выясним идут ли за ним данные. потому я решил его просто отключить - cli()
да с этим я еще в 36 сообщении разобрался. кто же знал что еще порт в низкий уровень перевести нужно
НАЮХА??????????????????
Простите, ну уже с катушек слетаю, ... полсотни сообщений ... ну сколько можно тупить-то! Ну, поставьте же Вы, наконец, скобки в выражении "~ 1<<2" !!! Чтобы оно сначала сдвигало, а потом инвертировало, а не наоборот, как у Вас сейчас!
Порт ему надо переводить! Разобрался он!
Поражаюсь выдержке.) Сам бы уже давно психанул и послал куда подальше.(
Кстати, 2 мкс получил реакцию на прерывание. Чисто ради спортивного интереса.)
Попробуйте так, согласно таблице
запись байта в память - 2 такта
Кстати, 2 мкс получил реакцию на прерывание. Чисто ради спортивного интереса.)
Почему нет?
Результат:
Green, Вы не перепутали 5 мкс и 0.5 мкс?
Опять же, подсчет длительности Вы осуществляете аппаратным таймером, а не прерыванием либо основной программой.
Причем в прерывании таймер не стартует. Только флаг. Затем бог весть сколько ползем по лупу до места, где этот флаг проверится и только потом стартуем таймер. Код в топку.
И обработчик прерывания с push r24 выглядит многообещающе ))) Откуда уверенность что необходимо и достаточно r24?
Если уж так хочется чего померить - пишем buf[i++] = TCNT2; именно в обработчике. Прерывания по изменению уровня. Обнулять таймер не обязательно. Когда буфер кончится - из лупа вывод.
Green, Вы не перепутали 5 мкс и 0.5 мкс?
Опять же, подсчет длительности Вы осуществляете аппаратным таймером, а не прерыванием либо основной программой.
Я ничего не перепутал.) У ТС минимальная длительность 0-го импульса 3 мкс. Я привёл пример его измерения с помощью INT0. При минимальном времени обработчика.
Если уж так хочется чего померить - пишем buf[i++] = TCNT2; именно в обработчике. Прерывания по изменению уровня. Обнулять таймер не обязательно. Когда буфер кончится - из лупа вывод.
Это просто пример. Но даже так всё работает.
Оттуда.
подскажите пожалуйста почему ардуино ide не содержит различных вспомогательных функций (того же автокомплита)? и есть ли какой нибудь более функциональный аналог для mac os? (типа phpstorm)
Оттуда.
Проблема в том, что через какой регистр производится обращение компилятор определяет сам и эта штука не постоянна.
подскажите пожалуйста почему ардуино ide не содержит различных вспомогательных функций (того же автокомплита)?
Интереснейший вопрос после 4-х лет на форуме. И в нужной теме.
представляю вариант кода (в виде картинки потому что комментарии сбиваются)
плохая идея читать что либо в прерывании, лучше так
представляю вариант кода (в виде картинки
Никогда так не делайте, если хотите, чтобы это кто-то читал
представляю вариант кода (в виде картинки потому что комментарии сбиваются)
потому что не надо пытаться запихнуть в комментарии "Войну и мир". Пишите коротко. Длина строки кода вместе с комментариями не должна превышать 80 символов, а лучше - если 50-60
Поправьте комментарии и вставьте код нормально.
плохая идея читать что либо в прерывании, лучше так
к сожалению не успевает так прочитаться
плохая идея читать что либо в прерывании, лучше так
Не смущай человека. Идея читать в прерывании верная. Только так можно мерить время точно. Почему - я выше писал. В прерывании можно все. Но быстро. И аккуратно. Могу показать много разного кода, где в прерывании чего только не делается. И запускается другое прерывание и даже сортировка списка. Не говоря уже о том чтоб таймер прочитать.
Не смущай человека. Идея читать в прерывании верная. Только так можно мерить время точно. Почему - я выше писал. В прерывании можно все. Но быстро. И аккуратно.
ну-ну... посмотрите на код ТС. "Быстро и аккуратно" - это про него, как думаете?
Не хочу подробно обсуждать, пока он код нормально не вставит, но ему явно не стоит говорить то, что вы выше написали. Он из того абзаца услышит только то, что ему удобно - мол, "в прерывании можно все"... и так и будет писать - всю программу в прерывание. как сейчас.
Нет, в прерывании, конечно, можно все. Только сперва надо выключить все прерывания, а у ТС как он включил в setup, так они и продолжают работать. А если продолжают работать, цикл while в этом случае категорически противопоказан.
Ну ту "картинку" действительно обсуждать не стоит. Но похоже она в любом случае завершится за 100-200мксек. Терпимо вполне. Особенно по сравнению, например, с софтовым UART. Работать будет (по крайней мере может работать при правильной реализации), остальному тоже мешать не будет. Меня больше смущает в таких случаях системные прерывания. Если они "тикнут" немного раньше чем прийдет старт - будет пропуск данных. Но это не часто, к счастью.
Ну ту "картинку" действительно обсуждать не стоит. Но похоже она в любом случае завершится за 100-200мксек. Терпимо вполне.
что-то я там вижу длительность на порядок больше... но может это потому. что картинка кривая :)
Пусть вставляет код нормально
Пусть вставляет код нормально
да.
не получается нифига
Ну а теперь выкиньте из прерывания все while.
Посмотри дизасемблированый код строки 15. Думаю удивит ;)
Параметры для _delay_us(...); ставь меньше расчетных. 1мксек - 16 тактов, грубо 10 процессорных команд. Потому сишные операторы сами по себе забирают время близкое к тем что требуются. Это надо учитывать.
Параметры для _delay_us(...); ставь меньше расчетных. 1мксек - 16 тактов, грубо 10 процессорных команд. Потому сишные операторы сами по себе забирают время близкое к тем что требуются. Это надо учитывать.
Расчетная - в смысле ту которую рассчитываем получить))
//рассчитывать нужно правильно
Сомневаюсь что автор такты считал. Иначе бы знал, что строка 15 скомпилируется в цикл, проходящий переменное кол-во раз. От 0 до 7. И длительность ее соответственно меняется очень заметно.
Кроме того, учитывая точность процесса, не стоит просто от стартового мерить. Лучше отслеживать фронты на каждом бите и по ним работать. Хотя это похоже пытается делать местами, например стр 12.
Ну а теперь выкиньте из прерывания все while.
пытаюсь понять как это сделать. как минимум одно там должно остаться
подумал логически - прерывание сработало, значит нам не нужно оно больше как минимум до тех пор пока мы не выясним идут ли за ним данные. потому я решил его просто отключить - cli()
теперь у меня все работает в цикле loop -
Ну а теперь выкиньте из прерывания все while.
пытаюсь понять как это сделать. как минимум одно там должно остаться
подумал логически - прерывание сработало, значит нам не нужно оно больше как минимум до тех пор пока мы не выясним идут ли за ним данные. потому я решил его просто отключить - cli()
теперь у меня все работает в цикле loop -
http://microsin.net/programming/avr/avr-gcc-atomically-and-non-atomically-executed-code-blocks.html