FPGA - синхронизировать «очень близкие» часы от сигнала

Это скорее учебный вопрос, я могу решить проблему, но было бы хорошо знать, как это сделать - можно ли восстановить часы по сигналу, и легче ли это, когда частота часов в основном известна?

Я использую плату Terasic DE10 Lite, отражающую видео с Mac SE/30 (512x342x1bpp) на VGA-дисплей. Соединения Mac представляют собой vsync, hsync и пиксели с аналоговой платы, уровень преобразуется в 3,3 В, а затем подключается к GPIO платы FPGA. Разрешение 1024x768 вполне подходит, если удвоить пиксель. Получить выход VGA на частоте 60 Гц несложно, IP-блок ALTPLL на частоте 65 МГц позволяет просто подсчитать переднее/заднее крыльцо и синхронизирующие импульсы.

Копирование сигнала Mac немного сложнее. Я закончил с одним @always на тактовой частоте ALTPLL, работающей на частоте 15,67 МГц (и экспериментировал с числами mult/div, чтобы попытаться максимально приблизить ее), скорость вывода пикселей Mac. Таким образом я не могу точно сопоставить тактовую частоту . Это отсчитывает вертикальный пустой период, затем для каждой строки отсчитывается до тех пор, пока не начнутся пиксели, и отсчитывается каждый пиксель. Пиксели записываются в блок двухпортовой оперативной памяти, созданной из другого блока IP, и выводятся подпрограммой VGA.

Это работает и прекрасно читается. Но это некрасиво, так как есть ошибки выборки из-за немного несовпадающих часов. Если вместо часов ALTPLL я возьму CPUCLK из разъема Mac PDS и использую его для синхронизации пикселей, все будет настолько стабильно, насколько это возможно. Используя часы FPGA, пиксели нестабильны и случайным образом меняются там, где они не должны.

Вопрос в том, что вы делаете, если вы не можете взять системные часы? Я думаю, что должен быть какой-то способ динамической настройки частоты и фазового сдвига на основе входных данных, но я не знаю, где искать.

(этот вопрос не получил ответа на Stack Overflow, возможно, он лучше подходит здесь)

Ответы (2)

Никакие два часа никогда не будут идеально совпадать. Метод определения истинной тактовой частоты по данным называется «восстановление тактовой частоты».

Если вы знаете номинальную скорость передачи данных, то один простой метод, не требующий использования блока PLL/DCM, заключается в избыточной выборке данных и поиске фронтов. Обычно вам нужно будет увеличить скорость выборки как минимум в 4 раза по сравнению с битрейтом. Вот как это работает...

  1. Создайте в своей части часы с битрейтом в 4 раза выше. В случае битрейта 65 МГц это тактовая частота 260 МГц.

  2. При использовании тактовой частоты 260 МГц двойная или тройная регистрация входящих битов во избежание проблем с метастабильностью. Проблемы такого типа могут возникать, если входной сигнал изменяется очень близко к фронту тактового сигнала. Это почти гарантированно произойдет при выборке данных с использованием другого тактового генератора, из которого данные были сгенерированы.

  3. При желании выполните два дополнительных этапа регистрации и проголосуйте 2 из 3 большинства на последних трех этапах. Это уменьшит ложное обнаружение фронтов из-за шума, что становится важным на следующем шаге, поскольку вы используете фронты в данных для определения тактовой частоты.

  4. Создайте двухбитный счетчик, который считает от 0 до 3, а затем возвращается к 0. Счетчик тактируется тактовой частотой 260 МГц.

  5. Всякий раз, когда вы видите переход от 0 к 1 или от 1 к 0 во входных данных, предположите, что вы находитесь на фронте тактового сигнала, и сбросьте счетчик на 1 (cnt <= "01").

  6. Всякий раз, когда счетчик имеет значение 2 (cnt = "10"), используйте результат вашего большинства голосов в качестве входного образца. И если вы сохраняете количество пикселей, также увеличьте его.

Я лично использовал описанный выше метод для успешного восстановления часов на последовательных данных со скоростью до 100 Мбит/с.

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

Для более низкой скорости передачи данных вы увидите что-то вроде...
...0,1,2,3,0,1,2,3, 0,1,1,2,3 ,0,1,2,3, 0,1,2,3...

Для более высокой скорости передачи данных вы увидите что-то вроде...
...0,1,2,3,0,1,2,3, 1,2,3 ,0,1,2,3,0,1, 2,3...

Существует еще один метод, при котором вы можете выполнить 4-кратную передискретизацию, используя два тактовых сигнала, которые имеют ту же частоту, что и ваши пиксельные часы, но сдвинуты по фазе на 90 градусов. Выполняя выборку в четыре регистра (один по нарастанию и один по падению для каждого тактового сигнала), вы можете добиться того же эффекта, что и при настройке на основе счетчика, описанной выше. Максимально возможная частота пикселей для этого метода выше, но логика немного сложнее.

