Версия 1.1.9 · для тех, кто хочет цифр

ТЕХНИЧЕСКИЙ РАЗБОР

Что у плеера внутри — с числами и методикой проверки. Каждое утверждение на этой странице стоит на коде или на замере с живого устройства. Если нужна инструкция «что нажать» — она в мануале, простым языком.

VULAN

Свой USB-драйвер: UAC2 без root

Не обёртка над системным API, а собственный стек USB Audio Class 2.0. Плеер получает у Android разрешение на USB-устройство, забирает аудио-интерфейсы у ядра (claim с отцеплением штатного драйвера), разбирает дескрипторы конфигурации сам — ищет audio-streaming интерфейсы и выбирает альтернативную настройку под нужную частоту и разрядность — и качает изохронные пакеты через libusb. AAudio и системный микшер в тракте не участвуют.

Частота следует за файлом: 44,1 кГц играет как 44,1, hi-res 192 — как 192, без пересчёта в общую частоту. Потолок 384 кГц. Разрядность — какую объявил ЦАП: 16, 24 или 32 бита; внутренний формат — 32-битное целое, для CD-звука выход байт-в-байт.

Асинхронный режим — настоящий. В дескрипторах отыскивается feedback endpoint; если он есть, темп подачи подстраивается под кварц ЦАПа, а не наоборот. Если у железа обратной связи нет — плеер пишет об этом в журнал честно, а не делает вид.

Громкость — в регистре ЦАПа. Запрос по UAC2 крутит аппаратный регистр (64 ступени, шкала в 1/256 дБ), музыка при этом не пересчитывается — биты нетронуты на любом уровне.

Паспорт ЦАПа. Полный разбор дескрипторов подключённого устройства показывается на экране: интерфейсы, форматы, частоты, наличие обратной связи — и отчёт о каждом потоке: кадров отдано, недоборы, пакеты OK/ошибки, сколько сэмплов изменено обработкой, нагрузка на ядро.

Про совместимость честно: обещаний по моделям, которых у нас не было в руках, мы не даём. Формула одна — пришлите модель и журнал, посмотрим.

Декодирование

Своя сборка FFmpeg: играем всё

Собственная урезанная сборка FFmpeg по принципу «выключить всё, включить перечисленное»: 30 контейнеров, более 40 декодеров. APE, WavPack, TTA, Musepack, TAK, WMA (включая Pro и Lossless), AIFF, ALAC, Shorten, TrueHD, DTS, AC3, четыре варианта DSD — всё это играет на телефоне, которому сами эти форматы неизвестны.

Сканер видит то, что Android прячет: стандартный медиакаталог молча пропускает .dsf, .dff, .ape, .wv, .tta, .mpc, .mka, .tak, .wma, .aiff — плеер находит их сам. Теги настоящие: у DSF собственный разборщик вшитого ID3, у экзотики теги достаёт FFmpeg.

Windows-версия открывает 45 расширений. Список составлен не по памяти: каждый формат проверен в самой библиотеке — и разборщик контейнера, и декодер. Чего нет в списке — того нет честно: показывать файлы, которые не заиграют, — обман.

CUE-листы. «Один FLAC на весь диск плюс .cue» разбирается на отдельные песни: имена, исполнители, перемотка, гэплесс. Время считается в кадрах CD — 1/75 секунды, разбор покрыт тестами.

Мгновенный старт в большой фонотеке. Замер на телефоне с 2532 треками: передача очереди движку съедала 2373 мс из 2375. Теперь движку сперва отдаётся окно вокруг нажатого трека, звук стартует, остальное досылается кусками по 200 треков под уже играющую музыку.

Однобитный поток

DSD: свой разбор и децимация

Заголовок DSF читается собственным кодом, однобитный поток превращается в сверхвысокое PCM: DSD64 (2,8224 МГц) — в 176,4 кГц, DSD128 — в 352,8 кГц по той же лестнице.

