Перейти к содержанию
    

Как реализовать на Verilog'e

Вывел резет - не меняется, т.е. всегда единица.

post-41333-1359822449_thumb.jpg

 

У Вас в коде четко написано, что при значениях code от 0 до 5, сигнал reset будет равен 1.

 

 

В тестбенче у вас cnt ( который Вы используете заместо сигнала code ) принимает значения от 0 до 5.

 

Почему Вы удивляетесь, что reset всегда равен 1? :)

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

У Вас в коде четко написано, что при значениях code от 0 до 5, сигнал reset будет равен 1.

Собственно, основная проблема как написать так, чтобы счетчик сбрасывался только при обновлении значения code .

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Собственно, основная проблема как написать так, чтобы счетчик сбрасывался только при обновлении значения code .

 

Задержите code на такт. Сравнивайте задержанное и нет значения между собой. При несовпадении формируйте сигнал сброса.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Задам еще один вопрос в данную тему. Имеется следующий код:

always @(posedge clock or posedge signal) begin
    if(signal==1) begin
        vipr=1;
    end
    
    else if(vipr==1) begin
        cnt = cnt + 1;
        case(cnt)
            0: frequency=0;
            4: frequency=1;
            5: frequency=0;
            10:frequency=1;
            11:begin frequency=0; 
                    cnt=0; 
                    vipr=0; end
        endcase    
    end    

end
assign out=frequency;

Что я хочу добиться этим кодом. С приходом переднего фронта signal мне необходимо сразу же выдать два (или более импульса) на выход out. Причем длительность signal может быть больше длительности этих двух импульсов. Но почему-то в testbenche я получаю следующую картину:

post-41333-1365406541_thumb.jpg

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

И еще вопрос: можно ли в Modelsim посмотреть значение переменных?

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Правильнее анализировать состояние signal по фронту clock, и в случае если обнаружена смена состояния из 0 в 1, начинать формирование импульсов.

Формирование 1 импульса по приходу signal:

module h2d (
  input clock,
  input signal,

  output pulse
);

reg signal_reg;

always_ff @(posedge clk)
  signal_reg <= signal;

assign pulse = signal & ~signal_reg;
endmodule

Если сигнал signal асинхронен отностиельно clock, то необходимо добавить два дополнительных триггера для предотвращения возникновения метастабильного состояния на входе.

По желанию pulse можно сделать регистром, тогда выход будет привязан к clock.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

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

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

А если дописать пару строчек:

module h2d (
  input clock,  // System clock input.
  input signal, // Start signal input.

  output pulse  // Generated pulses output.
);

parameter PULSE_COUNT = 1; // Number of output pulses.
localparam PULSE_COUNT_W = $clog2(PULSE_COUNT) + 1; // Pulse counter width.

reg                   signal_reg; // Start signal detection register.
reg [PULSE_COUNT_W:0] pulse_cntr; // Output pulses counter.
logic                 start;      // Start pulses generation.

assign start = signal & ~signal_reg;

always_ff @(posedge clk)
  signal_reg <= signal;

always_ff @(posedge clk)
  if (start) signal_cntr <= '0;
  else if (~signal_cntr[$high(signal_cntr)]) signal_cntr <= signal_cntr + 1;

assign pulse = signal_cntr[0];

endmodule

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

У Вас написано на SystemVerilog, а я еще с Verilog до конца не разобрался. Поэтому попробовал записать так:

always @(posedge clock) begin
    if(signal==1) begin
        vipr=1;
    end
    
    if(vipr==1) begin
        cnt = cnt + 1;
        case(cnt)
            0: frequency=1;
            1: frequency=0;
            4: frequency=1;
            5: frequency=0;
            9: frequency=1;
            10:frequency=0;
            14:frequency=1;
            15:frequency=0;
            19:frequency=1;
            20:begin frequency=0; 
                    cnt=0; 
                    vipr=0; end
        endcase    
    end

Но всеравно, почему-то происходит отставание выходных импульсов out=frequency от входного фронта сигнала signal

