Внимание: Данный материал создан исключительно в образовательных и исследовательских целях. Все манипуляции проводились на личном оборудовании автора. Несанкционированный доступ к чужим системам и сетям преследуется по закону.

Современные IoT-устройства, несмотря на компактные размеры и ограниченные ресурсы, представляют собой полноценные embedded-системы. Под пластиковым корпусом бюджетного гаджета часто скрывается стандартный Linux-компьютер с собственным ядром, драйверами, файловыми системами и сетевыми службами.

Статья посвящена проведению полного цикла реверс-инжиниринга типовой IP-камеры: от аппаратного анализа печатной платы до закрепления в операционной системе с root-правами.

Разберём путь от подключения к внутренним отладочным интерфейсам устройства до реализации устойчивого удаленного root-доступа по Wi-Fi. На примере IP-камеры Aceline AIP-O4 наглядно рассмотрим типовую архитектуру бюджетного IoT-девайса и классические ошибки, допускаемые вендорами при проектировании безопасности.

TL;DR - если не хочется читать целиком

Было проведено реверс-исследование IP-камеры Aceline AIP-O4.
Через UART был получен доступ к загрузчику U-Boot, после чего параметр init был изменён на /bin/sh и получен доступ в root-консоль.

Далее была обнаружена возможность выполнения произвольных shell-скриптов через /var/syscfg/test.sh в read-write разделе файловой системы.

Результат:

  • получен полный root доступ через telnet shell по Wi-Fi

  • внедрён бэкдор устойчивый к перезагрузкам

  • найдена уязвимость path traversal в веб-сервере

  • сохранена штатная работоспособность устройства

Этап 0: Выбор устройства

Первым делом нужно определиться с подопытным, поэтому я выделил вот такие критерии для выбора устройства:

  • Цена 1000-1500 руб., чтобы было не так жалко, если вдруг случайно сделаю "кирпич".

  • Не очень высокая предполагаемая степень защиты. Если будет чрезмерно сложно, интересный эксперимент превратится в пытку и тяжёлую нудную работу, что убьёт весь энтузиазм и любопытство.

  • Богатый функционал и разнообразие периферии. Это даст более широкий простор для экспериментов.

Выбор пал на IP-камеру Aceline AIP-O4, и вот что у неё на борту:

  • Камера

  • Микрофон

  • Динамик

  • ИК-подсветка

  • Слот для SD-карты

  • Wi-Fi (как точка доступа, так и подключение к другой сети)

На борту урезанная версия Linux - маленький, слабенький, но всё-таки настоящий компьютер с настоящей ОС.

Камера была куплена 07.03.2026 за 950 руб. в магазине DNS.

IP-камера Aceline AIP-O4
IP-камера Aceline AIP-O4
Информационный стикер на корпусе
Информационный стикер на корпусе

Для дальнейшей работы мне понадобились следующие инструменты:

  • Отвертки, пластиковая лопатка для ремонта электроники (чтобы аккуратно поддеть детали корпуса), 3 шт. Dupont проводов, гелевая клейкая лента (не проводит ток, клеится легко, очень плотно прижимает провода к UART контактам - пайка не нужна)

  • Arduino UNO (как UART-мост) или отдельный USB-TTL адаптер на FT232BL/RL

  • Программатор CH341A с прищепкой SOP8

  • MicroSD карта любого объёма

  • Софт: PuTTY, NeoProgrammer, binwalk

Этап 1: Разведка и препарирование пациента

Любой hardware-анализ начинается с отвертки. Пластиковой лопаткой или медиатором поддеваем тонированную панель на передней части камеры, выкручиваем два винта и аккуратно извлекаем внутренности. Важно не повредить тонкие шлейфы, идущие к микрофону и Wi-Fi антенне.

Извлекаем начинку из корпуса
Извлекаем начинку из корпуса
Общий вид всей начинки в сборе
Общий вид всей начинки в сборе
Вид на плату спереди
Вид на плату спереди

Отсоединив периферию, мы получаем доступ к основной плате. Нас интересует "Святая Троица" IoT-устройств: процессор (SoC), SPI Flash память и отладочный интерфейс UART. На фото отлично видно всех троих: самый большой чип - это SoC, рядом с ним SPI Flash с 8 ножками, а на обратной стороне платы расположились 4 медных контакта UART.

