Совсем коротенький рассказ — о довольно бесполезной но забавной штуковине, извините :)
Как-то раз я написал интерпретатор BASIC, который можно использовать на контроллере хоть с 1кб памяти (в частности AVR / Arduino). В основном мы им пользовались через Bluetooth‑модуль с телефона (я уж рассказывал). Но у меня руки чесались сделать своеобразный «терминальчик» — ну я и сделал.
Как видите — в качестве экрана тут дисплей 4 строки по 20 символов. А клавиатура полноценная — обычная c PS/2 разъёмом. Между ними и UART‑ом воткнут контроллер (младший STM32). Вообще‑то можно было без него, реализовать общение с клавиатурой и дисплеем в том же контроллере где интерпретатор крутится — но тогда это не был бы терминал, его нельзя было бы использовать с любым другим UART-интерфейсом.
Покажу картинки, код — и немножко расскажу.
Рассмотрим поближе
Как видно, сам терминал представляет из себя маленькую плату - гораздо меньше даже самого дисплея, который конечно гораздо меньше клавиатуры.
При разводке платы я заложился на интерфейс дисплея с 4-битной шиной данных вместо восьми (несколько дополнительных строк кода — это проще чем несколько лишних дорожек на плате), поэтому вы можете видеть в разъёме небольшой «гэп» от линий D0 до D3.
В целом на плате почти ничего нет — разъёмы для UART (справа) и клавиатуры (слева). Провод питания с типичным USB‑разъёмом — и регулятор для срезания 5В. У меня явно под рукой не оказалось SMD‑шного в тот момент, поэтому вот он торчит в корпусе TO-92. Ну и несколько резисторов — подтяжки, делитель. В общем если кто‑то решит повторить — понятно что все эти компоненты зависят от конкретной платы. Выкинуть можно всё или почти всё.
Маленький подстроечный резистор — по‑моему для регулировки контраста. Выводные резюки в паре мест вместо SMD‑шных впаяны просто чтобы развязать топологию (плата односторонняя) — никакого другого смысла в их выборе нет:)
Чертёж платы не привожу, т.к. он был на скорую руку выполнен в графическом редакторе — но по картинке видно что по большому счету плата не содержит ничего интересного кроме МК и разъёмов. Подключение к МК достаточно подробно описано в README на гитхабе, сейчас к этому перейдём.
Клавиатура работает от 5 Вольт, контроллер от трёх. К счастью его входы 5v-tolerant и им только две подтяжки нужны. Но в целом использовав 5-вольтовый контроллер можно было немного упростить схему.
Программируется контроллер через тот же UART‑разъём. Я собственно ради этого люблю STM32 чипы что у них встроенный загрузчик через UART работает. Просто при сбросе контакт BOOT замкнул ненадолго — и вот ты в режиме загрузки.
Теперь про код
Не думаю что кому‑то он прямо в таком виде понадобится, но частями позаимствовать или адаптировать его несложно. Наверное самая «выдающаяся» часть в нём это «bitbang» клавиатуры (у неё довольно незамысловатый синхронный интерфейс — одна линия CLK, другая данные). Я с ним впервые в жизни столкнулся но не сказать чтобы это было сложно.
Похоже на... много на что, не правда ли :) на SPI, USART и т.п.
В нормальном режиме протокол «драйвит» клавиатура, поэтому со стороны контроллера мы используем прерывание по внешнему пину.
В протоколе есть некоторое расширение на случай когда надо наоборот клавиатуре что‑то передать со стороны «компьютера» — этого я не заимплементил т.к. передавать ничего не собирался.
Клавиатура естественно возвращает не буквы а скан‑коды, поэтому кроме бит‑бэнга потребовалось ещё и держать таблицу преобразований. Точнее их в коде две — для верхнего и нижнего регистра. Для букв это необязательно но для символов, знаков препинаний и т. п. всё равно пришлось бы делать.
Часть кода (sendHex
и т. п.) вообще не нужна для функционирования а используется только для отладки по ходу программирования.
Я любитель имплементить протоколы (в т.ч. LCD‑шный) вручную нежели затаскивать чужие библиотеки — но сами видите, там кода‑то прямо скажем немного. Самому доку глянуть или бороться с чужими «кодулями» — не всегда известно на что больше времени уйдёт. Конечно выгоднее использовать дисплей с I2C‑интерфейсом (и в смысле схемы) — но они реже попадаются под руку (тем более крупного размера).
Несколько функций (например wrapLine
, scrollDown
) — это необходимая для адекватного отображения логика. Если вы пробовали заимплементить «терминал» хотя бы на компьютере, то наверное знаете что вопросы типа «как обработать Backspace» достаточно неоднозначны. В общем тут возможно можно что‑то улучшить.
Так или иначе вся программулина — меньше 400 строчек кода (из которых половина - пропуски и скобки).
Заключение
В общем эта штука вполне себе работала — на титульной картинке она подключена к самодельной плате с Бейсиком на STMF32 103 — с которого мы управляем очевидно семисегментным элементом. Бейсика хватает чтобы подключить скажем 7-сегментный дисплей из нескольких знаков, датчик температуры, несколько кнопок и т. п.
Но в целом на Бейсике мне программировать показалось скучновато:) плюс построчный ввод с 4-строчным экраном это не самое удобное.
Можно подключить и к любым другим устройствам с UART — хоть к компьютеру настольному, хоть к Raspberry Pi (ну и старинную картинку с тостером мы помним наверное). Хотя понятно что большого удобства маленький экран не обещает. На телефоне через блютус в чем‑то удобнее.
Тем не менее само впечатление от поделки — этакий «старинный комп» в миниатюре — довольно забавное.
В качестве развития идеи быть может когда‑нибудь вместо Бейсика прошью что‑нибудь повеселее. Forth я помню имеет несколько вариантов для контроллеры — надо попробовать.
А ещё пожалуй клавиатуру заменить — например вместо обычной использовать старинную клавиатуру Бодо с 5 клавишами, которые позволяют вводить буквы латинского алфавита разными комбинациями (ну и переключаться в другие регистры — с цифрами и знаками).
Если у вас возникнут какие‑то конструктивные‑забавные идеи насчет вариаций подобной штуковины — приглашаю делиться в комментариях :)
Комментарии (14)
Uint32
14.11.2024 05:02Просто изумительно!
Мой полнейший респект и уважуха!
Поймал себя на мысли, что давно не получал такого удовольствия от прочтения статьи на хабре.
NickDoom
14.11.2024 05:02Интересно, насколько сейчас распространены клавиатуры, поддерживающие PS/2 через пассивный переходник? Когда USB только появлялись — это была практически обязательная фича. В зависимости от того, что именно контр увидел, он переключался или в режим USB с диффлиниями, или в режим вот этого вот странного последовательного порта «с зачем-то ещё какими-то клоками, будто ему старт-бита и стоп-бита мало».
А вот в наше скорбное время массового оплёвывания простых и надёжных проверенных решений — каков процент клавиатур с этой легаси? Сгореть, наверное, не должны, напряжения там не как в RS-232, но имеют все шансы офигеть и не понять, что там у них такое на линиях данных.
В целом да, штучка хорошая, у меня вообще была пакостная мысль для отладки делать по умолчанию сквозной порт PS/2, то есть включаем свой девайс (более-менее произвольный) в комп (через китайский переходник PS/2 в USB, ибо комп с PS/2 сейчас поди найди), в девайс втыкаем клавиатуру, открываем текстовый редактор — и с клавиатуры говорим контру, что ему делать, а он, изображая виртуальную клавиатуру, пишет нам в ответ в текстовый редактор,
куда нам идтикак он это смог или не смог сделать.И в этот момент открывается предложение от вируса отписать в пользу его создателей всё движимое и недвижимое имущество, а контроллер отвечает «Y».На самом деле я от этой мысли отошёл именно из-за сомнения в современных клавиатурах, а больше склоняюсь к V-USB, по которой эмулируется флэшка из одного-единственного большого кластера, занятого одним файлом. А в нём и настройки, и логи…
RodionGork Автор
14.11.2024 05:02Честно говоря мне кажется что вообще настольные компьютеры и отдельные клавиатуры к ним сдают позиции - ноутбуки, планшеты, телефоны - всё это их теснит :)
Сгореть точно не должны, т.к. на линиях данных у USB по-моему небольшие резисторы есть а линии данных у клавиатуры работают с подтяжками. Вопрос же можно расширить - вдруг сейчас многие USB-клавы поддерживают PS/2 как недокументированную фичу а мы-то и не знаем!
Moog_Prodigy
14.11.2024 05:02Я делал подобный терминал на AVR. Только клавиатуру от какого-то кассового аппарата приспособил, там был опрос ее матрицы. Дисплей 1602. В принципе - ничего сложного. Не сказать правда что этот девайс мне сильно пригодился для отладки - оказалось проще стационарный комп с досом где-то нарыть, чем пытаться что-то на этом экранчике разглядеть, а про вывод я молчу.
mgupi
14.11.2024 05:02А можно схемку хоть от руки хоть в паинте нарисованую?
RodionGork Автор
14.11.2024 05:02схемка в нарисованном виде не существовала но т.к. она в общем-то из проводков между разъёмами и контроллером состоит то она текстом описана:
Wiring
For TSSOP-20 package
pin 16 (VDD) to +3.3
pin 5 (VDDA) to +3.3
pin 15 (GND) to GND
pin 1 (BOOT0) to +3.3
pin 4 (RESET) to GND, temporarily
pin 17 (USART1_TX) to RX of the FTDI-cable
pin 18 (USART1_RX) to TX of the FTDI-cable
pin 6 (PA0) LED
pin 2 (PF0) ps/2 - data
pin 3 (PF1) ps/2 - clock
здесь не упомянуты ноги к разъёму дисплея однако, не помню почему. но на этот счет есть чертёж платы - здесь справа UART
а ноги контроллера в доке можно посмотреть, ну или вот вкратце
ноги же дисплея на фото видно - на нём подписаны чОтенько
надеюсь это поможет :)
хотя как я сказал выше, лучше переделать используя 5в контроллер, будет проще
mgupi
14.11.2024 05:02Спасибо, а в чем прошивка (проект) писалась? Про avr немного знаю, с stm еще не сталкивался..
RodionGork Автор
14.11.2024 05:02в блокноте писалась. там в файле compile.sh скорее всего строчка вызова gcc соответствующая есть. для них есть какие-то развесистые среды но мне было неохота разбираться. впрочем названия адресов соответствуют документации так что при необходимости синтаксис автозаменой можно подогнать под среду/фреймворк.
arteast
Давайте я вам заголовок поправлю. "UART-терминал из STM32, LCD-дисплея и компьютерной клавиатуры". Вы главный компонент забыли упомянуть.
RodionGork Автор
Я не забыл, просто в отличие от остальных двух МК может быть любой, как сказано (не обязательно STM32). Но можем и поправить.
Ну и насчет "главного" это неправильно. Как сказано где-то в начале без отдельного МК сделать можно. А вот без клавы или дисплея уже как-то неудобно будет :)
arteast
Вообще без МК сделать терминал сложновато. Я, честно говоря, подумал, что вы контроллер клавиатуры умудрились как-то перепрошить, чтобы он не только опрос матрицы делал. Тут как в анекдоте - с МК любой дурак сумеет, а ты без МК попробуй )
RodionGork Автор
Сделать-то можно, в виде проекта на пару месяцев - только чтобы по-честному это должно быть не "перепрошивание клавиатуры" потенциальное а плата на рассыпухе из логики. Но что с этим делать дальше? выложить на хабр чтобы кто-нибудь первым делом в комментах написал "нууу, если бы на дискретных транзюках... а так любой дурак может" :)
Moog_Prodigy
Нууу, если бы на лампах....а так любой дурак сможет.