Фильтр — оконный sinc Кайзера на 768 отводов, рассчитывается при открытии файла под его частоту. Свёртка развёрнута в байтовые таблицы: на телефоне это доли процента загрузки ядра.

+6 дБ по конвенции SACD добавляется при децимации — DSD-издания традиционно тише PCM. Сверх того есть отдельная ручка «Громкость DSD» 0–12 дБ под охраной true-peak лимитера: перегрузка невозможна по построению, обычные треки эта ручка не трогает никогда.

Класс файла — на экране: DSD64, DSD128, DSD256 — это говорит слушателю больше, чем голые мегагерцы. Слово bit-perfect для DSD не пишется никогда: децимация исключает побитовость по природе формата, и врать об этом мы не будем.

Обработка

DSP: вся математика в двойной точности

Весь расчёт обработок — в 64-битных числах с плавающей точкой (в нативной DSP-библиотеке 181 употребление double в 6 файлах): фильтры не копят слышимых ошибок округления даже в длинных цепочках.

Параметрический эквалайзер — до 16 полос, у каждой частота, усиление и добротность; типы фильтров bell, low shelf, high shelf. Простой эквалайзер — стандартные приборные ряды: октавный (10 полос), полуоктавный ISO (15), треть-октавный (31), усиление ±12 дБ на полосу; добротность считается из густоты ряда сама.

Честный пересчёт между рядами. Переключение 15 → 31 → 15 полос не меняет звук: наивный перенос врёт (колокола соседних полос складываются), поэтому подгонка кривой идёт заходами с половинным шагом — ошибка садится ниже 0,005 дБ за доли миллисекунды.

PEAK GUARD — лимитер с предвидением: громкость начинает опускаться за 2 мс до прихода пика, детектор восстанавливает волну между отсчётами (true-peak) — там, где клиппуют ЦАПы. Замер на худшем построимом сигнале: сырьё +2,98 дБFS, простой сторож пропускает +1,99, этот лимитер +0,61.

Реверберация — четыре зала, хвосты измерены на живом телефоне: от ≈0,6 до ≈3,4 с («Собор»). Числа залов одни на Windows и Android. Компрессор — stereo-linked RMS, максимум 6 дБ подавления, времена 60/300 мс, автоподъёма нет намеренно.

CRYSTAL: до +5,5 дБ в 10–16 кГц с обходом утомляющей зоны 2–5 кГц и мягким вычетом мутности у ~220 Гц. GRAVITY: до +12 дБ на 40–110 Гц, выше 125 Гц быстрый спад, чтобы фундамент не заслонял голос.

Правка на лету без щелчка: новый каскад фильтров подменяется плавным крестом ~20 мс в момент отправки пакета в ЦАП.

Нуль-тест тракта: выход вычитается из источника — расхождение 0,0000 дБ на миллионах отсчётов, когда обработки выключены.

EBU R128

Выравнивание громкости: мера вместо вкуса

Цель −14 LUFS — уровень стримингов; поправка ограничена ±12 дБ, подъём всегда оставляет 1 дБ запаса до полной шкалы. Лимитер при выравнивании не применяется — динамика записи не тронута.

Фонотека промеряется фоном по стандарту EBU R128; разбор приостанавливается, пока играет битовый тракт VULAN. Ползунка нет намеренно: поправка считается из измерения файла, а не из вкуса. Разбег громкости в живой фонотеке — до 17 дБ.

Эфир

Радио: рейтинг меряется у слушателя

Каталог: 314 проверенных станций «Россия» + 29 именных, 354 «Мир» + 521 именная, 118 FLAC-станций Hi-Res — каждая проверена трижды в разное время суток (55 станций 44,1/16, 34 — 48/16, 25 — 24-битных, включая три 96 кГц и одну 192/24). Плюс офлайн-книга на 62 187 станций планеты в двух мегабайтах.