Обратная сторона платы
Обратная сторона платы
Плата без объектива
Плата без объектива

Идентификация компонентов:

  • SoC: Ingenic XBurst T31. Архитектура MIPS32. Популярный и дешевый чип для видеоаналитики.

  • Flash-память: 8-пиновая микросхема GD25Q64CSIG (GigaDevice). Это SPI NOR Flash объемом 64 Мегабита (8 Мегабайт). Питание логики - 3.3V. Здесь хранится загрузчик, ядро и вся файловая система.

  • UART: На плате любезно оставлена нераспаянная гребёнка из четырех контактов, подписанная как GND, TX, RX, 3V3. Бинго.

Этап 2: Слушаем эфир и ловим U-Boot

Прежде чем что-то менять, нужно понять, что вообще происходит под капотом при старте устройства.

Пока ждал доставку нормального программатора, я собрал колхозный UART-мост из Arduino UNO для первичного "прослушивания" логов загрузки. Сначала замыкаем RST и GND на Arduino, чтобы отключить микроконтроллер от шины UART и сделать USB-UART мост от USB порта компьютера до UART на плате камеры. Dupont провода подсоединяем к контактам UART на плате - TX (Transmit) камеры к TX Arduino, ну и GND (Ground) --> GND, разумеется.

Обратите внимание на то, как UART устройства подключаются к пинам Arduino в роли UART-моста: не TX к RX (Receive), а именно TX к TX. Замыкание RST на GND отключает основной микроконтроллер (ATmega) от шины, и мы начинаем напрямую общаться с чипом USB-TTL, встроенным в плату Arduino. Именно поэтому пин TX на Arduino (который физически ведет к RX USB-чипа) должен подключаться к TX целевого устройства.

В обычных UART соединениях используется TX→RX.

Подключение к UART позволило увидеть логи загрузчика в реальном времени, и понять, что мы на верном пути.

Важно: Arduino оперирует 5-вольтовой логикой, а SoC камеры работает на 3.3V. Если бы мы соединили TX Arduino с RX камеры для отправки команд в терминал, мы бы с высокой вероятностью сожгли процессор. Поэтому при помощи Arduino (без использования резисторов) мы можем только посмотреть логи.

UART мост из Arduino UNO
UART мост из Arduino UNO

Позже я перешел на классический USB-to-TTL адаптер (FT232BL). Намного удобнее, стабильнее и компактнее.

Подключение: GND к GND, TX к RX, RX к TX - тут уже всё стандартно. Питание подается штатно от блока питания камеры.

Подключение к UART
Подключение к UART

В настройках терминала (я использовал PuTTY) указываем COM-порт USB-to-TTL адаптера (можно посмотреть в диспетчере устройств), Connection type - serial, baudrate - 115200. Включаем питание камеры от штатного блока питания, и... в консоль посыпался лог загрузки!

Некоторые интересные моменты, которые удалось сразу же понять из логов:

  • systemCommonConfigRead,1722] tip_led_switch: 1 telnetd_switch: 0 alarm_interval_sec: 60 sd_capacity_multiply: 1 сообщает нам о том, что telnetd не вырезан из прошивки, но программно отключён. Что ж, это очень хорошая новость.

  • 00:00:17.267 11 CONET> ra0APStart,1387] is going... (ap0, gwIpv4=172.50.4.1) даёт информацию о наличии Wi-Fi интерфейса, который является точкой доступа и статическим адресом шлюза назначается IP 172.50.4.1. Отлично, это нам тоже пригодится.

Но самая важная строка в нем выглядела так:

Hit any key to stop autoboot:  1     0 

Уязвимость №1: Загрузчик U-Boot не заблокирован. У нас есть ровно 1 секунда, чтобы нажать Enter и прервать загрузку ОС, получив консоль isvp_t31#. Просто спамим любую клавишу, прерываем процесс загрузки, и получаем промпт командной строки. Если не успели - просто перезагружаем камеру через отключение и включения питания.

Из консоли U-Boot мы можем изменить параметры загрузки ядра (bootargs). По умолчанию система монтирует ФС и просит логин/пароль, но командой printenv посмотрим, какие переменные загрузки сейчас установлены. Среди них нас интересует параметр, который сейчас выглядит как init=/linuxrc.

