После запуска Doom на кнопочном телефоне, я искал устройства на которых можно это повторить. К ним есть требования: цветной экран и несколько мегабайт памяти (идеально 4, но можно запустить и на двух). Видел счётчик электричества и USB тестер, то и другое есть с цветными экранами. Но покупать не стал, потому что скорее всего такие устройства имеют лишь десятки килобайт памяти, как и мощный чип им не нужен. Наконец на распродаже на известном китайском маркетплейсе увидел детский фотоаппарат, его и заказал для своего извращённого развлечения реверс-инжинирингом.
Но также нашел детский фотоаппарат со скидкой в немного другом корпусе на нашем маркетплейсе, заказал и его, ведь он будет у меня много раньше чем товар из Китая. Его и начал изучать первым...
(Не)много китайского кринжа
Камера в прямом смысле ноунейм, потому что нет ни названия бренда, ни адреса завода изготовителя. Ни на упаковке, ни в микроскопической инструкции.
Несмотря на то, что кнопки данной камеры сами по себе громко щёлкают, так и при нажатии камера пищит громко и мерзко. Первым делом полез в настройки это отключать, там сразу стоял русский перевод, и с ходу не нашел настройки громкостью. Сменил язык на английский, и тогда стало понятно, что "volume" перевели как "объём".
Также в настройках нашелся номер версии чего-то: AX3295B_22-08
Что бросается в глаза - экран мерцает как старый телевизор, и глаза от этого устают. Также со стороны экрана есть дырочка в корпусе, через который светит неприкрытый светодиод и выжигает глаза если не держать камеры немного под углом.
Разрешение камеры этого чуда - 640x480. Это разрешение фильтра Байера, а значит на один пиксель камеры есть лишь один цветовой компонент, там 1/2 зеленых, 1/4 красных и 1/4 синих. Честный, не интерполированный, RGB будет лишь в разрешении 320x240. В инструкции разрешение честно не указывают, зато указывают модель сенсора камеры - GC0308, по этому названию можно найти разрешение.
Зато в настройках есть широкий выбор разрешений для фото: VGA, 1M, 2M, 3M, 5M, 8M, 10M, 12M, 16M, 18M, 20M, 40M. VGA в понимании данной камеры - это 640x480. Остальное - это натягивание совы на глобус растягивание этого разрешения на указанное в настройках. Причём тут даже обман на обмане, потому что более чем 12M (4032x2880) оно не растягивает. Наверное, это должно научить ребёнка что ничему нельзя верить.
Качество сенсора камеры отвратительное, светочувствительность очень низкая, в тени уже ничего не видно.
Настройки видеозаписи в настройках: VGA, 720p, 1080p. VGA это тот же 640x480. Видео сохраняется MJPG кодеком в AVI. Пробовал через ffmpeg закодировать видео в том же формате, но оказалось что воспроизводить оно может только записанное собой. На видео созданных через ffmpeg камера намертво зависает. Догадался, что дырочка около микро-usb разъёма - это скрытая кнопка сброса.
Может проигрывать музыку, но выхода на наушники нет, только через встроенный динамик. Который, внезапно, хорошо воспроизводит низкие частоты, что держишь в руке и ощущаешь удары и вибрации. Правда вокал звучит плохо, и в современной музыке всё сливается в какофонию. Но инструментальную классику слушать можно.
Аккумулятора хватает лишь на 20-30 мин, и это при прослушивании музыки с выключенным экраном.
Изучаем глубже
Хотя на заказанном из Китая винты были видны прямо на фото товара, но в этом всё скрыто, так что стал изучать его поведение при подключении к компьютеру. Когда подключаете такие устройства, то лучше следить за ними через системный лог Linux, а не lsusb
. Дело в том, что они могут переподключаться под другим идентификатором, или появляться лишь на доли секунды.
Сначала камера появляется в системе так:
New USB device found, idVendor=0219, idProduct=3280, bcdDevice= 1.00
Product: GENERAL - AUDIO
Manufacturer: Generic
Как только от драйвера приходит запрос SCSI - не отвечает и переподключается так:
New USB device found, idVendor=1908, idProduct=3283, bcdDevice= 1.00
Product: GENERAL - AUDIO
Manufacturer: Generic
Через SCSI приходит такая идентификация:
Direct-Access Buildwin Media-Player 1.00 PQ: 0 ANSI: 4
На этот раз работает как картридер, и бонусом как веб-камера отвратительного качества. lsusb
считает что вендор 0x1908
- это Gembird.
Поиск BuildWin в интернете позволяет узнать альтернативное название - AppoTech, под таким именем у этой китайской компании есть представительство в США.
Также я подключил через так называемый загрузочный кабель (boot cable, микро-USB в разъёме которого дополнительный пятый контакт замкнут на землю, можно сделать через OTG переходник и AM-AM USB кабель). В системе появилось такое устройство:
New USB device found, idVendor=1908, idProduct=3319, bcdDevice= 1.00
Product: BLDR v1.00
Manufacturer: BUILDWIN
Через SCSI называется так:
Direct-Access BuildWin Video050Loader 1.00 PQ: 0 ANSI: 2
Это мало что даёт, так как я не нашел никакой информации как управлять этим BLDR
. Остаётся только разобрать и считать прошивку программатором.
Сложности разбора
Мне удалось подковырнуть и снять декоративную панель со стороны объектива. Но под ней есть четыре углубления, три с винтами, и одно глухое. Хотя у меня есть отвёртка с мелкими битами - но углубления настолько глубокие, что биты упираются на своём утолщении и не достают винтов. Пришлось заказывать набор тонких часовых отвёрток.
Отвинтил три винта. Также держится на пластиковых защёлках, но они не жесткие. Плата держится на еще одном винте на части корпуса с экраном.
Внутри оказался безымянный аккумулятор, на нём какие-то следы, будто от сорванной наклейки, на приклеенную сторону заглядывал, там тоже ничего.
На обратной стороне обнаружился безымянный чип с большим количеством ножек. Видимо, это и есть центральный процессор. При наклоне и подсветке фонариком, на нём таки написано 2237J, что не похоже на название, лишь на серийный номер. Даже не похоже чтобы название чипа удаляли, похоже что его никогда и не наносили.
Рядом с процессором есть чип флэш-памяти: Puya P25D16SH, который считал программатором. В паре программ не нашел чип в списках, в интернете нашел такую информацию для ручной настройки: 3.3V, 16Mbit (2MB), page: 256-byte.
Сложности дизассемблирования
Предыстория
Когда-то считывал прошивку со старого китайского телевизора. Хотел посмотреть, можно ли исправить overscan, который он делает на HDMI (не исправляется даже через инженерное меню, потому что там можно скорректировать в границах +/- 50 пикселей, а он срезает больше). Чип там TSUMV59XES, более известный просто как V59. Так вот, я не смог понять какой у загрузчика набор инструкций, а остальная прошивка сжата или зашифрована. Нашел документ со списком возможностей чипа, и там процессор описан как "High speed/performance 32-bit RISC CPU", также узнал что это чип MStar. Нашел исходники прошивок MStar для похожих чипов и там 8051 в паре с ARM или OpenRISC. Но и это не помогло, так что забросил. Зато узнал про OpenRISC.
По данным в прошивке видно, что данные выровнены по 32 бита. Числа явно little-endian. Попробовал дизассемблировать как ARM - не подходит. Попробовал MIPS - тоже не подходит. Бросились в глаза комбинации байт FC FF FF 03
и FВ FF FF 13
, это похоже на команды прыжка назад, как используются в любых циклах. 26 бит константа и 6 бит опкод. Заглянул в документацию OpenRISC - так и оказалось!
Почему-то OpenRISC, в отличии от распиаренного RISC-V, это какой-то ультра-нишевый набор инструкций, его нет ни в IDA, ни в Ghidra. Пробовал собрать binutils для OpenRISC - так там вообще не проверяли поддержку little-endian OpenRISC, поэтому дизассемблер на 50% инструкций пишет, что это неизвестные. Нашел на Github модуль для IDA, написанный на питоне, но для какой-то старой версии (до седьмой). Исправил модуль чтобы запускался на седьмой и выше - нашел в процессе очень сомнительные решения и недостаток инструкций, которые есть в документации. Переписал всё полностью, за пример брал модуль msp430.py
. Мой модуль здесь.
У OpenRISC есть похожая черта с MIPS - delay slot, инструкция идущая после прыжка исполняется в любом случае. Не знаю, отключается ли это на MIPS, но у OpenRISC есть специальный флаг ND (no delay), если установлен - то процессор при прыжке не выполняет инструкцию следующую за прыжком. Как оказалось, вся прошивка скомпилирована в таком режиме. Но я добавил в модуль для IDA возможность выбора режима ND через Alt-G (так же как для 32-бит ARM сделано переключение между thumb и 32-бит инструкциями).
Всего кода в прошивке ~360KB, ~250KB данных, остальная часть прошивки - это таблица офсет/размер и далее данные "типа файлов", потому что без имени, только номер в таблице. Это маленькие картинки из интерфейса в jpeg (с не удалёнными мусором метаданными от Adobe Photoshop CC 2018, что занимает ~25-35% от изображений). Также звуки в wav, несколько bmp, и неустановленные данные (наверное шрифты и локализация).
В прошивке много ссылок на данные по адресам начинающимся с 0x020xxxxx
, и в самом начале прошивки я нашел установку регистра SP (stack pointer) на 0x021ffffc
. Наверное 0x02000000
это начало ОЗУ, 0x021ffffc
это начало стека и конец памяти, так как стек растёт к младшим адресам. Значит, предположительно, на камере 2МБ памяти.
Теперь, зная набор инструкций - можно попробовать вставить свой код и прошить программатором. Но это очень неудобно, так что я стал искать готовые инструменты или интерфейс в прошивке.
Неизвестный BuildWin
Инструментов и документации к AppoTech/BuildWin в сети очень мало, и это старые модели устройств. Но можно узнать, что они сначала промышляли контроллерами к USB накопителям. Старая серия AX2xxx - это медиаплееры с процессором на инструкциях 8051 и аппаратными декодерами mp3/jpeg. В серии AX3xxx про процессор написано "High Performance 32-bit RISC CPU". Почему-то никто не указывает OpenRISC прямо. OpenRISC считается зашкваром, или что-то с "Open" в названии это зашквар? Или, может потому, что у архитектуры лицензия LGPL?
Из инструментов для других чипов - я узнал что используются SCSI команды из зарезервированного для вендоров диапазона (0xc0..0xff), а именно 0xcb, 0xcd.
Почему SCSI?
Похоже это удобно в Windows, так как не надо делать никаких драйверов (знаете эту проблему с поиском и установкой драйверов?). Устройство может притворятся диском, в который не вставлен накопитель. При этом есть возможность давать кастомные команды через стандартный драйвер. И прошлое компании сказывается, что начинали они с USB накопителей.
Через Wireshark записал USB трафик камеры с системным драйвером, и нашел что "BuildwinMedia-Player 1.00
" это ответ на команду INQUIRY
. Этот ответ я нашел в данных прошивки, и нашел код который ссылается на эти данные. "
Video050Loader
" и "BLDR
", из ответа на загрузочный кабель, в прошивке нет, очевидно это передаёт загрузочный ROM прописанный прямо в чипе.
"Разделённые" константы в ассемблерном коде
Немного о том, как выглядят ссылки на данные в OpenRISC коде. Если вы знаете 32-бит ARM, то там есть команды загрузки констант, что лежат где-то рядом. Таким образом эти константы просто найти без дизассемблирования. Но тут не так, загрузка 32 бит констант (адрес это тоже 32-бит константа) разделена на загрузку в старшую часть регистра, и арифметическую операцию дописывающую нижнюю часть.
Так выглядит в коде OpenRISC загрузка адреса 0x209FCA4
:
09 02 80 18 l.movhi r2, 0x209
A4 FC 42 A8 l.ori r2, r2, 0xFCA4
Что в оригинальном коде от компилятора должно было выглядеть так:
l.movhi r2, hi(somedata)
l.ori r2, r2, lo(somedata)
И не обязательно, чтобы старшая часть загружалась предыдущей инструкций, это может быть 10 инструкций до.
Пришлось дорабатывать модуль дизассемблера, добавил указание целой константы в финальной инструкции:
09 02 80 18 l.movhi r2, 0x209
A4 FC 42 A8 l.ori r2, r2, lo(0x209FCA4)
Запуск произвольного кода
Проанализировав код прошивки, я нашел, что переход в загрузочный режим не обязателен. Камера подключенная к USB с загруженной ОС позволяет выполнять произвольный код по SCSI команде 0xcd.
Также нашлась команда 0xda для перезапуска чипа в режим загрузчика.
Тут возникает вопрос, а как узнать, какой код выполнять? Как прочитать или записать память? А никак, интерфейсом это не предусмотрено. Если у вас нет оригинала прошивки или дампа, полученного через программатор - то никак это не найти.
Но как тогда читать/записывать память? Может, урезать какой-то функционал в прошивке и вместо него добавить функцию чтения? Но мне повезло, прямо до обработчика команды 0xcd идёт функция чтения/записи памяти через USB. Достаточно использовать её адрес в команде для 0xcd.
Пример SCSI запроса:
00: 55 53 42 43 # "USBC"
04: 01 00 00 00 # тег, в ответе придёт такой же
08: xx xx xx xx # размер данных (little-endian)
0с: 80 # 00 - передать данные устройтву, 80 - запросить данные с устройства
0d: 00 # флаги, не нужно
0e: 10 # размер SCSI команды (6, 10 или 16)
0f: cd # SCSI команда
10: f4 91 03 02 # адрес функции обработчика чтения записи - 0x20391F4
14: xx xx xx xx # адрес памяти для чтения/записи,
# -1 значит использовать временный буфер
18: ff ff ff ff # 0x20391F4 позволяет вызвать еще одну функцию,
# после чтения с компьютера, или до передачи на компьютер,
# -1 значит ничего не вызывать
1с: 00 00 00 # не используется
И я прочитал всю оперативную память по адресу 0x02000000
. Также стал искать адреса кода загрузчика из чипа, сохранил 2МБ памяти с нулевого адреса, и нашел его адресу 0x00100000
, только почему-то первый килобайт затёрт нулями. Именно затёрт, потому что на него есть прыжки из кода чуть ниже. Поискав по коду загрузчика - я нашел данные "BuildWinVideo050Loader 1.00
", и код ссылающийся на них. Как оказалось - код загрузчика тоже имеет вендорскую команду для выполнения кода. Но уже почему-то 0xcb. И по адресу 0x102620
нашел функцию чтения/записи памяти для вызова через команду 0xcb.
Кривые binutils для OpenRISC
Решил измерить частоту процессора, проверить запись памяти и выполнение кода. Написал код на ассемблере, скомпилировал через ассемблер из binutils. И тут сюрприз - это big-endian код. Попытался разными способами передать опции меняющие порядок байтов в компилятор ассемблера, но он не знает ничего. И похоже, такие опции для OpenRISC просто не реализованы, настолько кривая поддержка этого набора инструкций. В итоге написал программу, что читает данные по 4 байта и разворачивает их в обратном порядке.
Частота процессора
Как замерить частоту процессора на неизвестном чипе? Если процессор работает на постоянной частоте и не суперскалярный, то всё просто: делаем цикл, и если мы повторим его количество раз, равных частоте процессора, то код выполнится за количество секунд, помноженное на время одной итерации в тактах.
Например (r5 - счётчик):
1: l.addi r5, r5, -1
l.sfgtui r5, 0
l.bf 1b
Но мы не знаем, сколько тактов уходит на одну итерацию. Поэтому нужен еще один замер, где добавим простую инструкцию, которая должна отрабатывать за один такт.
2: l.addi r4, r4, 0
l.addi r5, r5, -1
l.sfgtui r5, 0
l.bf 2b
l.jr lr
Тогда время выполнения второго цикла должно быть на секунду больше.
Нашел пустую область памяти, записал свой код туда. Прочитал обратно - возвращает что и было записано. Вызвал свой код - устройство перезагрузилось. Что я сделал не так? Первая мысль была - что есть защита от исполнения, значит надо записывать поверх другого кода. Нашел крупную функцию по обработке AVI файлов. В начало поставил инструкцию возврата. А далее записал свой код. Всё записалось и читается.
Выполняю код - нет никакой задержки. Запустил несколько раз. Иногда падает. Но иногда начинает давать задержку. Вычислил частоту как близкую к 141.72MHz.
Я находил в коде значение 144000000, и сначала подумал, что это не связано с частотой процессора. Позже нашел описания AX32xx чипов на сайте AppoTech, где есть чипы с частотой 144MHz. На сайте нет упоминания чипа AX3295B - указанного в версии из опций. Тогда почему получается 141.72? Предполагаю, что приходят прерывания от таймера, что обрабатываются во время работы цикла, что тратит 2% мощности процессора. Кстати, там же указано, что у этих чипов 8кб кэша данных, и 8кб кэша инструкций. Правда на сайте у чипа с частотой 144MHz - 8MB памяти, а у чипа с 120MHz - 2MB, так что или в камере чип пограничный, или у него есть 8MB, но используется лишь 2MB.
Наверное, некоторые подумали, что странно, что есть защита от выполнения определённых страниц памяти, но нет защиты от записи кода. Так что, наверное, защиты от выполнения нет. Но почему код то даёт задержку, то не даёт, то падает? Кэш инструкций? Но я выбирал свободное место в памяти, которое не должно было выполняться, следовательно не попало бы в кэш. И я выбирал функцию в которую вставил свой код - что тоже не должна была выполняться сразу после загрузки. Тогда что? Ведь память записывается и читается обратно. Не сразу догадался, что реально просходит - это память остаётся в кэше данных, и не записывается пока не будет чем-то вытеснена из кэша, кажется у ARM процессоров тоже есть такой режим. Эксперименты показали, что нужно записать свой код, а потом прочитать 8кб любых данных, код стал выполняться всегда и без ошибок.
Зачем OpenRISC, когда есть знакомый ARM?
И тут, наконец, из Китая дошел фотоаппарат, что я заказывал первым.
Включаю его, те же картинки, но почему-то всё как будто написанное другими людьми, но по тем же инструкциям.
Например:
На втором экран не мерцает, и даже светодиод глаза не слепит. Звук нажатия клавиш не бесит. Перевод на русский нормальный.
Первый работает как веб-камера, второй нет.
На первом на две игры больше: скролл-шутер и лабиринт.
На первом в тетрисе одноцветные фигуры, и их очень тяжело быстро спустить вниз, потому что нажатие вниз это сдвиг на одну клетку вниз, и зажать нельзя. Во втором фигуры разных цветов, и нажатие вниз сразу сбрасывает фигуру.
Первый не умеет проигрывать никакое видео, кроме записанных на нём же MJPG. Второй может проигрывать 3gp (h263) и mpeg4 (Simple Profile) c AAC звуком.
Первый при проигрывании музыки показывает плейлист (нажать влево), второй не показывает ни списка треков, ни даже названий.
У первого есть накладные фильтры в фото режиме, и даже зум при зажатии вверх-вниз, у второго ничего.
Понимание мегапикселей в опциях разное (тоже обман, но чуть по-другому).
Второй работает как картридер очень медленно (USB 1.1?).
И даже разбирается второй очень легко, биты не застревают, никаких пластиковых защёлок нет:
Хоть я и не замерял размеры, но на вид печатные платы внутри обоих моделей имеют одинаковую форму и размер, и расположение всех кнопок и разъёмов одинаковое. Так что для меня это выглядит так, что можно поменять корпуса местами и всё подойдёт по размеру.
Версия прошивки из опций второй камеры привлекла внимание. Потому что в начале подписано "MMI Version", не помню уже что это сокращение означает, но встречалась лишь на телефонах, значит ли это...
Подключаю к USB - производитель Spreadtrum. И это оказался тот самый чип SC6531, на котором я уже запускал Doom год назад. Только не определяется экран - нашел коды инициализации экрана и добавил поддержку в свой порт Doom.
Но что делать с управлением, на этой камере всего 6 кнопок, это стрелки, и две кнопки со смыслом enter/escape. Причём одна кнопка - это кнопка питания, а она идёт отдельно от остальных со странным интерфейсом. Пришлось добавлять поддержку кнопки питания.
Из шести кнопок я сделал 10, зажатая кнопка питания изменяет функциональность остальных (как Fn на клавиатуре). Этого хватает для игры в Doom.
Результат на видео:
А что с OpenRISC?
Пожалуй, что самое интересное я сделал - доступ к процессору устройства получил. Сделал модуль дизассемблера для IDA. Писать драйвера под его железо и портировать Doom на него - будет рутиной. Тем более что надо будет собирать компилятор (старый) из коммитов на гитхабе, а там еще какие-нибудь сюрпризы обнаружатся, как с binutils. Надо придумывать как уместить Doom в 2 мегабайта. А я уже запустил Doom на детской камере на привычном мне железе.
P.S.: Не удивлюсь, что если есть на чипе Spreadtrum, то есть и версия на Mediatek MT6261, которые также популярны в кнопочных телефонах. Может даже на чипах RDA (которые тоже в кнопочных есть, но реже Spreadtrum и Mediatek). Зачем портировать одну и ту же задачу на разные чипы, и каждый раз это делают разные люди, и делают всё по своему - я не понимаю. Причём, у одних одно лучше получается, у других другое.
Комментарии (26)
SergeyNovak
10.12.2023 17:27Очень интересно и познавательно.
Тебе надо на барахолку, куда сносят всю беcхозную и сегодня уже бесполезную по прямому назначению электронику. Там раздолье!
Было бы интересно почитать про исследование фотоаппаратов Canon. Они на процессорах DIGIC разных поколений. Причем от мыльниц вроде PowerShot до зеркалок EOS. Под них есть различные хаки, которые запускаются прямо с флэшки для снимков:K_Chicago
10.12.2023 17:27PowerShot - в свое время отнюдь не мыльница. До сих пор имею PowerShot G5, купленый в 2002м.
Это довольно продвинутый аппарат, с множеством самых передовых опций того времени:
полностью поворотный дисплей видеоискателя, при этом сохраняется и оптический видеоискатель; ИК-remote, доступ по USB позволяет полностью дистанционно управлять всеми настройками аппарата, есть режим съемки "М" (полностью ручной, включая фокусировку) и даже имеется Time Lapse (правда, всего лишь на 100 кадров, непонятно почему).
Даже сейчас лишь немногие камеры имеют полностью поворотный (fully articulated) видеоискатель.K0styan
10.12.2023 17:27PowerShot - это было общее имя для всей линейки не-зеркалок Canon. Там были самые разные девайсы: и максимально продвинутая G-серия, и простенькая A, и компактная, но с сохранением функциональности S.
Firsto
10.12.2023 17:27различные хаки, которые запускаются прямо с флэшки для снимков
До сих пор пользуюсь Magic Lantern на древнем 5D.)
VladimirFarshatov
10.12.2023 17:27Любопытно, сколько это исследование заняло времени?
jpegqs Автор
10.12.2023 17:27Чуть больше двух недель. В разы быстрее, чем я делал порт Doom на чип Spreadtrum год назад. Но я же Doom под OpenRISC так и не портировал, только доступ к процессору получил.
VladimirFarshatov
10.12.2023 17:27Давно-давно реассемблировал БИОС, а позже DR-DOS 5.1 .. тогда тоже было потрачена куча времени. Не сказать что совсем бесполезно, но .. умерло оно всё.
Завидую вам, молодым. Только с возрастом (видимо где-то в мозгах заблокировано до поры) начинаешь понимать, что в жизни есть только один невосполнимый ресурс - время самой жизни.
vadimk91
10.12.2023 17:27Совершенно согласен. "У человека две жизни, и вторая начинается тогда, когда мы понимаем, что жизнь всего одна" (Том Хиддлстон)
ValdikSS
10.12.2023 17:27Зачем портировать одну и ту же задачу на разные чипы, и каждый раз это делают разные люди, и делают всё по своему - я не понимаю.
Чтобы получить дешевое устройство, и особенно игрушку, нужно взять максимально дешевые и доступные комплектующие: сверхмассовый высокоинтегрированный некондиционный SoC, который есть у кучи поставщиков за копейки.
jpegqs Автор
10.12.2023 17:27У меня есть идея, что потому, что у каждой компании разрабатывающей чипы есть свои подрядчики. Которые выполняют заказы, но код заказчику обратно никогда не отдают.
lonelymyp
10.12.2023 17:27Это же китай, что есть сейчас на складе, из того и собирают, отбраковка, Б/У с разборки, прошивку пишут по такому же принципу, приносят образец и говорят сделать такую же.
acc0unt
10.12.2023 17:27Реверс ноунейм-китайцев по всем канонам жанра.
Про SCSI-команды: да, это тяжёлое наследие флешек. Таким методом шьются практически все флешки - и у многих компаний, которые начинали с флешек, и по сей день бутлоадеры сделаны именно так. Так что если видишь вообще любой девайс с USB и с MSD-классом - наверняка где-то там в зарезервированных областях SCSI команд есть закладочка от производителя.
Например, у чипов JieLi из ультрадешёвых клонов AirPods есть такого же типа прошивочный интерфейс USB. Хотя USB в беспроводных наушниках ну вот вообще никак не используется. Как же так вышло?
Китайский эволюционный путь, бессмысленный и беспощадный. Из чипа для флешек кремний эволюционирует в чип для USB MP3 плеера. К контроллерам USB и NAND прирастает аппаратный декодер MP3 и хлипенький блок ADC/DAC. У чипа MP3 плеера вскоре после этого вырастает Bluetooth - и получается чип для портативной Bluetooth-колонки. А потом Apple делает AirPods - и в эволюционной гонке чип из Bluetooth-колонки скукоживается, учится работать в TWS-режиме, и становится чипом для беспроводных наушников.
NutsUnderline
10.12.2023 17:27Китайский эволюционный путь
я прям представил описанное в виде анимации с морфингом
hooperer
10.12.2023 17:27Бодрого дня, вот прямо интересно, а есть ли порт на pic32 к примеру? ;)
strvv
10.12.2023 17:27попробую ответить за автора, насколько я в свое время встречался, ядро pic32 это же MIPS?
jpegqs Автор
10.12.2023 17:27Какая разница, был бы 32-бит процессор, достаточно памяти и мегагерц, 4МБ и лучше 100 МГц и более. Это если хочется сделать порт с наименьшим приложением усилий. Если характеристики хуже, то придётся ресурсы игры и саму игру упрощать, что дополнительные трудозатраты на порт. Не стал отвечать, потому что конкретная архитектура не имеет значения.
hooperer
10.12.2023 17:27pic32Z2048efg144B- I/PI даже вот интересно) ну и если к ней подключен скажем TM043NDH02-40 TFT 4.3' ну мало ли, ну вдруг)
v1000
такое впечатление, что понятие «детский» это не про целевую аудиторию, а про функционал устройства (сарказм)