Одинаковая плата телевизора, другой LVDS: от зелёной полосы до Full HD
Как я адаптировал TP.T950ST.PB752(N) под родную матрицу: доступ через UART, профиль панели, два ограничения 720p и двоение из-за порядка каналов A/B.
Содержание
Я купил другую материнскую плату для телевизора. Разъёмы совпадали с оригиналом, маркировка PCB тоже: TP.T950ST.PB752(N). Но плата приехала со своим шлейфом и платой матрицы. На донорском шлейфе была задействована только часть проводов, а разъём со стороны матрицы отличался от родного.
Старая материнка окончательно вышла из строя. Считать с неё настройки уже не получилось. Я оставил родную панель, её плату и шлейф, а новую материнку стал адаптировать программно.
Сначала были подсветка, чёрный экран и широкая зелёная полоса справа. В итоге удалось получить правильное изображение Full HD и сохранить настройки после перезагрузки. Для этого пришлось решить три отдельные проблемы.
Что действительно совпадало
Похожий разъём не гарантирует одинаковой распиновки и настроек. Перед программными экспериментами я сравнил платы, шлейфы и перемычки питания. На обеих материнках была установлена R12V, а R5V оставалась пустой. Это наблюдение относится к моим платам: на другом телевизоре нужно отдельно проверить питание и назначение контактов.
| Узел | Что было в моём случае |
|---|---|
| Новая материнка | TP.T950ST.PB752(N), Amlogic TXHD2 |
| Система | Android 14, устройство t950s_be30ae |
| Оперативная память | 1 ГБ по загрузочному журналу |
| Профиль донора | GENERAL_1366_768, LVDS 8 бит, один канал |
| Родная плата матрицы | Маркировка V400HJB-P03-CG |
| Донорская плата матрицы | LC320DXJ-SHAE VESA HD |
| Рабочее подключение | Новая материнка → родной шлейф → родная плата матрицы → родная панель |
Полную модель самой родной панели я достоверно не установил. Поэтому даже совпадение PCB и маркировки платы матрицы не делает приложенные бинарные файлы универсальными.
Ethernet подтвердил загрузку, UART дал доступ
Материнка получила адрес у роутера, но ADB на порту 5555 был закрыт. Я проверил открытые TCP-порты: обнаружились WebSocket дистанционного управления, файловый HTTP-сервис и DLNA MediaRenderer.
Они подтвердили, что Android работает, но доступа к профилю панели не дали. HTTP-порт DLNA нельзя превратить в ADB, просто указав его в adb connect.
Дальше я подключил CP2102 к UART, остановил автозагрузку U-Boot и временно включил последовательную консоль Android. Через неё запустил adbd, затем подключился по сети. Сборка поддерживала adb root, поэтому появился доступ к системным файлам.
В один из моментов экран отключился, ADB перешёл в offline, а затем перестал отвечать. По UART было видно Enter ddr suspend и poweroff 5v: плата ушла в ожидание. Короткое нажатие физической кнопки вернуло её к работе. Это оказалось обычным standby, а не повреждением прошивки.
Первый барьер: профиль панели
Донор был настроен на 1366×768 и один LVDS-канал. Родной панели подошёл профиль 1920×1080 с двумя каналами.
Настройки нашлись здесь:
/mnt/vendor/param/panel/panel_customer.ini
/sys/class/aml_lcd/lcd0/
/sys/class/unifykeys/
Путь /param/panel, встречавшийся в настройках загрузчика, внутри Android отсутствовал. В дампе LCD были key_valid=1 и config_load=1: драйвер использовал бинарный LCD-ключ unifykey.
Я сохранил исходные INI, LCD-ключ и environment U-Boot. Затем проверил подходящие параметры временно через sysfs. Изображение появилось, но занимало только часть экрана: изменение LCD timings во время работы не обновило всю конфигурацию DRM.
Для постоянного результата пришлось записать согласованную пару INI + LCD-ключ и перезагрузить систему. Изменение только ключа на одном из ранних этапов не сохранилось в ожидаемом виде после загрузки.
| Параметр | Рабочее значение |
|---|---|
| Активная область | 1920×1080 |
| Полный период строки / кадра | 2200 / 1130 |
| Pixel clock | 149160000 Гц |
| Частота | 60 Гц |
| LVDS | VESA, 8 бит, два канала |
Подсветку и последовательности питания я сохранил из рабочего профиля материнки. Копировать целиком случайный lvds_fhd.ini было бы неверно: в найденных профилях отличались и настройки подсветки.
Второй барьер: Android продолжал работать в 720p
Полноэкранная картинка ещё не означала полноразмерный интерфейс.
Physical size: 1920x1080
Override size: 1280x720
Команды wm size reset и wm size 1920x1080 ограничение не убирали. Проверка framework-ресурса показала причину:
.\adb.exe -s 192.168.1.197:5555 shell cmd overlay lookup --verbose android android:integer/config_maxUiWidth
Значение 1280 приходило из системного LowRamOverlay.apk. Отключить immutable overlay штатной командой не получилось даже с root. Удалять весь пакет я не стал: в нём были другие настройки.
Сначала я проверил временное переопределение ресурса, но после перезагрузки оно исчезало. Для постоянного решения установил отдельный системный overlay с единственным значением config_maxUiWidth=1920. После загрузки ограничение wm size удалось снять.
Остался ещё один предел:
ro.surface_flinger.max_graphics_width=1280
ro.surface_flinger.max_graphics_height=720
Обе строки находились в /vendor/build.prop. После резервирования файла я изменил их на 1920 и 1080 и перезагрузил телевизор. Теперь DRM показывал полноценный буфер:
size=1920x1080
crtc-pos=1920x1080+0+0
src-pos=1920.000000x1080.000000+0.000000+0.000000
Это были два разных ограничения. Снятие framework-лимита само по себе не увеличило графический буфер SurfaceFlinger.
Третий барьер: Full HD есть, а буквы двоятся
После всех исправлений картинка всё ещё выглядела странно. Скриншоты были лучше изображения на панели, на буквах появлялись повторные контуры.
Я проверил размеры слоёв SurfaceFlinger, выбранные ресурсы LauncherMars и сам APK. Лаунчер имел разметку Full HD, выбирал размеры 1920×1080 и отдавал такой же буфер. Маленькие растровые иконки действительно были мягкими, но ими нельзя было объяснить весь дефект.
Встроенный тест LCD выводил ровные цветные полосы и линии. Пробное отключение сглаживания dejaggy результата не дало. Эти проверки сузили поиск, но не доказали правильность передачи соседних пикселей.
Решающей оказалась проверка порядка каналов A/B. До неё было:
repack=1, dual_port=1, pn_swap=0, port_swap=0, lane_reverse=0
Я временно изменил только port_swap:
"1 1 0 1 0" | .\adb.exe -s 192.168.1.197:5555 shell tee /sys/class/aml_lcd/lcd0/lvds
Изображение сразу стало правильным. Затем я сохранил port_swap=1 и в INI, и в LCD-ключе, пересчитав его контрольную сумму. После перезагрузки результат сохранился.
Именно этот шаг исправил двоение. Изменения разрешения тоже были нужны, но решали другую проблему.
Что я сохранил для повторения
Подготовил полную инструкцию с доступом через UART и ADB, резервными копиями, командами диагностики, сохранением профиля и отдельными процедурами отката.
В архиве лежат инструкция для браузера, Markdown, скрипты перехода на Full HD, исправление порядка каналов, UI overlay и контрольные суммы. Скрипты сверяют текущие данные с известными хешами и отказываются писать в неизвестную конфигурацию.
Публичная версия UI overlay использует нейтральный идентификатор com.local.tv.overlay.fhdui. Она пересобрана с тем же единственным ресурсом; подпись и содержимое проверены локально. Эту пересобранную версию отдельно на телевизоре я не испытывал. LCD-профили и исправление A/B соответствуют проверенному ремонту.
Готовые LCD-профили рассчитаны только на описанную конфигурацию. Для другой панели нужны проверка напряжения, распиновки, интерфейса и собственные резервные копии. Совпадение разъёмов не отменяет эти различия.
В результате я оставил родные панель, её плату и шлейф. Новая материнка заработала с ними после настройки профиля, снятия ограничений Android и смены порядка LVDS-каналов. Полностью перепрошивать телевизор не потребовалось.