Если мы поменяем этот параметр на init=/bin/sh, ядро после инициализации сразу выбросит нас в root-оболочку, минуя авторизацию и стандартные загрузочные скрипты.

Заменяя init=linuxrc на init=/bin/sh, мы даём команду ядру Linux вместо штатной программы инициализации (которая запускает службы и процесс login, требующий пароль) просто запустить оболочку командной строки с правами суперпользователя.

Копируем bootargs из вывода printenv и меняем там параметр init, после чего применяем новый конфиг через setenv.

# Команда в консоли U-Boot для перехвата загрузки
# Устанавливаем переменную init=/bin/sh
setenv bootargs 'tf=0 console=ttyS1,115200n8 mem=43520K@0x0 rmem=22016K@0x2A80000 init=/bin/sh rootfstype=squashfs root=/dev/mtdblock2 rw mtdparts=jz_sfc:256k(boot),1632k(kernel),2752k(rootfs),3136k(app),384k(syscfg),32k(flag),8M@0(all)'

# Запускаем процесс загрузки
boot

Важно отметить, что команда setenv сохраняет значения переменных только в рамках текущей сессии, и после перезагрузки изменения пропадут (для чистоты эксперимента - в самый раз).

После загрузки мы получили root (/ #). Но система в состоянии комы: ничего не смонтировано, драйверов нет, сервисы мертвы. Ну... значит попробуем оживить её вручную.

Этап 3: Художественный фильм - "Сдампили"

Прежде чем мы начнем ковырять файлы инициализации, необходимо сделать полный дамп прошивки. Если камера "окирпичится", это будет наш единственный билет обратно.

Используем программатор CH341A и SOP8-прищепку, чтобы подключиться напрямую к чипу памяти GD25Q64C.

Важно не забыть предварительно обесточить плату, отключив штатный шлейф питания. Программатор сам подаёт напряжение на чип, и может работать в двух режимах 5V и 3.3V - не забываем проверить информацию о рабочем напряжении памяти, и переключить режим перемычкой на плате программатора, прежде чем подключаться к памяти.

(Часто бывает, что память работает на 1.8V, и для таких случаев нужен понижающий адаптер. Благо, что для CH341A это довольно типовой "обвес", поэтому его купить можно на любом маркетплейсе.)

Считываем все 8 Мб памяти с помощью NeoProgrammer (или аналогичной программы) и обязательно делаем проверку целостности получившегося дампа кнопкой Verify IC - программатор ещё раз прочитает данные с чипа, а затем побитно сравнит исходный и контрольный дамп. Если при чтении и при проверке получили "Success" - сохраняем дамп. Если видим ошибки, значит контакт был нестабильным и данные записались некорректно. Обычно, в таких случаях нужно установить прищепку получше и попробовать ещё раз. На это может уйти не одна попытка, но на мой взгляд это всё равно в разы удобнее и быстрее, чем выпаивать микросхему, снимать дамп, и потом припаивать обратно.

Снятие дампа напрямую с Flash-памяти
Снятие дампа напрямую с Flash-памяти
Скриншот из NeoProgrammer: успешное считывание и валидация дампа
Скриншот из NeoProgrammer: успешное считывание и валидация дампа

Дамп сохранен. Теперь можно действовать смелее.

В загрузчике U-Boot переменная bootargs заботливо хранила подробную карту разделов в памяти: mtdparts=jz_sfc:256k(boot),1632k(kernel),2752k(rootfs),3136k(app),384k(syscfg),32k(flag),8M@0(all). На основе этих данных и более детального вывода binwalk мне удалось составить точную карту разделов.

Карта разделов SPI Flash (8 MB)

Смещение (HEX)

Размер (KB)

Раздел MTD

Содержимое по данным Binwalk

Описание

0x000000

256

mtd0

U-Boot / SPL (сигнатуры JBOOT, LZO)

Загрузчик и инициализация железа

0x040000

1632

mtd1

uImage (Linux Kernel 3.10.14)

Сжатое ядро ОС Linux

0x1D8000

2752

mtd2

SquashFS (RootFS)

Корневая система (Read-only)

0x488000

3136

mtd3

SquashFS (App)

Бинарники вендора (в т.ч. initApp)

0x798000

384

mtd4

JFFS2 (SysCfg)

RW раздел. Хранит в основном конфиги

0x7F8000

32

mtd5

Raw Data (Flag)

Системные флаги и сброс настроек

0x000000

8192

mtd6

Full Dump

Весь образ целиком

Этап 4: Эволюция окружения - от "комы" к живой системе

Оказавшись в "голой" ОС через эксплойт U-Boot, нужно было найти способ штатно запустить систему с монтированием всех разделов, запуском служб и т.д., но при этом сохранить за собой права root.

Немного покопавшись в системе из-под root (всё ещё через UART-консоль и подцепленные к плате провода) мне удалось обнаружить скрипт инициализации /etc/init.d/rcS. Этот скрипт выполняется при старте системы, о чём нам заботливо подсказывает /etc/inittab:

# Фрагмент /etc/inittab
# now run any rc scripts
::sysinit:/etc/init.d/rcS

Более подробный взгляд на содержимое /etc/init.d/rcS выявил Уязвимость №2 (Логический бэкдор прямо от китайских разработчиков):

# Фрагмент /etc/init.d/rcS
# mount /var/syscfg
mkdir -p /var/syscfg
mount -t jffs2 /dev/mtdblock4 /var/syscfg

# start test.sh
if [ -f /var/syscfg/test.sh ];then
  sh /var/syscfg/test.sh &
else  # start boot.sh
  sh /bin/boot.sh &
fi

Разработчики оставили прекрасный хук! Если в разделе /var/syscfg (который, в отличие от read only корневой системы, смонтирован в JFFS2 и доступен для записи) существует файл test.sh, система выполнит его ВМЕСТО штатного boot.sh. Эти строчки в /etc/init.d/rcS буквально кричат "ЗАНОСИТЕ СЮДА ВАШ БЭКДОР!"

Ручная сборка стенда

Но наша система пока всё ещё в коматозном состоянии, и в ней ничего не происходит. Поэтому, руководствуясь порядком команд из /etc/inittab, я вручную поднял систему, чтобы получить живое окружение:

/sbin/swapoff -a
mount -t tmpfs tmpfs /dev
mkdir -p /dev/pts
mkdir -p /dev/shm
mount -a
hostname -F /etc/hostname
/bin/sh /etc/init.d/rcS

Система загрузилась штатно. Запустились все сервисы (веб-сервер, трансляция RTSP, облачные демоны и т.д.). Это уже большой прогресс! С каждым шагом становится понятнее как тут вообще всё устроено, и "магия" становится просто набором скриптов и команд.

В UART тут же полетел спам логов от всевозможных сервисов. Из-за этого стремительного потока невероятно полезной информации, команды приходилось отправлять "вслепую" - пока вводишь команду, она визуально уже "улетела" куда-то вверх вместе с логами. На это нужно просто забить, и допечатав команду (или вставив команду из буфера) смело нажимать Enter - команда выполнится.

Чтобы комфортнее взаимодействовать с подопытным, я подключился к Wi-Fi точке доступа, которую раздаёт камера, после чего поднял telnetd на самой камере:

telnetd -l /bin/sh -p 23 &

Кроме того, выяснилась неприятная деталь: при штатной инициализации камера поднимает незапароленную точку доступа для первоначальной настройки со смартфона. Оставлять её открытой - значит потенциально пустить кого угодно в свою root-консоль.

Меня такой расклад не устроил, и я нашёл решение - на лету дописываем настройки WPA2 в конфигурацию hostapd и перезапускаем демон точки доступа:

echo "wpa=2" >> /var/hostapd.conf
echo "wpa_passphrase=MySecretPassword123" >> /var/hostapd.conf
echo "wpa_key_mgmt=WPA-PSK" >> /var/hostapd.conf
echo "wpa_pairwise=TKIP CCMP" >> /var/hostapd.conf
echo "rsn_pairwise=CCMP" >> /var/hostapd.conf
killall hostapd && hostapd -B /var/hostapd.conf

(Опционально: на этом этапе, когда вся файловая система уже смонтирована, мы можем сделать бэкапы разделов на вставленную SD-карту с помощью cat /dev/mtdX > /mnt/mmc/mtdX.bin, где X - номер нужного раздела).

После активации режима точки доступа (AP Mode) камера поднимает DHCP-сервер и назначает себе статический IP-адрес шлюза точки доступа. В логах мы уже видели вот такая строку, где можно этот самый адрес и увидеть:

00:00:03.336 08 CONET> loadNetIni,2844] net support:eth0=1 ra0=1 bStaticIpFlag=0 gs_cAp0GwIpv4=172.50.4.1

Поэтому всё - подключаемся к Wi-Fi с паролем, и залетаем в root shell по telnet 172.50.4.1 словно к себе домой.

Этап 5: Автоматизация и закрепление бэкдора

Теперь, когда концепт доказан, мы напишем скрипты, которые камера будет исполнять при каждом включении сама. Для гибкости и удобства мы разделим логику на загрузчик (сохраняется во внутреннюю память и остаётся там даже после перезагрузки) и полезную нагрузку (хранится на SD-карте для удобства редактирования).

1. Создаем загрузчик test.sh:
Чуть позже мы поместим этот загрузчик в /var/syscfg/test.sh. Скрипт первым делом запускает штатную загрузку камеры (/bin/boot.sh), а затем раз в секунду в течение 30 секунд "пингует" наличие смонтированной SD-карты и скрипта с бэкдором на ней. Если находит - выполняет скрипт (с root правами), а если не находит (не вставлена SD-карта или на ней нет скрипта) - просто ничего не делает, чтобы всё работало как обычно.

#!/bin/sh
# Запускаем штатную загрузку камеры
sh /bin/boot.sh &

# Проверяем наличие на SD-карте файла с командами
# Если файл найден - выполняем
timeout=30
while [ $timeout -gt 0 ]; do
    if [ -f /mnt/mmc/backdoor.sh ]; then
        sh /mnt/mmc/backdoor.sh &
        break
    fi
    timeout=$((timeout-1))
    sleep 1
done

2. Создаем Payload backdoor.sh (на SD-карте):
Этот скрипт открывает Telnet-порт 23, отдавая нам root shell, и защищает заводскую точку доступа Wi-Fi паролем.

#!/bin/sh
# Поднимаем root-консоль
telnetd -l /bin/sh -p 23 &

# Ждем формирования конфига точки доступа
timeout=60
while [ $timeout -gt 0 ]; do
    if [ -f /var/hostapd.conf ]; then
        break
    fi
    timeout=$((timeout-1))
    sleep 1
done
sleep 1

# Перезапускаем точку доступа, 
# предварительно установив на неё пароль
killall hostapd
{
echo "wpa=2"
echo "wpa_passphrase=MySecretPassword123"
echo "wpa_key_mgmt=WPA-PSK"
echo "wpa_pairwise=TKIP CCMP"
echo "rsn_pairwise=CCMP"
} >> /var/hostapd.conf
sleep 1
hostapd -B /var/hostapd.conf &

Инжект:
Используя SD-карту и наш временный root-доступ через UART, копируем скрипт test.sh в системный раздел смонтированный в read-write режиме:

cp /mnt/mmc/test.sh /var/syscfg/test.sh
chmod +x /var/syscfg/test.sh
sync
sync

Перезагружаем устройство с установленной "волшебной" SD-картой, и идём открывать шампанское (и telnet).

Подключаемся к (уже запароленной) Wi-Fi точке доступа, открываем терминал (в моём случае Powershell), подключаемся к камере по telnet 172.50.4.1 и получаем root-shell:

Подключаемся к Wi-Fi и готовим telnet
Подключаемся к Wi-Fi и готовим telnet
Получаем root shell
Получаем root shell

Всё, теперь можно отключаться от UART и собирать камеру обратно в корпус. Дальнейшее исследование системы куда удобнее продолжать через беспроводной root shell, чем через проводной UART.

Итоги

Для конечного пользователя типовое IoT-устройство обычно выглядит как абстрактный "чёрный ящик", внутренняя логика которого скрыта за удобным мобильным приложением и облачными сервисами. Это нередко создает ложное ощущение закрытости и надежности системы. Однако аппаратный аудит может быстро разрушить эту иллюзию.

