При передаче пакета больше 32 байт (в моём случае 36 - 4 адресных диода ws2812b), если 1-ый бит 33 байта high "1", то после передачи всего пакета любых остальных данных шина остаётся в "1". Баг проявляется в независимости от использования DMA в режиме LSB first. Лечится установкой SPI_CR1_CPHA — Clock phase в "1" (вывод не используется) Revision ID: REV_ID 0x1001, В errdata об этом нет. На st меня забанили, да и сам бы забил, но вдруг это не баг конкретно этого чипа и кому то ещё поможет. Конфигурил через CMSIS, но как же без картинок :) ps в теории надо бы проверить 16 битный режим и MSB, но скорее всего это подвержено тоже, т.к. с них и начинал. Код перенёс с stm32f030 где всё работало, но с одним диодом (9 байт).
Будучи творческим человеком и техногиком, я обожаю при первой возможности апгрейдить своё оборудование. Время от времени я мониторю маркетплейсы в поисках чего-то новенького и в этот раз я наткнулся на настоящий мультитул для Embedded-разработчика — контроллер I2C/SPI/UART/JTAG в одной коробочке и всё это всего за 1.000 рублей... Конечно я не смог пройти мимо этой штучки и в рамках сегодняшней статьи хочу рассказать что оно из себя представляет и как с ним работать. Жду вас под катом!
❯ Что за устройство?
На самом деле такой формат статей для меня «в новинку», до этого я ни разу не делал обзоров на оборудование. Да и мой инструментарий слишком зауряден, чтобы делать ещё одну статью уровня «почему Quciko T12 лучше любой 900M станции» или «почему Вам не стоит покупать компрессорный люкей в 2025 году». Однако обзоров на сегодняшний гаджет я не нашёл, несмотря на его огромную пользу как для Embedded-разработчиков и инженеров, так и мастеров по ремонту смартфонов, планшетов и ноутбуков.
Во время подготовки статьи о том, как я написал BIOS для игровой консоли от Waveshare, в рекомендациях мне попадались другие товары от этого производителя — в том числе и сегодняшний гаджет. Меня сразу привлекла возможность переключения 3v3->5v логики и обширный набор поддерживаемых шин. В официальной вики были описаны следующие характеристики:
Шины: 1x SPI с двумя чип-селектами (можно подключить до двух устройств на одну шину), 1x I2C, 1x JTAG (полноценный, с ресетом!) и 2x UART с дополнительными линиями CTS/RTS для совместимости с классическими COM-портами.
Используемый контроллер: WCH CH347. Некоторым читателям чип может показаться знакомым по аналогии с классическим CH341A.
Питание: 5В, 3.3В, потребление ~65мА на VBus. Есть самовосстанавливающийся предохранитель на «входе».
Waveshare — достаточно известный бренд, под которым реализуются одноплатные компьютеры, «бутербродная» периферия для них и инструменты.
Я сразу смекнул, что смогу использовать гаджет как для восстановления программно-убитых устройств по типу КПК, так и для отладки своих собственных самоделок, благо набор шин к этому располагает. Устройство приехало ко мне примерно через месяц, в небольшом пакетике и брендовой коробочке, в которую входило само устройство, кабель USB Type-B (ну почему не Type-C?), Dupont-провода в IDC-коннекторе для всех шин, а также небольшой мануал. Нареканий к доставке кроме скорости не возникло.
Сам гаджет представляет из себя компактную металлическую коробочку с «ушками» для удобного крепления на столе или стене. Сверху расположена шпаргалка по распиновке и режимам работы CH347, а также светодиодные индикаторы для UART.
Разбирается гаджет очень просто: достаточно лишь открутить несколько винтов с обеих боковых пластин устройства и перед нами открывается вид на плату. Схемотехника здесь простейшая: самовосстанавливающийся предохранитель, линейный регулятор AMS1117, который питает контроллер и нагрузку на VCC (до ~600мА), сам CH347, а также набор ключей для согласования режимов работы. CH347 — это не просто ASIC, а вполне себе полноценный микроконтроллер, прошивку которого можно обновить, правда SDK для использования CH347 как МК производитель не предоставляет.
После подключения гаджет радостно зажег индикатор PWR, подтвердив свою работоспособность, а значит пришло время протестировать возможные варианты использования!
❯ UART
С UART всё просто и понятно: нам достаточно лишь выбрать желаемый режим работы (M0 — двухканальный UART, остальные режимы — UART + I2C/SPI или UART + JTAG) с помощью тумблера и подключить/припаять Dupont'ы к соответствующим пинам на плате. UART здесь достаточно быстрый: при двухканальном режиме работы, на UART0 можно добиться до 9Мб/с (мегабод), а на UART1 — до 7.5Мб/с.
Провода в разъёмы установлены не бездумно — у них есть цветовая маркировка и логика помимо «красный — VCC, чёрный — GND».
В качестве теста я решил снять лог загрузки со своего проекта самодельной игровой консоли. Для работы с UART я привык использовать Putty: сначала я припаял RX/TX и массу, затем запустил Putty и выбрал COM-порт, соответствующий первому каналу, установил бодрейт в 115200 и включил консоль:
Всё работает! В целом, гаджет можно использовать и для прошивки более сложных устройств: например многие смартфоны и кнопочные телефоны всё ещё имеют альтернативный режим прошивки через UART, а ретро-телефоны Samsung и LG так вообще не имеют альтернатив — если нет специального JIG, то остаётся лишь вызванивать RX/TX с разъёма и подпаиваться напрямую к UART процессора!
❯ SPI/I2C
С SPI и I2C уже всё чуточку интереснее. Дело в том, что как вы уже могли понять — чип использует свой собственный проприетарный протокол для организации моста между программой на ПК и шиной данных. Для работы с этим протоколом производитель предоставляет уже готовую библиотеку для Windows начиная с 2000, так что возможно у чипа есть перспективы для оживления легаси пром. оборудования. Для Linux же есть альтернативные драйвера, которые пробрасывают CH347 как обычные spidev и i2c-dev устройства.
Драйвер можно скачать здесь
Для проверки коммуникации можно использовать специальную тестовую программу из SDK, которая позволяет отправлять произвольные данные и даже прошивать флэшки 25 'ой и EEPROM'ки 24'ой серии.
Давайте же попробуем написать что-нибудь полезное! Например, подключим к гаджету 1.8-дюймовый дисплей и что-нибудь на него выведем.
С разводкой дисплея проблем не возникает: SDO к MOSI, SCK к CLK, VCC к VCC и BL (питание подсветки), однако для управления DBI-дисплеями необходимы ещё две дополнительные линии: D/C (линия, определяющая как интерпретировать байт на входе), а также RESET для аппаратного сброса контроллера. И с этим проблем тоже не возникает: у контроллера есть как минимум четыре свободных GPIO, два из которых мы с вами и будем использовать для управления линиями дисплея — GPIO6 (CTS на UART1) и GPIO7 (RTS на UART).
Далее я начал изучать PDF-ку с документацией сомнительного качества и писать код инициализации. Начинается всё с получения контекста устройства с помощью функции CH347OpenDevice, которая принимает в себя индекс нужного контроллера в системе и возвращает непонятный идентификатор (вероятно WinUSB?). Интересно то, что в остальном API используется не идентификатор, а как раз тот самый индекс, который в большинстве случаев будет 0. Далее мы получаем информацию об устройстве и сверяем режим работы, если он отличается от нужного — выбрасываем исключение:
/* Initialize CH347 */ deviceHandle = CH347OpenDevice(deviceIndex); if (!deviceHandle) thrownew std::runtime_error("Failed to open CH347 device");
Далее настраиваем SPI-контроллер. На выбор есть все три существующих режима, настройки полярности и возможность вручную дергать один из двух доступных ChipSelect'ов, а также тайминги. Частота работы определяется предустановленным набором делителей — 60МГц, 30МГц, 15МГц и т.п. Не забываем настроить таймаут каждой USB-транзакции:
if (!CH347SPI_Init(deviceIndex, &cfg)) thrownew std::runtime_error("Failed to initialize SPI");
И инициализируем дисплей. Здесь есть важный момент: функция CH347GPIO_Set устанавливает состояние всего GPIO-контроллера в чипе и поэтому принимает в себя три битовые маски с конфигурацией каждого пина. Функции GPIO стандартные — вход/выход, плюс обработка прерываний с помощью специального callback'а:
Теперь можно запустить программу и посмотреть на результат. Если вы увидели шум (или мусор) на экране — значит вы всё делаете правильно и контроллер успешно проинициализирован.
На фото можно заметить перемычку между CS и массой, однако не все контроллеры дисплеев толерантны к постоянному низкому уровню на CS. На моей практике контроллеры ILI отказывались проходить инициализацию, если не разграничивать каждую транзакцию с помощью CS.
Теперь можно что-нибудь вывести. Подготавливаем изображение, преобразовав в 16-битный массив пикселей, переводим контроллер в режим записи в VRAM, отправляем изображение:
Потенциальных применений у такого гаджета много: можно сделать красивые анимированные часы, мониторинг датчиков, показ уведомлений или дублировать окно с основного ПК. А ведь когда-то ради такого покупали LPT-провода, дисплеи от Сименсов и вручную превращали параллельную шину в последовательную...
❯ Заключение
Вот такой интересный гаджет выпустила компания Waveshare — и, что радует, по очень приятной цене! Ссылку по понятным причинам прилагать не буду, но при желании вы сможете его найти на всех трёх крупных маркетплейсах. Кроме того, можно купить Breakout-плату с тем же самым чипом за ~500 рублей, но там не будет таких удобных переключателей и Dupont'ов.
К сожалению, теста JTAG в статье не будет. У меня пока нет готовых к работе необычных гаджетов, где можно было бы протестировать OpenOCD... однако мой HTC Dream всё ещё ждёт свою прошивку модема!
А если вам интересна тематика ремонта, моддинга и программирования для гаджетов прошлых лет — подписывайтесь на мой Telegram-канал «Клуб фанатов балдежа», куда я выкладываю бэкстейджи статей, ссылки на новые статьи и видео, а также иногда выкладываю полезные посты и щитпостю. А ролики (не всегда дублирующие статьи) можно найти на моём YouTube канале.
Если вам понравилась статья...
И у вас появилось желание что-то мне задонатить (например прикольный гаджет) - пишите мне в телегу или в комментариях :) Без вашей помощи статьи бы не выходили! А ещё у меня есть Boosty.
Что думаете о таком преобразователе?
Что думаете об обзорах на оборудование? Есть смысл рассказывать о всяких ништяках, что я иногда покупаю для работы?
Запарился с одной задачей и, возможно, у кого-то был похожий опыт.
Суть: Нужно принимать данные по SPI в режиме Slave. Пробовал на Raspberry Pi 4 — но, как оказалось, его кристалл аппаратно не поддерживает SPI Slave, ну как, поддержка есть, но кривая и нестабильная (скорость должна быть 921600, не вытягивает она).
Нашёл альтернативу — процессор RK3576 (например, в Banana Pi BPI-M5). В даташите вроде как есть нормальная поддержка Slave, но есть нюансы:
Железо — платы на RK3576 стоят 15-20к, и просто так купить для теста не вариант.
Софт — драйверы и настройка SPI Slave, конечно, потребуют возни, но это уже второстепенно.
Вопрос: Может, у кого-то уже есть такая плата и возможность проверить SPI Slave? Или был опыт работы с этим процессором?
Буду рад любым советам, мануалам или даже "да, это реально, но нужно сделать то-то".
Вы чините ноутбуки? Если чините, то ваш мир уже не будет прежним. Погнали.
Hi-End programmers - Программаторы относятся к высшему классу, и приводить сравнение с ними некорректно. Добавлены для только фона и только в эту таблицу.
В 2024 году кроме нормального развития в программировании, (Где так и не закончена единственная задача! В виде стабильности сети.) Включая изучения распределённых файловых систем, работы с 3D в браузере.
Под его конец создано первое рабочее физическое устройство. Первой реализована одна из простых идей, всего которых уже не счесть.🫢
Пульт управления звуком, на основе ESP32 на C++.
Корпус спроектирован самостоятельно в FreeCad, многие элементы не имеют чертежа и нужно измерять самостоятельно штангенциркулем. И распечатан самостоятельно в FDM принтере.
Пока соединение по WIFI🛜 в мобильное приложение на смартфоне, принимающее команды. Но возможно использовать и Bluetooth.
Может регулировать громкость потенциометром, переключать треки вперёд назад 5 позиционной кнопкой. Считывая аналоговые и цифровые сигналы, и обмениваясь пакетами по UDP. Посылая медиа-сигналы в смартфон, который уже запускает музыку.
Имеет 2 экрана, I2C и SPI. Позволяющих выводить как ЧБ так и RGB изображения. Питается аккумулятором 18650.
За примерно 14 дней, в первую половину декабря. Не считая доставки.
В процессе был сожжён один DAC по неопытности.🥲 И несколько слабых блоков питания. Получен огромный опыт за короткое время.
Начальный этап в создании собственных аппаратных устройств, от мелочи для развлечения, умного дома и повышения удобства, до целевых промышленных устройств на массовое производство.
Наивный первый шаг к реализации идей мирового масштаба.
Пост не призывает к действию, все манипуляции проводите на свой страх и риск.
День 1
Был прекрасный тихий вечер.
На улице мороз -30, а я в теплом доме с кружкой чая.
Неожиданно приходит глупейшая мысль "А почему все обновляют биос, а я нет?"
Ну а что же, надо действовать! Опыт какой-никакой!
Качаю прошивку, (msi) завожу через M-Flash, игнорирую табличку "данная версия bios не предназначена для вашего устройства", я же лучше знаю.
Загружаем....иии....получаю кирпич весом в 20 кг.
Тут можно было бы и закончить, отнести в сервис, выслушать всяческие издевательства со стороны сотрудников СЦ, заплатить за восстановление bios, и жить себе спокойно. Но кучерявые волосы на голове нашептали быть в душе Евреем, а значит будем восстанавливать своими руками, но уже завтра.
День 2
Разбираем кирпич на части, смотрим:
Flash bios в данном случае это то, на котором желтая бумажка с надписью E7673IMS
Прикидываем варианты.
Чем шьют bios? SPI программатором.
Но дома только ST-link, USB - UART TTL преобразователь, и куча различных МК.
Черпаем информацию, ага, SPI программатор на Arduino! Где то у меня была одна реплика..
Берем ноутбук своей женщины
Качаем ПО, шьем МК, и подключаем.
В вышеуказанном посте Arduino pro mini, у меня же реплика Arduino nano, распиновка отличается.
+ я запитывал от стабилизатора на 3.3в(а не от 5в, как в посте)
Хотел еще сделать делитель напряжения для понижения логических уровней, но и так сойдет :)
Впаиваю огрызки витой пары напрямую в материнку к flash.
Итоговый результат:
Подключаем к ноутбуку, в программе выбираем размер flash(в моем случае 8192 кбайт), качаем на этот раз прошивку для МОЕГО bios, шьем 15 минут....
Пробный запуск....пост прошел!
Подключаем монитор и клавиатуру, повторяем, и...
Кирпич весом 20 кг снова становится рабочей машиной.
Эта история навевает воспоминаниями из детства. где подвигом было поменять настройки в bios, а о прошивке и речи не шло, так как все боялись случайного отключения эл.энергии
А сейчас можно убить, и без проблем восстановить bios, без "мам, пап и кредитов"
Это был мой первый опыт прошивки flash.
Спасибо за внимание, обсудить мою рукожопость можно в комментариях
P.S. Дамп старого биоса я снял перед тем, как всё умертвить, но цель была поставить именно новый
В кои то веки поборол лень и уговорил себя запилить пост про ремонт всякой залупы. На столе модные часики для спортсменов от гармин. Со слов владельца на ночь был запланирован апдейт, а на утро оказалась тыква
На включение и зарядку реакции нет. Разбираем. На АКБ 0. Следов воды, как это часто с ними бывает не оказалось. На контактах АКБ сопротивление в норме.
Пробуем заводить от ЛБП.
Картинка есть но на этом все.
Наученный опытом о бутлупе на часах и предистории клиента делаем вывод что проблема с ПО. Можно кончено постучать в бубен и попробовать прошить по USB но это отнюдь не всегда прокатывает и мне лень тратить время. Действуем более радикально. Будем прошивать SPI накопитель напрямую. Снимаем
Городим огород из проводов
И цепляем к программатору
Все никак руки не доходят вытравить платку под SPI флешки в BGA корпусе.. И так сойдет. Читаем флешку и вытягиваем ESN и серийник. Правим заведомо исправный дамп
Проливаем в новую флешку, на всякий случай, вдруг родной нездоровится. Накатываем шары и сажаем на место.
Часики бутнулись, Значит все путем и выводы сделаны верно
Собираем, тестим, отдаем клиенту. Такие дела. ЗЫ: да коврик грязный, надо бы протереть
Только 3 дня назад воспользовался сам этим проектом, думаю кому-то окажется полезным.
Успешно зашил 10 штук 25х флешей (2-2мб, 5-4мб, 3-8мб).
Собственно сам проект был взят у неизвестного товарища с сайта "технохрень" (не для рекламы). Далее текст из источника.
В общем это нужно чтобы перепрошивать 8 ножные SPI флешки. А это в свою очередь нужно чтобы восстанавливать роутеры, сбрасывать пароли на биосы и восстанавливать их, и много чего еще.
Будем делать за 10 минут самый простой программатор своими руками на Ардуино 🙂 Понадобится Arduino Pro Micro ну или любая другая (будет отличаться только распиновка на ардуино). Собираем эту сложную схему: