конвертер MAX485 подключение
- Войдите на сайт для отправки комментариев
Здравствуйте все !
Мною изготовлено 5 плат, на которых установлены Ардуино МЕГА 2560 и купленные конвертеры RS485 <-> TTL. выполненные на МАХ485. Необходимо подключить их по сети RS485 к ПК для передачи данных. При подключении 2-х плат проблем не было, данные принимались по запросу с ПК с адресом нужной платы. При подключении 3-х плат данные передавались не устойчиво, а при подключении 5-и вообще платы не отвечали на запросы, хотя по этому интерфейсу можно подключать до 32 модулей.
Посмотрев данные на модуль конвертера RS485 <-> TTL ни каких противопоказаний я не увидел. В инете приведены примеры подключений только 3-х подобных модулей, а большего количества я не нашел.
Когда я нашел принципиальную схему конвертера RS485 <-> TTL, выполненную на МАХ485, то увидел что в них уже подключены резисторы в 120 ом между проводами (А и В). Поэтому у меня появилось сомнения в правильности подключения модулей. Как я читал об интерфейсе RS485 должно быть только два резистора по 120 ом на входе линии и на выходе, а при объединении модулей RS485 <-> TTL в сеть их получалось 5 и эквивалентное сопротивление получалось 24 ома вместо 60. В модулях нет переключателей отключающих эти резисторы.
Вопрос: правильно ли я посчитал и что эти модули нельзя объединять в сеть более 2-х ?
В модулях нет переключателей отключающих эти резисторы.
странно, вроде раньше были перемычки.
Тогдая вижу один путь - выпаять резисторы с двух или трех модулей
b707:
мысли мои правильные ?
Все верно. Лишние резисторы уберите. Это именно они мешают. Я с этим тоже сталкивался.
Здравствуйте FoxJone !
Еще вопрос: что может быть если при приеме данных ПК по RS485 от Ардуино 1 включаю питания Ардуино 2 и связь ПК по RS485 с Ардуино 1 нарушается ?
С уважением Геннадий.
Не сталкивался с таким, но думаю что при включении идет какой то мусор по линии и каким то образом блокирует дальнейший прием. Без кода не понятно, что происходит.
Просниффьте линию и посмотрите что происходит.
Я извиняюсь, за то что не указал существенную поправку просто забыл - Ардуино 2 не подключен к сети RS485, подключен только один Ардуино 1. Я думаю, что это может быть из-за того, что они поключены к одному источнику питания +12 в (ОВЕН БП30Б-Д3-12) и может быть проскакивает помеха потому что нет никакой фильтрации, а модуль преобразования RS485 - TTL подключен к 5 в от Ардуино?
Стабилизатор с обвязкой на Arduino вполне себе фильтрация, полагаю.
Ну раз так, то однозначно питание.
Вообще, я никогда и ничего не питаю от ардуин, питание всех компонентов идет от БП. На такой случай у меня на столе стоит 5-вольтовый БП на 200 ватт, от которого куча выводов со всякими разными разъемами.
У меня все Ардуино (5 штук) в цехе, расстояние между приборами по разному, от 3 метров до 6, от последнего прибора до ПК длина линии примерно 10 - 15 метров. Запросы посылает ПК и ждет ответа 10 секунд, затем запрос следующему. Скорость по сети 19200. Схемы приборов абсолютно одинаковые. Ставить БП на каждый прибор руководство посчитало неэкономично и поэтому все запитаны от одного БП с выходным током 2.5 А.
Ставить БП на каждый прибор руководство посчитало неэкономично и поэтому все запитаны от одного БП с выходным током 2.5 А.
Купите 5 зарядок телефонных и от них питайте. 1А на один комплект - за глаза. Цена вопроса - 500 рублей за все 5 штук, дешевле, чем ваш БП на 12.
Я для одного завода делал контроллеры, так и поступил (там 4 комплекта было). Единственно, я зарядки из корпуса вынул и в коробку с контроллером определил.
А насколько проседают ваши 12 вольт на 15 метрах - один Ом ведает...
Ставить БП на каждый прибор руководство посчитало неэкономично и поэтому все запитаны от одного БП с выходным током 2.5 А.
Повесте ферритовые кольца на провода питания возле каждой Ардуины.
Вот нашел образовательное видео по этому поводу - https://youtu.be/7Ou7RTLV3fQ
Здравствуйте все !
Спасибо за советы.
Долго не писал, проводил эксперименты. Выпаял резисторы и тогда исчезли проблемы с питанием - включение или выключение любого прибора не влияет на считывание другого. Но осталась проблема: к сети RS485 подключил два прибора. Из програмы на компьютере (ПК) запускаю цикл опроса этих приборов, причем программа позволяет посылать запросы поочереди на каждый прибор или выборочно. Если запросы посылаются на любой из приборов, а другой в это время в программе на ПК отключен, то все работает - ответ от прибора идет. Если в программе на ПК разрешено посылать запросы на оба прибора, то отвечает только один. Если в программе на ПК запрещаю посылать запрос на прибор, который отвечал, то прибор, который не отвечал дает ответ.
В чем дело не могу понять - программы на обоих приборах одна и таже. Определение прибором своего адреса, для ответа, проходит нормально.
Еще момент - при скорости обмена 9600 перестают отвечать оба прибора даже в одиночку. Работают на скорости 19200. Пробовал скорость 38400, работают как на скорости 19200.
Не понимаю в чем дело ?
Подскажите, пожалуйста, что делать, какие эксперименты еще провести ?
Я так думаю, что виновата программа на компьютере. Или прошивка на контроллере. Или оба. Тут нужен медиум и хрустальный шар, иначе нипочем не разобраться...
Когда один прибор отвечает, а другой нет, я на монитор Ардуино прибора, который не отвечал, выводил то, что он принимает и что передает. Получилось что запрос от ПК прибор не видит и соответственно не отвечает ? Почему этот же запрос прибор видит когда остается один в сети не понимаю ?
Думаю, что я понял в чем дело, но не уверен и поэтому делюсь мыслями.
При приеме данных в Ардуино у меня анализируется первые 3 байта на адрес и если он совпадает, то прибор отвечает. Но ответ первого прибора также поступает и на второй прибор. Второй прибор анализирует 3 байта, видит, что это не адрес и ждет следующих данных. При этом не дочитанные данные полученные вторым прибором при ответе первым остаются в буфере. Запрос для второго прибора от ПК пишется в конец буфера приема и второй прибор анализирует первые 3 байта не дочитанных данных - естественно никакого адреса.
Это повторяется в каждом цикле. Как Вы считаете есть в моих рассуждениях здравое зерно ?
И подскажите как можно очистить буфер приема ?
Каков формат пакета (полностью)?
Команда запроса с ПК: M01 где: М - признак модуль, 01 - адрес модуля
Ответ Ардуино для ПК: М1, 100, 395 где: М1 - модуль и его номер, 100, 395 - целочисленные данные по 4 символа, разделитель запятая.
Команда запроса с ПК: M01 где: М - признак модуль, 01 - адрес модуля
Ответ Ардуино для ПК: М1, 100, 395 где: М1 - модуль и его номер, 100, 395 - целочисленные данные по 4 символа, разделитель запятая.
Я правильно понял, что вы там что то в ASCII читаете? Вы про байты слышали вообще?
Лично я бы ответ слал вот так: AE 01 20 0F 14 22 44. Что означает: AE - признак начала посылки (можете выбрать любой по вкусу) 01 - номер модуля, 20 0F - число 1 (8207 в данном случае), 14 22 - число 2 (5154), 44 - CRC8 (в данном случае простая байтовая сумма всей посылки начиная с 01 и заканчивая 22) и если CRC не совпадет, то посылка просто откидывается, как ошибочная.
А буфер приема не надо чистить, его надо вычитывать и анализировать. Можно вообще посмотреть что там и как в приборе принимает то?
В целом согласен с FoxJone, имею одно замечание - префикс пакета выбирается таким, чтобы он никогда не встречался в данных.
https://www.gammon.com.au/forum/?id=11428 -> "Error checking protocol"
В целом согласен с FoxJone, имею одно замечание - префикс пакета выбирается таким, чтобы он никогда не встречался в данных.
Если вы шлете числовые данные размером больше 254 (а обычно это так и бывает, если это не команды типа вкл/выкл), то это нереально. Поэтому проверяешь начало пакета. Если начало совпало с префиксом - то пакет пошел дальше в буфер. По окончанию пакета проверяешь контрольную сумму - если совпало, то весь пакет из буфера на расшифровку. Я таким образом даже модбас читал - лень было библиотеки модбаса искать и разбираться, оказалось проще самому написать.
Опять же никто не мешает сделать префикс из двух-трех байт, которые уже ТОЧНО не появятся в посылке вместе.
АА 55 АДРЕС_ОТПР АДРЕС_ПОЛ ДЛИНА_ПАКЕТА САМПАКЕТЛЮБОЙДЛИНЫ КС
Здравствуйте все !
Проблема решена ! Как я выше писал о получении ответа 1-го прибора вторым, так оно и получилось. Запрос от ПК для второго прибора записывался в конец сообщения первого. Я сделал очистку буфера приема, но это не помогло, запрос все равно дописывался в конец, поэтом у я подумал, что наверно очистка буфера не успевает закончится и сделал задержку 1000 мсек на посылку запроса для второго прибора с ПК. Все заработало, я уменьшал эту задержку до 250 мсек, при этом проблема стала снова возникать. Я увеличил задержку в два раза и все работает.
Большое спасибо всем за советы.
Ну понятно, как и предполагалось. Был неправильно организован обмен данными.
Он и сейчас неправильно организован, просто с костылями заработал. Буфер приема нельзя очищать! В нем может быть что то полезное. Его надо вычитывать, анализировать и лишь потом отбрасывать ненужное.
берём нормальный протокол ICOM CI-V и будет счастье
Здравствуйте !
Я с Вами согласен, что обмен организован криво, но в данном конкретном случае буфер приема чистится потому, что я точно знаю, что в нем должно быть - всего 4 символа. Все остальное, что может прийти, не нужно и анализ проводить ни к чему, удалить и все.
Еще раз благодарю за советы.
Поискал, нашёл у себя код для обмена по UARTу. Положу сюда, вдруг кто поиском наткнётся на эту тему, мож пригодится кому.
состав пакета:
0хАА / 0х55 / размер пакета / сам пакет (payload) / контрольная сумма(простое сложение)
там функции как запаковки так и распаковки.
Правильно ли я понимаю, что вместо элементов массива ставить напрямую нужные цифры нельзя?
Правильно ли я понимаю, что вместо элементов массива ставить напрямую нужные цифры нельзя?
что мешает ставить нужные цифры в элементы массива?
Имеется в виду тип int. Т е предварительно нужно разложить а в приемнике собрать?
Я не совсем понимаю, что вы хотите. Опишите задачу подробнее. Откуда берутся "цифры", которые вы хотите передавать? Вы хотите их прямо в коде забить? Или это будут переменные в программе?
Как передать например цифру 785 чтобы вторая ардуинка поняла ее именно как 785?
Как передать например цифру 785 чтобы вторая ардуинка поняла ее именно как 785?
Есть цифры 7, 8 и 5.
Если хотите получить вменяемый ответ на свой вопрос, пользуйтесь общепринятой терминологией.
Можно ли передать число 785 или необходимо разбить на два?
хочу передать по НС-12 значения нескольких переменных. Передавал по одному - иногда теряются.
Можно ли передать число 785 или необходимо разбить на два?
На два чего?
Можно ли передать число 785 или необходимо разбить на два?
передача идёт по байтам по любому. А ваше число состоит из двух байт. Функция отправки из моего скетча #25 работает с массивом байт, соответственно ответ на ваш вопрос - да, нужно разбить число на массив из 2-х байт.
можно к скетчу дописать функции запаковки и распаковки int и пользоваться этим на приёмнике и передатчике. Примерно так (не претендую на красоту):
Макс, не нужна тут никакая функция упаковки. Переменная типа int лежит в памяти как два байта подряд, по сути это уже твой массив, который тебе нужен.
Так что в строчке 40 просто вызываешь
и никакая функция не нужна
я в этом плохо пока разбираюсь, полчаса пытался такую строчку написать, чтоб работала) спасибо.
А при приёме можно ли также в массиве byte указать для переменной int адрес например byte mess [3]. Чтобы подхватила два байта mess [3] и mess [4] ?
типа так, но естественно так не компилируется
А при приёме можно ли также в массиве byte указать для переменной int адрес например byte mess [3]. Чтобы подхватила два байта mess [3] и mess [4] ?
можно воспользоваться функцией memcpy()
благодарю за пример, почитаю про это.
типа так, но естественно так не компилируется
а что-то зря я сказал что нельзя - так тоже можно, только адрес третьего элемента массива это (mess +3) Вот так попробуй:
да, уже сам допер, что так тоже работает, я просто ступил, что байты старший с младшим в памяти наоборот сидят, поэтому думал что не работает.
поэтому получаемый массив должен быть такой
собственно при отправке по твоему варианту
sendMessage ((
byte
*) &Var,
sizeof
(
int
));
, он так и отправляетсяto Uragan. вот такой вариант тогда проще, без функций упаковки и распаковки переменной, см. внимательно комменты
Что делать с одним числом понятно, с массивом чисел не очень. Для начала попробую более понятным способОм разбирать число на два.
Что делать с одним числом понятно, с массивом чисел не очень. Для начала попробую более понятным способОм разбирать число на два.
Не надл ничего разбирать - все переменные в МК и без вашего разбора представляют из себя наборы байт. А лишний разбор на байты помешает вам работать с массивом.
Судя по вопросу, вы и с одним числом сути не вкурили. Вам надо разобраться, тогда сможете сами на массив расширить легко. Задавайте вопросы. что непонятно.
Например код из #38 будет работать с массивом проактически без правки
Я не часто программирую. Поэтому должно быть максимально понятно если придется вернуться к программе через год, другой. Все эти указатели, адреса для моего мозга сложно.
Если вручную раскладывать на байты - для массива будет просто куча никому не нужных действий.
Но впрочем как хотите.
чуть подправил код, может так понятнее будет как разные типы данных отправлять, там все просто. Вот на приемнике парсить немного сложнее, в коде только пример парсинга одиночной int.