Как показала практика, за фасадом обычного бытового гаджета скрывается старый добрый Linux и классический стек технологий, изобилующий стандартными точками входа и логическими ошибками:

  • Нераспаянный, но активный UART-интерфейс на плате

  • Незаблокированный загрузчик U-Boot с возможностью изменения bootargs

  • Отсутствие верификации загрузочных скриптов (оставленный разработчиками хук test.sh в RW-разделе)

  • Использование устаревшего ПО с банальными уязвимостями конфигурации (веб-сервер с открытым корнем SD-карты и Path Traversal)

Громкие истории про "взлом сети через умный чайник" перестают казаться хакерской магией, когда понимаешь, что в их основе могут лежать вот такие архитектурные недочеты, кривые конфиги и оставленные на производстве отладочные бэкдоры.

Напоследок приведу схему, демонстрирующую пройденные этапы и общую последовательность загрузки устройства.

Этапы исследования:


Camera
   │
   ├─ UART → U-Boot
   │        │
   │        └─ bootargs → init=/bin/sh
   │
   ├─ root shell
   │
   ├─ анализ скрипта rcS
   │
   └─ /var/syscfg/test.sh
           │
           └─ backdoor

Последовательность загрузки устройства:

SPI flash
   │
   └── U-Boot
          │
          └── Kernel
                 │
                 └── /etc/inittab
                        │
                        └── /etc/init.d/rcS
                               │
                               └── /var/syscfg/test.sh
									 │
									 └── /mnt/mmc/backdoor.sh
										   │
										   └── /bin/boot.sh

Упомянутые в статье скрипты, конфиги, дамп прошивки и логи в исходном виде можно посмотреть здесь:

Ссылка на GitHub

Бонус

В процессе изучения конфига веб-сервера boa.conf я заметил вот такой параметр - DocumentRoot /mnt/mmc, который говорит нам о том, что корневая директория веб-сервера это... корневая директория SD-карты! Вероятно, файлы с SD-карты раздаются веб-сервером через простые GET запросы.

Уязвимость №3: после короткого теста через Postman была найдена и подтверждена классическая уязвимость Path Traversal.

Уязвимость возникает из-за того, что веб-сервер раздаёт файлы из директории /mnt/mmc, но не фильтрует последовательности ../ в URL.

URL адрес запроса, составленный определённым образом, позволяет выйти за пределы DocumentRoot, и веб-сервер (который в данном случае имеет root-права) любезно отдаст вам совершенно любой файл из системы.

Даже без физического вмешательства и разборки корпуса камеры, потенциальный злоумышленник, находясь в одной Wi-Fi сети с устройством, может скачать любые файлы, которые лежат в основной файловой системе ОС камеры или на подключённой к ней SD-карте (записи видео, логи, фото, хеши паролей из /etc/shadow, и т.д.).

В качестве демонстрации получим /etc/shadow через GET запрос на адрес http://172.50.4.1/../../../../etc/shadow :

Классика - Path Traversal
Классика - Path Traversal