Заявленный битрейт выброшен из рейтинга: собственный замер показал, что он не совпал ни у одной станции (разброс до двух раз). Плеер меряет настоящий приток сам, первые 2 секунды замер молчит, чтобы не врать; формула оценки ошибается только в худшую сторону.

Радар: «быстрый обход» — перекличка по первому байту, весь каталог до 3 минут; «глубокая проверка» слушает каждую станцию по 3 секунды живого эфира. Степень параллельности подбирается под связь сама; замеры хранятся отдельно на каждый профиль сети — Wi-Fi, мобильная, с туннелем и без. Пока слушатель ждёт звука включённой станции, фоновая проверка не начинает ни одного нового запроса.

Досье: до 8 последних реальных включений станции — через сколько заиграла, рвалась ли; ноль лишнего трафика. Там, где есть досье, правда сильнее оценки радара.

Старт за 2 секунды буфера; после обрыва запас копится дольше (7 с), чтобы не было звука-тишины-звука по кругу. «Стойкий эфир» — минута запаса перед стартом. До пяти переподключений с растущими паузами; минута ровной игры обнуляет счётчик; мёртвый сервер, который принял соединение и молчит, ловится отдельным сторожем.

Метаданные эфира: кодировка icy-меток определяется сама (windows-1251 у русских станций, UTF-8 у зарубежных). Под ЦАПом кольцевой буфер вмещает до минуты эфира.

1456 станций с собственными знаками 384×384 в двух ипостасях (карточка и прозрачный знак радара), весь каталог знаков — 42 МБ, средний знак 29 КБ. Чужие логотипы с чужих доменов не используются: пустое место честнее.

Сеть

Облака: сеть равноправна с диском

Пять дверей по публичной ссылке: Яндекс Диск, Google Диск, Облако Mail, Облако Билайн и любое S3-совместимое хранилище (Beget, Selectel, Timeweb, VK Cloud, Amazon, своё собственное) — без OAuth и входа в аккаунт. Плеер видит только ту папку, ссылку на которую дали.

Сетевые адреса идут той же собственной читалкой FFmpeg, что и файлы с диска: из облака играют DSD, APE, WavPack, TTA, TAK — и уходят в ЦАП тем же битовым трактом. Перемотка работает по сети без разрыва соединения.

Быстрый старт: разведка формата по первым 500 КБ вместо пяти мегабайт по умолчанию. Гигантская обложка в теге MP3 перешагивается: длина тега читается по первым десяти байтам, чтение начинается сразу за ним. Живой случай: файл 16 МБ нёс обложку 12,96 МБ и стартовал 8,1 с — стало 2 с.

Подписанные ссылки облаков протухают — на втором часе альбома плеер сам спрашивает свежую; у Билайна очередь добирается под уже играющую музыку.

Сертификаты не ослаблены: на старых Android, не знающих новых корней, плеер несёт GlobalSign Root R6 с собой — к системным корням добавлен один известный, проверка цепочки работает целиком.

Обновления: проверка новой версии с сайта раз в сутки со сверкой отпечатка SHA-256; установка — только руками слушателя.

Принцип

Честность приборов

Две правды на экране: что записано в файле (битность читается собственным разборщиком заголовка, а не со слов декодера — тот дважды врал) и куда реально ушёл звук. У форматов, где битности нет по природе (MP3, AAC), поле честно молчит.

«VULAN • bit-perfect» горит только когда ни один бит не тронут. Гасит его любая обработка: эквалайзер, баланс от 0,05 дБ, реверберация, поправка громкости. В нативном коде буквально: если нечего применять — сэмплы не трогаются вообще.

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

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

Вопросы по существу

Спрашивайте — покажем журнал

Разговор о технике мы любим предметный: если что-то из описанного вызывает сомнение — спросите, покажем замер или код. Если на вашем железе что-то повело себя иначе — пришлите модель и журнал, разберёмся.