Вопрос на перспективу… Хотелось бы со временем перекатиться с ардуины на что-то поинтереснее. На данный момент ищу компактную плату разработки (не более 80х50 мм). От нее мне нужно:
3.3 логика
не менее 18 ШИМ для сервоприводов (можно с костылями)
не менее 1 i2c
любая беспроводная связь, позволяющая обмениваться двум таким МК данными напрямую
крайне желательно наличие встроенного BEC, поддерживающего до 12V входящего. Если сможет держать вдовесок мелкий монохромный oled дисплей, то совсем прекрасно.
желательна загрузка по USB, но могу и программатор приобрести
желательна поддержка arduino ide, но готов и в CubeIDE перекатиться, дело привычки
Вроде бы под пожелания подходит WeAct S3 Mini / LOLIN S3 Mini (обе на ESP32-S3), правда там, судя по всему, либо 3.3 либо 5 вольт надо подавать, но никак не 12. И с библиотекой Servo максимум 16 сервоприводов (думаю, на частоте 240 можно сделать блокирующий на 2.5мс вывод ШИМ на таймере, с достаточным разрешением, с пере-вызовом через 17,5мс). Может есть что-нибудь более подходящее под мои хотелки?
Скажите, а у вашей ШИМ , которая на 16 моторчиков подается, одна и та же частота, просто коэффициент заполнения (duty) разный или частоты тоже разные?
У ESP32S3 есть 8 каналов ШИМ, но только 4 таймера их обслуживают, так что не более 4 разных частот.
У ESP32S3, как ни странно, дела хуже обстоят с ШИМ, чем в оригинальном ESP32. У старичка 16 каналов ШИМ, у S3 - 8.
Если ваша библиотека как-то делает 16 приводов на S3, то скорее всего ее можно допилить (а может даже и не нужно), чтобы она делала 18 на ESP32.
Но это надо в код смотреть библиотеки.
Помимо модуля LEDC (который обычно все и используют для ШИМ), в ESPшке есть еще Motor Contol PWM. Отдельный шибко умный модуль, в котором можно более качественно ШИМ генерить. И по таймингам и по плавности переходных процессов.
Наверно, ESP32S3 не лучший выбор для 18 шим каналов. Т.е. сделать, конечно, можно. Но проще будет выбрать контроллер, в котором 18 каналов есть уже из коробки.
Если же все-таки возьметесь делать на ESP32, то берите именно его, а не S3. Там изначально 16 LEDC каналов
про 16 серво в стандартной библиотеке написано на сайте ардуино. Мне 18 нужно.
Я думал закостылить: запустить два таймера, таймер 1 чтобы на максимальной (спорно, еще не считал оптимальных значений) частоте работал и ничего не вызывал, таймер 2 чтобы на частоте цикла серво, и вызывал функцию, которая “повесит” контроллер на 2.5мс (максимальная длина импульса серво, таймер 1 должен переполняться как раз к этому времени в идеале). А в функции сделать repeat с условием выхода - достижением таймера 1 некоторого значения. И в этом цикле через порты поднимать/гасить каналы в зависимости от сравнения значения таймера 1 с значением ШИМ каждого из серво. На достаточно высокой частоте не должно быть заметно погрешностей из-за времени, затраченного на сами сравнения и записи в регистры портов. Главное чтобы частота таймера 2 была кратна частоте таймера 1.
Возможно очень дебильный план)))
Повторюсь, если есть более подходящая плата разработки - с радостью рассмотрю
На AVR у меня один 16битный таймер обслуживает 5 сервоприводов с разрешением 10 бит на любых пинах. Можно и 7-8. Думаю на ARM, учитывая частоты и количество таймеров, можно сделать ещё лучше.
Но, конечно же, лучше аппаратный расширитель. Оно проще.
трогал такие, было дело. Для сервоприводов плохой вариант. Чип задумывался как драйвер светодиодов, в связи с чем на 500-2500нс приходится слишком маленькое разрешение. Либо я не знаю о каких-то командах для его конфигурирования, тщетно искал инфу об этом.
Уххх как вы меня огорчили ))) Я уже купил себе такой расширитель… Лежит уже неделю и всё никак к нему не притронусь )))) По описанию прям вот ууууфффьььь. А вот по практике - будем посмотреть…
Зря я его посоветовал выше… Блин! Не испытанное устройство… Чисто теоретически (((
ну может для ваших задач он вполне сгодится. Когда надо было очень медленно сервами управлять я видел недостаточность разрешения (мелкие рывки), причем значительно большие, нежели я мог бы ожидать от “мертвой зоны” сервоприводов
Я очень хочу избежать заказа печатной платы и сборки из нескольких разных плат, т.е. очень был бы рад плате “всё в одном”, подходящей под мои нужды. Понимаю, что возможно это нереально
Ну это философский вопрос… Это очень реально, просто мы тут застряли в одной парадигме - ардуйня и им подобная ))))
Поясню… Ардуино - это по сути платформа для прототипирования. Взяли очень удобную Dev-Board привязали к ней очень удобные модули… Только по сути это прототип!!! Для промышленного изготовления надо выбросить более 50% того, что есть в обвязке всего этого, оптимизировать код, чтоб не было лишнего.
Так что на мой взгляд вы тут услышите советы именно по связке готовых модулей с готовым dev-board… И это не плохо! Когда этот прототип сработает, тогда вы сможете выбросить лишнее и связать это в конечный промышленный вариант.
Я видел недавно такую, небольшую, с дисплеем (480x???), CAN и RS485 Прям хоть бери целиком как есть и вставляй в свое транспортное средство (пусть удет яхта, например) как бортовой комп.
Хочу просто развить мысль, не подумайте, что я прям рьяно поспорить собираюсь))
На мой взгляд удобная плата разработки ну во-первых удобна для изготовления штучных хоббийных устройств. Но также подходит даже для мелкосерийных коммерческих проектов. Ведь для изготовления своей платы потребуется:
Разработка и производство штучных экземпляров, работа над ошибками и снова изготовление, пока не получится стабильный вариант.
Для производства потребуется оборудование. Собственное, либо заказ производства у того, кто обладает необходимым оборудованием.
Потребуется найти поставщиков компонентной базы, плюс логистика.
Получается, идти по этому пути нужно только в том случае, если это экономически обоснованно, т.е. дешевле, чем взять готовую плату, удовлетворяющую потребностям, если, конечно же, таковая существует
возник вопрос про двухядерность этих МК. Не понимаю, пока что, на каком именно уровне встроены эти ядра? Таймеры есть в каждом ядре, или общие? Как повлияет функция delay() или delayMicroseconds()? И как привязываются прерывания? В каждом можно свою функцию повесить, или что? Если есть ссылки на инфу - моё почтение тому, кто ткнет носом
Вообще не понимаю, как там тактирование и управление выводами работает. А если в одном потоке (на одном ядре) будет установка вывода в HIGH и так вот вдруг невероятно совпадет, что в другом потоке (на другом ядре) этот же вывод будет установлен в LOW прям в этот же момент. Что в регистре портов в итоге получится? У ядер есть очередность обращения к общим ресурсам?
Не надо путать ядро и периферию. Это независимые сущности, связанные только шиной передачи данных.
В тот же момент не получится. Именно в силу того что общение идёт по общей шине. Кто первый шину занял то подаст комаду. Второе ядро будет ждать пока шина не освободится. Так что одновременно ни как.
Ого вы вопрос подняли. Там миллион нюансов. Есть ситуации, например, когда лишь Core0 может кое-что делать.
Короткий ответ: не заморачивайтесь. ESP-IDF все сделает за вас. Вы можете указывать, на каком ядре запускать ваши задачи, если их несколько (xTaskCreatePinnedToCore() , если я правильно помню).
Касательно пина: записи в регистры - атомарные операции. Совсем Т.е. будет или результат от ядра0 или результат от ядра1. Результат, когда значение регистра испортится - невозможен.
Но вообще, для разрешения таких ситуаций используются обхекты синхронизации. Если у вас быстрые операции, то можно использовать критические секции (portENTER_CRITICAL / portEXIT_CRITICAL). А можно использовать и семафоры, но с нимим чуть больше накладных расходов и их нужно создавать. А критическую секцию можно просто объявить:
Эти функции всего лишь указывают FreeRTOS task scheduler, чтобы прекратил выполнение задачи на столько-то миллисекунд. Задача убирается из списка активных вот и все. Когда проходит указанное время, то задача возвращается в список активных. К ядрам это не имеет отношения.
Ребят, ну в целом вы ответили подробнейше на вопросы, стало яснее.
То есть, я же правильно понял, что у ESP32 там вообще своя ОС зашита, и она много с чем разбирается? А смогу я, скажем, на 1 ядро повесить протокол беспроводной связи и вычисление углов сервоприводов, а на второе - генерацию 18 ШИМ по прерываниям? Если второе ядро будет “ждать”, первое будет продолжать функционировать, читать/отправлять данные по воздуху и вычислять кинематику?