ArduinoMEGA: 64 цифровых входа вызывают случайные значения digitalRead
У меня есть 64 датчика Холла (датчики магнитного поля) (DRV5023AJQLPG). ), подключенный к Arduino MEGA 2560. Для этого я использую 48 цифровых контактов и 16 аналоговых контактов в качестве цифровых входных контактов. Программа в Arduino непрерывно считывает эти 64 цифровых входных контакта (в цикле for) и отправляет последовательный байт на ноутбук через USB-кабель всякий раз, когда один из этих входных контактов изменяется между НИЗКИМ и ВЫСОКИМ. Я также использую внутренние подтягивающие резисторы ATmega2560, чтобы предотвратить неправильные показания входных контактов, когда датчик не выдает на выходе 0 В (т. е. когда он не измеряет достаточно сильное магнитное поле).
Все работает нормально, когда я физически подключаю только до 16 датчиков. Затем ноутбук получает только те байты, которые правильно определяют, когда датчик измеряет изменение состояния.
Однако, когда я начинаю подключать больше из этих 64 датчиков, ноутбук начинает получать нерегулярные потоки байтов, ошибочно предполагая, что все подключенные датчики измеряют изменяющиеся магнитные поля (ВЫСОКИЕ и НИЗКИЕ показания).
Я могу назвать две причины таких нерегулярных показаний: 1. Либо внутренние подтягивающие резисторы ATmeag2560 не работают должным образом. 2. Или плата Arduino и >16 датчиков Холла вместе потребляют слишком много тока.
Подтягивающие резисторы не работают? При тестировании только с 16 подключенными датчиками это стабильная, правильно работающая установка. Когда я явно не использую подтягивающие резисторы в программе, настройка действительно начинает вести себя ненормально, также с 16 датчиками. Таким образом, кажется, что внутренние подтягивающие резисторы правильно активированы программой.
Датчики Arduino + 64 потребляют много тока? Помимо питания платы Arduino и датчиков через USB-кабель (обеспечивающий 500 мА), я также пробовал внешние источники питания, обеспечивающие 1 или 2 А. Я также запитал плату Arduino через внешний регулятор напряжения 5 В, +1 А, минуя встроенный регулятор напряжения Arduino. Все это, похоже, не влияет на нерегулярное поведение системы. При измерении текущего использования этой установки (с помощью амперметра) оно не превышало 250 мА.
Рассчитав комбинированное текущее потребление (используя данные таблицы), я пришел к следующему:
- sensor operating current: 2,7 mA
- sensor output current when in ‘active’ state: 0,25 mA
- TOTAL current of 64 sensors (3mA*64=) 192 mA
- Arduino MEGA current (approx) 150 mA
- TOTAL current of 64 sensors + Arduino MEGA: **342 mA**
Таким образом, как расчетное, так и измеренное потребление тока находятся в пределах того, что могут выдержать упомянутые источники питания.
Я немного застрял. Может ли кто-нибудь предложить что-нибудь, что может вызвать эту проблему? Или указать на неправильное мышление обо мне? Спасибо за любые ответы.
«Схема» (показаны только первые 8 подключенных датчиков. ArduinoMEGA подключена к компьютеру через USB-кабель с отключенной линией питания):
Верхняя сторона: датчики Холла и шины Vcc и GND:
Нижняя сторона: ArduinoMEGA + 64 красных выходных линии датчика к входным контактам:
Ниже приведен код Arduino:
/*
Протокол Arduino к Pd
Размещение или удаление шахматной фигуры отправляет только один байт.
Никакие другие серийные данные не передаются.
событие: значение байта:
размещение шахматной фигуры на поле: 0-63
удаление шахматной фигуры с поля: 64-127
Отображение вывода ArduinoMEGA в значение байта:
byte pin
0 6
1 7
2 8
3 9
…
46 52
47 53
48 A0 (analog 0)
49 A1
50 A2
…
62 A14
63 A15
*/
byte prevSquares[64]; // массив, содержащий предыдущие показания
byte i; // переменная, используемая в циклах for
byte sensorValue; // переменная временная память digitalread
void setup() {
Serial.begin(9600);
for (i = 0; i < 64 ; i++) {
pinMode(i+6, INPUT_PULLUP); // активируем подтягивающий резистор
}
for (i = 0; i < 64 ; i++) {
prevSquares[i] = digitalRead(i+6);
}
}
void loop() {
for (i = 0; i < 64 ; i++) {
sensorValue = digitalRead(i+6);
if (sensorValue != prevSquares[i]) {
// шахматная фигура была поставлена или снята с поля
if (sensorValue == 0) {
// шахматная фигура была поставлена
// отправляем серийный байт (0-63):
Serial.write(i);
}
else {
// шахматная фигура удалена
// отправляем серийный байт (64-127):
Serial.write(i + 64);
}
//обновляем массив prevSquares:
prevSquares[i] = sensorValue;
}
}
}
@Edo Paulus, 👍5
Обсуждение1 ответ
Лучший ответ:
Увидев вашу схему, я думаю, что общая проблема здесь заключается в том, что вам нужно более внимательно прочитать и следовать техническому описанию для этой части. Во многих случаях, когда вы ковыляете проект вместе в небольшом масштабе, есть много вещей, которые вы можете игнорировать и сойти с рук, но по мере увеличения масштаба все закругленные углы начинают складываться. В этом случае вам может сойти с рук 16, но как только вы начнете добавлять слишком много, их станет слишком много. Давайте рассмотрим несколько:
Подтягивающие резисторы
Как я упоминал в комментариях, полагаться на внутренние подтягивания, вероятно, не очень хорошая идея. По моему личному опыту, они хороши только для добавления кнопки быстрого ввода в целях отладки. Я не уверен конкретно, что может вызвать проблемы только после 16 датчиков. Возможно, в совокупности внутренние подтяжки имеют другой и более низкий предел тока, но я недостаточно знаком с внутренней архитектурой ATMega2560, чтобы делать больше, чем просто строить предположения.
В любом случае лучше всего использовать отдельные внешние подтягивающие резисторы в соответствии со спецификациями, указанными в техническом описании. (См. уравнение 1 на стр. 13 таблицы данных.)
Развязывающий конденсатор
Согласно техническому описанию, стр. 17:
Керамический конденсатор емкостью 0,01 мкФ (минимум), рассчитанный на VCC, должен быть размещен как можно ближе к устройству DRV5023.
Этот конденсатор обозначен как C1 на рисунках в техническом описании и является обязательным. Этот тип конденсатора называется развязывающим конденсатором, и одна из функций, которые он выполняет, — это локальное накопление энергии, поэтому, когда датчик начинает потреблять небольшой дополнительный ток, ему не нужно ждать, пока среагирует регулятор, а наоборот. уже имеет некоторую локальную энергию.
В вашей схеме указан один конденсатор емкостью 1 мкФ на выходе регулятора напряжения, однако конденсаторы для датчиков отсутствуют. Один конденсатор предназначен только для фильтрации выходного сигнала регулятора и не удовлетворяет требованиям развязки датчика.
Фильтрующий конденсатор
Обозначаемый в техническом описании как C2, это дополнительный конденсатор для фильтрации высокочастотного шума. В большинстве случаев это не требуется, согласно техническому описанию, стр. 13:
В большинстве приложений этот фильтрующий конденсатор C2 не требуется.
Однако ваш проект может не подпадать под "большинство приложений", и есть несколько моментов, которые меня особенно беспокоят.
- У вас есть длинные провода, которые в основном действуют как антенны, улавливающие любой ближайший шум.
- У вас есть длинные линии электропередач, идущие параллельно вашим сигнальным линиям, которые могут вызвать паразитную индуктивность, что приводит к другим интересным вещам. (Учитывая толщину разделяющей их фанеры, это может не быть проблемой, но об этом следует знать).
Я бы определенно попробовал первые две идеи, приведенные выше, и использовал бы их только в крайнем случае. Единственный способ узнать наверняка, нужно ли вам это, — подключить осциллограф к линии и посмотреть, насколько он шумный, но это не то, что у вас, вероятно, есть под рукой.
Другие проблемы
Меня просто немного беспокоит падение напряжения. В зависимости от сечения используемого провода, когда все датчики подключены, на конце жилы может возникнуть незначительное падение напряжения.
При таком количестве проводов, идущих вместе к Mega, могут возникнуть проблемы с перекрестными помехами.
Еще одна распространенная проблема при масштабировании заключается в том, что существует более высокая вероятность наличия неисправных компонентов. Это особенно касается этой части, которая, согласно техническому описанию, особенно чувствительна к электростатическому разряду. Возможно, есть мертвый датчик, который вышел из строя таким образом, что вызывает проблемы для других датчиков. Может быть, пройти и протестировать все 64 датчика, по 8–16 за раз, чтобы убедиться, что все они работают по отдельности и что проблема возникает только тогда, когда все они подключены.
Другие идеи
Во многих других комментариях по этому вопросу предлагалось использовать мультиплексор и/или мультиплексирование, и я кратко повторю это здесь. Мультиплексоры обычно используются в ситуациях, когда у вас недостаточно контактов, и вы хотите разделить один контакт на несколько других контактов. Хотя с Mega это не проблема (похоже, у вас достаточно контактов, чтобы делать то, что вы хотите сделать), есть и другие преимущества, которые можно извлечь из этого мультиплексирования.
Например, вы можете разделить плату на 8 частей 2 x 4, а затем использовать мультиплексор (например, 4051 или 74151), локальный для каждой части. Тогда у вас будет всего 8 коротких проводов, идущих к мультиплексору, в отличие от длинных антенноподобных проводов, идущих к Mega. Это может улучшить общую целостность сигнала.
Спасибо за все эти развернутые ответы! Я только что попытался добавить внешние подтягивающие резисторы (22 кОм), но это не сделало систему стабильной. Теперь я попробую добавить эти развязывающие конденсаторы. Я думаю об использовании 0,01 мкФ (с допуском ± 20%), или лучше использовать 0,1 мкФ? Если и это не сработает, я воспользуюсь мультиплексированием. У меня есть пара [расширителей ввода-вывода](http://nl.farnell.com/microchip/mcp23017-e-sp/ic-io-expander-16bit-i2c-28dip/dp/1332088 ) под рукой со связью I2C. Или лучше 401 5s? (Тогда я, вероятно, также могу заменить MEGA на обычный Arduino UNO), @Edo Paulus
И да, я проверил все датчики отдельно, и они работают нормально. Да и осциллографа под рукой нет., @Edo Paulus
Добавление развязывающих колпачков сделало его стабильным! На данный момент я просто добавил один керамический колпачок 0,1 мкФ на ряд из 8 датчиков, чтобы проверить это. Кажется, это работает. Позже я, вероятно, куплю и добавлю крышку 0,01 мкФ для каждого датчика. Кроме того, я еще раз перепроверю внутренние и внешние подтягивания. Спасибо, Джейк, а также спасибо @gerben., @Edo Paulus
- Что выбрать между датчиками температуры и влажности: AM230x или DHT22?
- Взаимодействие с датчиком SSI?
- Объединение кода для нескольких датчиков в одной программе
- Датчик PIR и сон (прерывание) на Mega2560
- Как подключить 2 датчика FSR к Arduino Mega?
- Использует ли подтягивающий резистор меньше энергии батареи, чем подтягивающий резистор?
- Как сканировать сигнал HIGH на digitalRead во время основного цикла, одновременно выполняя другие задачи?
- ШИМ-сигнализация с Arduino: для чего использовать землю?
Лично я считаю, что 64 датчика - это пустая трата места... Вы можете подключить их в 8 рядов по 8 датчиков, включить один ряд и затем прочитать его, а затем перейти к следующему. В любом случае, что такое поток ошибок? все высокие, все низкие, постоянно меняются? И это происходит со всеми контактами или только с некоторыми из них?, @frarugi87
Поток состоит из взлетов и падений, непрерывного изменения. Это происходит в любой момент, скажем, на половине всех контактов или больше, но *какие контакты* со временем меняются. Поток *действительно* выглядит так, как будто подтягивающие резисторы не используются. (Кстати: датчики запитаны (соединения: земля, Vcc, выход) и имеют внутреннее состояние. Использование матрицы 8x8 будет постоянно включать/выключать их, и они потеряют свое внутреннее состояние.), @Edo Paulus
Тогда я бы использовал несколько мультиплексоров... Или 16-битные расширители портов.. Потому что лично мне не нравится заполнять выводы платы датчиками, иначе вы не сможете добавить что-то еще.. В любом случае... Вы сделали все пробует с той же прошивкой (поэтому компиляция для 64 датчиков даже при использовании 16 из них)? Вы подключали новые датчики при выключенной плате или нет? Судя по техническому описанию, atmega должна выдерживать токи до 200 мА, а ваша схема потребляет примерно 50 мА для UC и 16 мА для подтягиваний, так что все должно быть в порядке., @frarugi87
Да, я провел все тесты с программным обеспечением, считывающим все 64 входных контакта, даже когда было подключено меньше датчиков. Я (не) активировал датчики, (отключив) заземление этих датчиков, в то время как плата Arduino оставалась под напряжением. Для ясности: датчики *не* питаются через контакты atmega, а получают питание от земли платы arduinoMEGA и контактов 5v (то есть от встроенного регулятора напряжения), и я также проверил его с внешним + регулятор напряжения 1А)., @Edo Paulus
Вы пытались оставить все 64 датчика включенными и (не)активировать их все, (отключив) подключение сигнального провода вместо провода заземления?, @frarugi87
Я *просто* сделал это. Это дает аналогичный результат, за исключением того, что он становится нестабильным уже при подключении> 8 датчиков., @Edo Paulus
Пробовали ли вы фактически измерять текущее использование, а не только вычислять? Попробуйте добавить несколько конденсаторов к источнику напряжения рядом с датчиками, так как здесь могут быть проблемы с шумом. PS вы можете мультиплексировать только выходные контакты, чтобы датчики оставались включенными. Включите внешние подтягивания в одной строке, а затем прочитайте все столбцы. Подобно тому, как клавиатура мультиплексируется., @Gerben
Как и большинство 8-битных процессоров AVR, ATmega2560 имеет ограничение по току в 200 мА, поэтому, пока датчики подключены непосредственно к *микроконтроллеру*, это не поможет вам увеличить мощность *платы*., @microtherion
Как физически устроены все эти датчики? Как они связаны? Присутствует ли макетная плата? (Просто думаю о шуме и перекрестных помехах). Кроме того, глядя на техническое описание датчика, в нем указана подтяжка 10K, однако внутренние подтяжки AVR обычно находятся в диапазоне 30–60K, что может быть слишком мало и вызывать медленную работу. времена подъема., @Jake C
На самом деле это немного больше нюансов, чем резистор 10 кОм, допустимый диапазон зависит от напряжения питания, см. уравнение 3 на странице 16 http://www.farnell.com/datasheets/1888830.pdf, а затем в зависимости от значения вы выбираете для резистора, вы вычисляете значение для конденсатора. В любом случае было бы полезно, если бы вы могли поделиться своей схемой и значениями конденсатора, просто чтобы убедиться, что он настроен правильно., @Jake C
В любом случае, может быть лучше просто прекратить использование внутренних подтягивающих резисторов, поскольку резистор используется как часть фильтра нижних частот. Используя внутренние подтяжки, вы ставите всю производительность фильтра на точность этого значения сопротивления, которое не является особенно точным или стабильным., @Jake C
Недавно я тестировал кое-что еще (старый телефон) и обнаружил, что внутренних подтягиваний недостаточно для надежной работы. Подключение 64 из них может быть проблемой (хотя вы можете получить несколько массивов резисторов). Как насчет использования некоторых [аналоговых мультиплексоров](http://www.gammon.com.au/forum/?id=11976)?, @Nick Gammon
Вы пытались развязать блок питания с помощью керамики 0,1 мкФ и электролита 100+ мкФ?, @Avamander
@EdoPaulus, это действительно странно .. Еще один тест, который вы можете сделать, - это фактически измерить то, что находится на штыре: таким образом вы можете понять, является ли это ошибкой датчиков или ошибкой UC. Тем более хотя бы в качестве теста можно попробовать отделить питание uC от датчиков. Или разместите датчики в группах по 8, например, и разделите питание (например, поставьте диод (анод +5В или лучше выше, катод Vcc группы датчиков) и конденсатор (между Vcc группы датчиков и земля) в диапазоне 10-100мкФ., @frarugi87
Спасибо за все предложения. Добавил фото и схему установки. Мой следующий план — добавить внешние подтягивающие резисторы ко всем входам и не использовать внутренние подтягивающие резисторы. Для значения резисторов я буду использовать уравнение, упомянутое @jake-c (уравнение 3 на странице 16 [ссылка](farnell.com/datasheets/1888830.pdf)), @Edo Paulus
@Gerben Мне любопытно, однако: как мультиплексировать выходные контакты, сохраняя при этом питание датчиков? Я читал немного больше о мультиплексировании, но мультиплексирование клавиатуры, похоже, включает только мгновенные кнопки и диоды, без постоянного питания ИС для каждого датчика. Может быть, есть ссылка, которая дает больше информации об этом? ты., @Edo Paulus
@EdoPaulus Взгляните на [эту схему, которую я собрал вместе](http://i.stack.imgur.com/7jM2q.png). Вы включаете подтягивание только для одной строки за раз. Вы добавляете диоды, чтобы предотвратить соединение рядов вместе. Из-за диодов вам нужен подтягивающий резистор на столбцах, чтобы получить сильный НИЗКИЙ сигнал. Убедитесь, что резисторы R7-9 имеют большее значение, чем подтягивающие резисторы., @Gerben
Возможно, вам придется установить резистор 10 кОм между сигналом и землей датчика Холла, чтобы избежать электрических помех. С уважением, Гийом, @Guillaume