post-41333-1365420912_thumb.jpg

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Ну, все, в общем-то, на поверхности лежит ;). Но чтобы не лишать вас удовольствия (да и пользы так больше будет), дам лишь подсказку - попробуйте за cnt понаблюдать, поподробнее посмотреть, что на каждом такте происходит между ним и сигналом frequency.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Еще вопрос по моему коду:

always @(posedge clock) begin
    if(signal==1) begin
        vipr=1;
    end
    
    if(vipr==1) begin
    ...
    end
end

Если signal стал равен 1 то будет ли сразу проверяться и выполняться в случае истинности условие if(vipr==1). Как я понял в случае блокового присваивания должно выполниться сразу. В отличие от не блокового, которое выполниться только со следующим приходом clock.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Если signal стал равен 1 то будет ли сразу проверяться и выполняться в случае истинности условие if(vipr==1). Как я понял в случае блокового присваивания должно выполниться сразу. В отличие от не блокового, которое выполниться только со следующим приходом clock.

 

Да, именно так все и будет - ничто не мешает в одном и том же такте выполнить присвоение vipr = 1, а затем проверить vipr на 1 и зайти внутрь этого блока.

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Разобрался почему у меня было такое большое отставание frequency от signal следующей корректировкой кода

assign posedge_signal=signal&(~previous_signal);
always @(posedge clock) begin
    previous_signal<=signal;
    if(posedge_signal) begin
        vipr=1;
    end
    if(vipr==1) begin
        cnt<=cnt+1;
        case(cnt)
            0: frequency=1;
            1: frequency=0;    
            4: frequency=1;
            5: frequency=0;
            9:    frequency=1;
            10:frequency=0;
            14:frequency=1;
            15:frequency=0;
            19:frequency=1;
            20:begin frequency=0; 
                    cnt<=0; 
                    vipr=0; end
        endcase    
    end    
end

И получил следующую картину:

post-41333-1365571774_thumb.jpg

Теперь вопрос сигнал frequency (он же out) отстает на один такт clock. Это возможно как то устранить?

И еще, сейчас попробовал записать часть кода для формирование четырех выходных импульсов короче:

always @(posedge clock) begin
    previous_signal<=signal;
    if(posedge_signal) begin
        vipr=1;
    end
    if(vipr==1) begin
        cnt<=cnt+1;
        vipr_cnt<=vipr_cnt+1;
        case(cnt)
            0: frequency=1;
            2: frequency=0;
            6: begin frequency=0; cnt<=0; end    
        endcase        
        if(vipr_cnt>5) begin
            vipr=0;
            vipr_cnt<=0;
        end
    end    
end

но почему-то не работает условие if(vipr_cnt>5).

Изменено пользователем sidy

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

winipuh, Вам, ссылку дал, из коллекции MUST read!

Почитайте и разберитесь, что там написано, многое станет понятней.

 

 

 

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Возник еще один вопрос, не могу разобраться в чем дело:

Имеется код:

    wire DistCode[2:0];
    wire DistCS;
    wire DistData;
    reg RegCS;
    assign DistCode[0]=D_A0_MCU;
    assign DistCode[1]=D_A1_MCU;
    assign DistCode[2]=D_A2_MCU;
    
    always @(posedge CLOCK_0) begin
        RegCS<=DistCS;
        if(RegCS&(DistCS)) begin
            case(DistCode)
            1: REL2<=DistData;
            2: REL3<=DistData;
            3: REL4<=DistData;
            endcase
        end
    end

При компиляции выдается сообщение:

Error (10044): Verilog HDL error at project.v(37): expression cannot reference entire array "DistCode"

Поделиться сообщением


Ссылка на сообщение
Поделиться на другие сайты

Присоединяйтесь к обсуждению

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

Гость
Ответить в этой теме...

×   Вставлено с форматированием.   Вставить как обычный текст

  Разрешено использовать не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отображать как обычную ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставлять изображения напрямую. Загружайте или вставляйте изображения по ссылке.

×
×
  • Создать...