Комментарии (17)


  1. SHUstri
    17.03.2026 06:00

    Спасибо за такие статьи.
    Ничего не понял, но как будто прикоснулся к чему-то прекрасному и по-настоящему инженерному, а не этому вот ИИ-всему.


  1. lelik363
    17.03.2026 06:00

    Обязательно ли нужен прямой доступ к плате камеры, чтобы проделать все эти манипуляции?


    1. sqooph
      17.03.2026 06:00

      Нет, можно вообще не покупать а прям в приложении WB реверсить.


    1. x0ttab Автор
      17.03.2026 06:00

      В данном случае, первостепенной задачей для меня было получение постоянного root доступа по сети, чтобы исследуемую железяку можно было видеть не только снаружи, но и изнутри: смотреть запущенные процессы, знать какие порты слушаются, что в логах видно, и так далее. И, разумеется, чтобы можно было отключиться от UART, собрать камеру обратно в корпус, и заходить под root без танцев с бубном проводами.

      Поэтому, чтобы сделать это быстро (и не искать уязвимости вслепую) - думаю, что доступ к плате всё же нужен.


  1. thereisnocolor
    17.03.2026 06:00

    Господи, как же это хорошо. Понятно, просто, со сниппетами и скринами. Больше спасибо!


  1. VsBirdEye
    17.03.2026 06:00

    Зачастую анализ прошивки от устройства, если удается ее найти, дает еще массу векторов для атаки и закрепления - например, hardcoded пароли которые "чисто случайно" оказываются еще и паролями от встроенного root аккаунта.
    А весь доступный веб-интерфейс и api у устройства при тщательном тестировании на типовые уязвимости добавляет еще тележку дыр.
    Вообще у меня порой возникает ощущение, что "дырявость" китайских устройств это не столько недостаток квалификации разработчиков, сколько осознанная политика - чем больше дырявых устройств по миру, тем проще через них получать доступ, собирать информацию.


    1. thereisnocolor
      17.03.2026 06:00

      Не хотите ли написать соответствующую статью? Например за основу взять прошивку от какого-нибудь устройства Xiaomi, в силу их распространенности.


    1. NutsUnderline
      17.03.2026 06:00

      как в теории там все дырявое, а как на практике - еще выискать надо.


  1. NutsUnderline
    17.03.2026 06:00

    для экспериментов еще дешевле можно взять вообще отдельно модуль камеры, без корпуса и даже без объектива. но использовать arduino вместо копеечного преобразователя - usb uart это уже кроилово

    собственно я озадачился подобной задачей, однако реверсер из меня так себе, но я был "хитрый" и взял модуль который заведомо можно перепрошивать. Правда внезапно был пароль на uboot, но его тоже уже на дизасмили до меня.

    в результате я потратил время на неуспешные игрища с хешем рутового пароля , без поиска таких вот "тонких" моментов. зато появились дополнения по прошивки камер в OpenIPC


  1. NutsUnderline
    17.03.2026 06:00

    кстати я вот точно так же тисками держал плату и повредил индутивнность распаянную на самом краю платы


    1. x0ttab Автор
      17.03.2026 06:00

      Я тоже переживал, чтобы ничего не сломать случайно, но, вроде бы, обошлось :) Если под рукой есть более щадящий и аккауратный инструмент для фиксации платы, то конечно, лучше тисками не пользоваться.


  1. chyvack
    17.03.2026 06:00

    OpenIPC на неё нельзя залить?


    1. NutsUnderline
      17.03.2026 06:00

      для этого гораздо лучше зайти на сайт OpenIPC и посмотреть на какие камеры можно (и на какие нельзя)


      1. chyvack
        17.03.2026 06:00

        в том и дело, что openIPC есть поддержка

        Ingenic T31AL
        Ingenic T31L
        Ingenic T31N
        Ingenic T31X
        Ingenic T31ZL
        Ingenic T31ZX, про Ingenic XBurst T31 ничего не сказано, гугл говорит Ingenic T31N Стандартная (Normal) Сбалансированный вариант для массовых камер. Часто встречается в модулях с разрешением 4Мп (2560x1440) при 20 к/с.


        1. NutsUnderline
          17.03.2026 06:00

          нужно же только чуть погуглить дальше

          https://github.com/OpenIPC/device-mjsxj03hl/blob/master/Manual_ru.md

          https://wiki.openipc.org/en/installation.html#step-1-determine-the-system-on-chip

          В нашем случае он имеет численно-буквенную маркировку. Ingenic T31N. Буква N - серия. Она указана во втором ряду.

          букву знать важно потому что u-boot под разные буквы а прошивка общая брать здесь https://github.com/OpenIPC/firmware/releases/tag/latest

          тут она даже с картинкой, вместе с руководством https://github.com/OpenIPC/wiki/blob/master/en/installation.md

          самое прикольное что шить можно с microsd карты

          https://github.com/OpenIPC/wiki/blob/master/en/ingenic-t31-unbrick-with-sd-card.md

          насколько они вообще поддержаны смотрим https://openipc.org/cameras/vendors/ingenic

          видим что большинство камер на t31 поддержаны хорошо

          https://github.com/OpenIPC/wiki/blob/master/en/guide-supported-devices.md

          видим несколько камер на t31, внутренности можно по фоткам сравнить

          так что уточняем букву и скорее всего шьем не моргнув глазом


  1. zompin
    17.03.2026 06:00

    А можно ли перепаковать образ залив в него новое/изменив чуществующее?


    1. NutsUnderline
      17.03.2026 06:00

      технически да. будет ли там место - не факт