Pull to refresh

Comments 23

А это нормально для МК, измерять время количеством итераций цикла?
Казалось бы, если скомпилировать с другим уровнем оптимизации, результаты работы функции может непредсказуемо измениться.
Нормально. Вообще лучшем решением было бы использование прерывания по этому входу, или написать этот участок на ассемблере. Но даже так, оптимизатор не станет играться с кодом, где фигурируют внешние порты.
Наверное на хабре не хватает блога 'Ненормальная электроника'
Это распространенная практика. Раз уж мы используем хардварный хак вместо АЦП, почему бы не использовать такой метод. Тем более, что во многих контроллерах есть независимый счетчик (а иногда и больше), а частота кристалла стабилизирована кварцем.
А потом удивляемся, чегой-то спутники падают!
Объясните вот этот кусок кода пожалуйста:
while (PINA & 1){
t++;
if (t == 43) i++, t = 0; // константа 43 подобрана экспериментально
}

Почему нельзя сделать вот так:
while (PINA & 1); ?
Нужно не просто сделать паузу, а еще считать, сколько времени она длится. в переменной i накапливается количество итераций цикла (деленное на 43). A переменная t увеличивается на 1 каждую итерацию, и сбрасывается при t == 43.
Спасибо, был не внимательным =)
Опять же, если i может меняться от 0 до 255, почему бы не задать ему тип unsigned char. Ну и запретить сброс мк при переполненние.
Внутри цикла i может меняться в пределах от 40 до 255 + 40 (дале по коду i -= 40; и выравнивание в случае помех на краях). И более того, если если что-то с аппаратурой странное случится, например разряд будет идти дольше обычного, и после этого хотелось бы все-таки 255 увидеть, а не случайное значение из-за переполнения.
Расскажите про начальные условия, какой же это был резистор и как вы его подключали что бы получить 3 разряда «точности»?
ИМХО гораздо полезней пресекать такие ошибки на корню, чем огород городить.
Тут либо сопротивление так велико, что имеют место ЭМ наводки, либо не правильно использовался внутренний источник опорного напряжения, и как итог вместо сопротивления измерялся срачь по питанию…
Потенциометр на 50kОм, включен как делитель напряжения, пробовал и напрямую его подключить, и через эмиттерный повторитель, результат один и тот же. Это было не похоже на наводки. одно и тоже значение, на выходе держалось при большом диапазоне входного сигнала, а потом резкий скачек, примерно на 100 единиц из 256.
Вероятно Вы неверно настроили АЦП. Есть там флаг ADLAR, (хотя могу и соврать), отвечает за выравнивание результата левое/правое.
При левом выравнивании у нас будет 8-битная значащая часть в старшем регистре, а в младшем — 3 младших разрядов.
При правом выравнивании у нас 3 бита в старшем регистре (вот именно их вы и снимали), и 8 младших — в младшем.

Если я прав, то у вас эпический велосипед получился.
Забивание гвоздей микроскопом =).
И почему-же были сомнения в том что наистандартнейший метод двойного интегрирования может не заработать?

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

Что-же касается встроенного ADC, то обычно 7-8 бит из него удается извлечь без особых ухищрений при условии соблюдения основных правил разводки аналоговой части. Все они указаны в даташите в разделе ADC. Если-же плата уже готовая, то можно попытаться усреднить несколько значений. Ну и про реижм ADC Noise Reduction не нужно забывать.
Вообще, для этих целей лучше использовать микроконвертеры ADuC 845/847/848.
2 independent 24-bit ADCs on the ADuC845
Single 24-bit ADC on the ADuC847 and
single 16-bit ADC on the ADuC848
используем их для измерения как с термопар, так и с термосопротивлений с разрешающей способностью 1/32 градуса — показания стабильны.
Целевой приемник информации — контроллер ATmega32. Имеет встроенный АЦП, но выдаваемый им результат имел разрешение 2-3 бита, а остальные биты несли в себе мусор.

