nabbla (nabbla1) wrote,
nabbla
nabbla1

Categories:

Счётчик в кодах Грея - окончание

Начало, продолжение

Осталось за малым: всё-таки реализовать "обычный режим", где дойдя до крайнего значения, счётчик сразу перескакивает в начальное, без хитрого реверса, который мы наблюдали вчера. А ещё сделать разрешение работы clk_en и вход синхронной загрузки. И проверить, что всё работает и при другом количестве бит.


Изменения, в общем-то, не очень большие:

module GrayCodeCounter (input clk, input clk_en, input sload, input [Width-1:0] D,
			output reg [Width-1:0] Q = 1'b0,
			output Ddummy);
parameter Width = 4;
parameter NoReverse = 1'b1;	//если 1, то за 1000..000 идёт сразу 0000..000,
//в противном случае ещё на такт застревает в 1000..000 и начинает идти в обратную сторону,
//затем на 2 такта застревает на 0000..000 и снова вперёд

reg dummy = 1'b0;	//вводим дополнительный бит справа, "контрольная сумма", такая, что сумма всех битов всегда должна быть чётной
assign Ddummy = dummy;

wire [Width-1:0] carryChain;

assign carryChain[0] = ~dummy;

genvar i;
generate
  for (i=1; i<Width; i=i+1) begin	:take_your_stupid_name
    assign carryChain[i] = carryChain[i-1] | Q[i-1];
  end
endgenerate

wire [Width-1:0] T_input;

assign T_input[0] = ~dummy;
assign T_input[Width-2:1] = Q[Width-3:0] & (~carryChain[Width-3:0]);
assign T_input[Width-1] = (Q[Width-2] | NoReverse) & (~carryChain[Width-2]);

always @(posedge clk) if (clk_en) begin
	dummy <= sload? ^D : ~dummy;
	Q <= sload? D : Q^T_input;
end

endmodule


Вход clk_en позволяет запретить любое изменение на выходе, будь то счёт или параллельная загрузка.
Когда sload=1, то вместо счёта загружается значение с входа D.

Главная хитрость в том, что нужно правильно инициализировать бит dummy, иначе можем "случайно" начать считать не в ту сторону.

Не так давно узнал о таком вот синтаксисе верилога:
^D


Где D - это шина. Это означает "горизонтальный" XOR, т.е D[Width-1]^D[Width-2]^...D[1]^D[0]. Удобно, не нужно городить очередной for или generate хотя бы здесь :)

Не стал начисто "убивать" свой старый вариант с реверсом, вместо этого ввёл параметр NoReverse и значение по умолчанию: "1". Как это реализовано - видно, когда NoReverse=1, старший разряд больше не обращает внимание на значение второго по старшинству, поэтому и при "нолике", и при "единичке" переключится, главное, чтобы все остальные разряды, включая dummy, содержали нули.

Теперь при Width=4 этот модуль синтезируется в 10 ЛЭ. Многовато, можно было при правильном использовании добиться 5N/4+1 для N разрядов (N ЛЭ на N бит, плюс фиктивный бит, плюс "горизонтальный XOR" для него), но увы.


Проверим для начала работу clk_en и режим "без реверса":


Всё верно: пока clk_en=0, вообще ничего не делаем, потом приступаем. Дойдя до 8 = 4'b1000, сразу переключаемся в 0 = 4'b0000, и повторяем всё то же самое, как ни в чём не бывало.

Теперь ещё опробуем синхронную загрузку:


Видно, что dummy, вместо того, чтобы переключиться в очередной раз, стал равным "чётности" поступившего значения E = 4'1110, т.е 1. И как видно, счёт продолжился в правильном направлении, что не может не радовать.

И глянем Width=8. Увы, отсинтезировалось оно в 25 ЛЭ, слишком много на мой вкус. Ну хорошо, не смог один бит вместить в 1 ЛЭ, вместил в 2 ЛЭ, это было бы 16, плюс "фиктивный бит" dummy, это 17. Плюс логика "горизонтального XOR" между 8 значениями - это ещё 3 ЛЭ, итого 20. Как так-то?? Но хотя бы работает правильно:

И предельная частота для моей ПЛИС 5576ХС4Т: 76,92 МГц, худо-бедно.

Главного достигли: получили параметризуемый модуль. Можно задавать Width от 3 и вверх. Вообще, могли бы сюда включить очередной generate, чтобы отдельно рассмотреть случаи 1 и 2, "оставим это читателю в качестве упражнения".

Остаётся вопрос: а нафига вообще он нужен? Ну, я хочу с ним один опыт провернуть, но возможно чуть позже...
Tags: ПЛИС, работа, странные девайсы
Subscribe

  • Так есть ли толк в ковариационной матрице?

    Задался этим вопросом применительно к своему прибору чуть более 2 недель назад. Рыл носом землю с попеременным успехом ( раз, два, три, четыре),…

  • Big Data, чтоб их ... (4)

    Наконец-то стряхнул пыль с компьютерной модели сближения, добавил в неё код, чтобы мы могли определить интересующие нас точки, и выписать…

  • Потёмкинская деревня - 2

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

  • Великая Октябрьская резня бензопилой

    Сегодня прокатился прочистить Абрамцевскую просеку. Как обычно, с приключениями. Выезжал на велосипеде, а вернулся на самокате. Первый раз по этим…

  • Очередная несуразность в единицах измерения

    Когда-то я написал программу PhysUnitCalc - калькулятор, умеющий работать с размерностями. Мне казалось, что я наступил уже на все грабли, которые…

  • Big Data, чтоб их... (3)

    "В предыдущих сериях": мой прибор выдаёт 6 значений: 3 координаты и 3 угла, т.е все 6 степеней свободы твёрдого тела. Причём ошибки измерения этих 6…

  • Post a new comment

    Error

    Anonymous comments are disabled in this journal

    default userpic

    Your IP address will be recorded 

  • 0 comments