Проблема с восстановлением тактовой частоты с помощью разблокированной передискретизации заключается в том, что она требует частых переходов, поскольку точность, с которой может быть измерена ширина области без переходов, ограничена погрешностью согласования независимых тактовых импульсов. Таким образом, это, вероятно, будет хорошо работать для строки сканирования, содержащей текст. Но на пустой строке с декоративной ограничивающей рамкой всего один или два пикселя с каждой стороны, это было 490 пикселей между ними или 492? Даже доля процента ошибки в сопоставлении часов приведет к тому, что правый край строк без текста не будет соответствовать правому краю строк с ним.
Именно по этой причине практическая система предпочла бы, чтобы монитор, который он заменяет, блокировал PLL на частоте, кратной частоте горизонтальной синхронизации, и анализировал переходы данных только в статистическом смысле, чтобы найти количество точечных часов между синхронизациями и потенциально дробное смещение синхронизации относительно идеальной позиции выборки для первого пикселя. Возможно, в ограниченном случае с одним источником и видео с низким разрешением с двумя состояниями эта разблокированная передискретизация может работать; но это не то, что есть в обычном продукте, таком как ЖК-монитор с четкими оттенками серого или карта захвата. У FPGA наверняка есть PLL.
@ChrisStratton Для 768 строк x 60 кадров в секунду частота HSYNC, вероятно, будет около 46 кГц. Они используют плату Terasic DE10, на которой установлена ​​FPGA 5CSXFC6D6F31C6N. Минимальная входная частота PLL на этой FPGA составляет 5 МГц, что в 100 раз превышает частоту HSYNC. Поэтому они не могут подавать HSYNC непосредственно в PLL, а поскольку это демонстрационная плата COTS, нельзя легко добавить внешнее оборудование PLL, которое будет принимать более низкую частоту. Я не уверен, как они заставят PLL работать в их случае.
Это действительно небольшая загадка для PLL. Однако, хотя ваша идея восстановления часов, возможно, может привести к читаемому тексту, она не приведет к выравниванию, если автономные часы не будут достаточно точными, чтобы исходная проблема неправильного чтения текста не была проблемой. Возможно, потребуется добавить внешний PLL, возможно, перемноженный внутри. На самом деле эти демонстрационные платы имеют разъемы, разработанные специально для поддержки дополнительных внешних схем.
@ChrisStratton Та же идея счетчика может быть применена к HSYNC вместо данных, чтобы избавиться от проблемы с пустыми данными. Сделайте 13-битный счетчик с 4-кратной частотой пикселей. Используйте этот счетчик для подсчета длины HSYNC с точностью до четверти пикселя. Во время каждой строки сканирования предыдущий отсчет используется для преобразования текущего отсчета в смещение пикселя, которое можно использовать для выборки и сохранения данных пикселя. Логика определения положения пикселя по двум счетчикам — это просто логика добавления/вычитания. Соблюдение времени становится немного сложнее, поскольку теперь у нас будут большие счетчики на высокой частоте.
Это может быть что-то сужено: я думаю, что вы говорите, что нужно запустить тактовую частоту в 4 раза по сравнению с приблизительной точечной тактовой частотой, а затем использовать измеренное количество тактовых импульсов между предыдущими синхронизациями по сравнению с ожидаемой долей ошибок, которая приводит к добавлению /пропуск четверти периода время от времени. К счастью, точечные часы OP довольно медленные по сравнению с возможностями FPGA, они, вероятно, могут увеличиться в 8-10 раз.
@ChrisStratton Я немного думал об этом. Тоже кажется приемлемым вариантом. Я знаю, что некоторые PLL поддерживают динамическое смещение фазы. В основном можно было бы просто найти числа умножения/деления PLL, которые были бы ближе всего к кратности HSYNC, а затем использовать логику счетчика передискретизации (как указано выше), чтобы подтолкнуть фазу. Это может иметь некоторые преимущества в том, что другие части конструкции становятся проще, когда у вас есть настоящие пиксельные часы для работы вне PLL.

Было бы полезно немного подумать о том, как видеокарта на самом деле формирует свои выходные сигналы.

См., например, модель XFree86. Вот один для 1024x768 @ 60 Гц (без чересстрочной развертки) из онлайн-инструмента генератора , детали зависят от реализации, но идея применима практически ко всем компьютерам и видеорежимам.

Dot Clock Frequency:     60.80 MHz 
Modeline "1024x768" 60.80  1024 1056 1128 1272   768  768  770  796

У вас есть часы пикселей, область активного видео, сигнал синхронизации, определенный как его начало и конец, и общее количество часов в периоде строки, в этом примере 1272. Все они выражаются в единицах часов пикселей, которые это означает, что все восходит к пиксельным часам и делает это согласованным в цифровом отношении способом.

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

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

Как можно узнать номера моделей? Ну, вы лично , вероятно, могли бы поискать их.

Я подозреваю, что современный пиксельный (ЖК-монитор и т. д.) монитор, работающий от аналогового источника, выполняет что-то вроде «поиска», когда вы нажимаете кнопку настройки изображения. Разрешение по горизонтали, наверное, нетрудно угадать, а продолжительность активного видео можно измерить. Затем вы можете измерить отношение общего периода горизонтальной развертки к активному видео, и из этого вы узнаете приблизительное общее количество тактовых импульсов пикселей в модельном ряду — например, в моем примере 1272 определяется пропорционально времени 1024. Таким образом, вы блокируете свой PLL при предположении 1272 (или около того).

Затем вы пробуете различные числа вокруг этого и выполняете какое-то сравнение, чтобы увидеть, при каком из выбранных вами данных кажутся «лучшими», где «лучший» может быть определен как что-то вроде показа наибольшего среднего значения разницы между пикселями на уровне последовательных пикселей около обе стороны экрана, указывая на то, что сэмплирование хорошо выровнено по середине периодов пикселей и не улавливает промежуточные переходы между ними, и делает это по всему экрану так, чтобы оно совпадало как по фазе, так и по частоте. Или, может быть, он просто проверяет, что активная область имеет точно нужное количество тактовых импульсов в пикселях. Но если вы можете позволить себе генерировать часы, которые, скажем, в 3-6 раз превышают реальные пиксельные часы,

Вероятно, этот анализ — это то, что вы могли бы сделать с программным обеспечением на ядре процессора (внутренним или внешним по отношению к FPGA), которое позволяет совать регистры, которые управляют вашим конечным автоматом захвата, и запускать статистику не в реальном времени для замороженного буфера строки; например, аппаратное обеспечение для захвата можно рассматривать как цифровой прицел.