Вы что то сделали ОЧЕНЬ Сильно не так. Т.к. даже в худших условиях, что у меня были мусорными были максимум три младших бита из 10.
ну. Например AREF висящий в воздухе. Но чаще забытые конденсаторы по питанию. У меня почти стандартная ситуация: проверяю плату — сигнатура читается, прошиваю — ошибка. Причина: прошываю LPT программатором. на плате забыл конденсатор по питанию.
Вы действительно где-то ошиблись, если получили от АЦП такую низкую точность.
А в данной схеме нужно отметить, что емкость обычного конденсатора очень сильно зависит от температуры и при нагреве результаты измерения уплывут, нужно либо использовать конденсатор NP0 либо, например, заряжать через образцовый, термотабильный резистор и тоже измерять время заряда, и по нему корректировать результат.
а вот нифига. Не нужно точных конденсаторов и источников тока.
Потому метод двойного интегрирования и есть один из самых точных.
На самом деле нужно замерить время заряда и разделить его на время разряда.
при этом учитывается и температура при заряде-разряде и много чего еще.
все хорошо. корме возможности точно считать время.
Приведённая схема реализует «Интегрирующий АЦП» («АЦП последовательного счёта») — интегратор (RC цепь), компаратор (вход микроконтроллера) и счётное устройство (собственно программа). Поэтому "… без АЦП" в заголовке некоторое лукавство или, точнее, просто не соответствует истине. Про разновидности АЦП можно прочесть в Википедии.

«Неправильная» работа встроенного АЦП говорит скорее о схемотехнической ошибке либо об ошибке в реализации алгоритма опроса АЦП (нельзя так же исключать.

Но за изобретательность несомненно плюс =)
А почему вы уверены в этом самом «пороговом 1.4 В»? Обычно логика имеет зону логической 1, зону логического 0 и зону неопределенности внутри которой может происходить что угодно. Примерно как тут: www.interfacebus.com/Chart-of-Low-Voltage-IC-Switching.png
И 1.4 В на другом порту или на другом чипе/типе МК могут превратиться, например, в 0.9 В. Или у вас там какой-нибудь специализированный вход, для которого 1.4 и ни милливольтом больше?
>Целевой приемник информации — контроллер ATmega32. Имеет встроенный АЦП, но выдаваемый им результат имел разрешение 2-3 бита, а остальные биты несли в себе мусор.

Для начала вопрос на засыпку: а у вас в схеме аналоговые и цифровая земля правильно развязаны?

А вообще хочу вас предупредить на будущее: для высокоточных измерений на мегах требуется внешний источник опорного напряжения. Мне ленно открывать даташит, но в последних его версиях явно указано что опорное напряжение не константа, и является диапазоном. При этом не указано от каких факторов этот диапазон зависит. Faceplam в общем. Обратить на это внимание прошу поскольку имеется свой, и не только свой, «положительный» опыт :)

И ещё пара моментов для размышлений:
>>Транзистор в схеме применяется для того, что бы напряжение, до которого зарядится конденсатор не зависело от текущего положения потенциометра.

а компенсацию параметров транзистора, впрочем и остальных компонентов, включая контроллер, в зависимости, к примеру, от температуры вы как компенсировать собираетесь? Пороговые напряжения ведь плавать будут в зависимости от напряжения питания (температуры, влажности, старения компонентов), ведь сопротивление логических входов высокоомное,… это уж если рассуждать в рамках аналоговой электроники и рассматривать логический вход как аналоговый. А вообще описанное вами решение потенциально нестабильно в перспективе, при том уже в ближайшей перспективе.
В общем +1 к комментарию nerudo, в котором он совершенно верно написал, о том, что порог перехода 0 1 — логический, но не в коем случае не аналоговый, и пороговые напряжения никто не гарантирует с какой либо пригодной, для подобных измерений, точностью.
Sign up to leave a comment.

Articles