一、波形变换需求
二、思路
(1)脉冲边沿提取,得到波形的上升沿r_rise和下降沿r_fall
(2)将上升沿r_rise延迟一节拍r_r_rise,r_rise更新上一周期的周期和脉宽并清空上一次的脉冲周期计数和脉宽周期计数,r_r_rise启动本次脉冲周期计数和脉宽计数,r_fall结束本次脉宽计数
三、代码
`timescale 1ns / 1ps
module pulse_transfer(ttl_in ,// mcu ttl inputsys_clk ,// 100MHz clk inputreset_n ,// negtive reset inputttl_out, // fpga ttl output );/*! -------------------------------------------------------------------------- */
/*! module port defination */
input ttl_in ;
input sys_clk ;
input reset_n ;
output ttl_out ;parameter FRE_SYS = 30'd100000000;//100MHz/*! -------------------------------------------------------------------------- */
/*! module macro defination */
parameter MAX_PULSE_WIDTH_COUNT = 16'd20000; /*! max width 200us = 10ns*20000 */
parameter MAX_PULSE_PERIOD_COUNT = 30'd100000000; /*! max period 1s */
parameter COUNT_OFFSET = 3'd2;
parameter TIME_1US = 8'd100;
parameter TIME_300NS = 8'd30;/*! -------------------------------------------------------------------------- */
/*! get rise and fall edge */
wire w_is_rise_trigger;
wire w_is_fall_trigger;
reg r_ttl_in_delay;
reg r_ttl_in_delay_1;
always @ ( posedge sys_clk or negedge reset_n )
beginif( !reset_n ) beginr_ttl_in_delay <= 1'b0 ;r_ttl_in_delay_1 <= 1'b0 ;endelsebeginr_ttl_in_delay <= ttl_in ;r_ttl_in_delay_1 <= r_ttl_in_delay ;end
end //assign w_is_rise_trigger = ~r_ttl_in_delay&ttl_in;
//assign w_is_fall_trigger = ~ttl_in&r_ttl_in_delay;/*! -------------------------------------------------------------------------- */
/*! synch rise and fall trigger */
reg r_is_rise_trigger;
reg r_is_fall_trigger;
always @ ( posedge sys_clk or negedge reset_n)
beginif( !reset_n ) beginr_is_rise_trigger <= 1'b0;r_is_fall_trigger <= 1'b0;endelse if({r_ttl_in_delay,r_ttl_in_delay_1} == 2b'10)beginr_is_rise_trigger <= 1'b1;r_is_fall_trigger <= 1'b0;endelse if({r_ttl_in_delay,r_ttl_in_delay_1} == 2b'01)beginr_is_rise_trigger <= 1'b0;r_is_fall_trigger <= 1'b1;endelse beginr_is_rise_trigger <= 1'b0;r_is_fall_trigger <= 1'b0;end
end/*! -------------------------------------------------------------------------- */
/*! get start count trigger */
reg r_count_start_trigger;
wire w_count_clear_trigger;
assign w_count_clear_trigger = r_is_rise_trigger;
always @ ( posedge sys_clk or negedge reset_n )
beginif( !reset_n ) r_count_start_trigger <= 1'b0;elser_count_start_trigger <= w_count_clear_trigger;
end /*! -------------------------------------------------------------------------- */
/*! get period and width count enable flag */
reg r_is_pulse_period_count_enable;
reg r_is_pulse_width_count_enable;
always @ ( posedge sys_clk or negedge reset_n)
beginif( !reset_n ) beginr_is_pulse_period_count_enable = 1'b0;r_is_pulse_width_count_enable = 1'b0;endelse beginif( r_is_rise_trigger )beginr_is_pulse_period_count_enable = 1'b0;r_is_pulse_width_count_enable = 1'b0;endif( r_count_start_trigger )beginr_is_pulse_width_count_enable = 1'b1;r_is_pulse_period_count_enable = 1'b1;endif( r_is_fall_trigger )r_is_pulse_width_count_enable = 1'b0;end
end /*! -------------------------------------------------------------------------- */
/*! pulse width and period count handle */
reg [30:0] r_pulse_period_count;
reg [30:0] r_pulse_period;
reg [30:0] r_pulse_width_count;
reg [30:0] r_pulse_width;
always @ ( posedge sys_clk or negedge reset_n )
beginif( !reset_n ) beginr_pulse_width_count <= 30'd0;r_pulse_width <= 30'd0;r_pulse_period_count <= 30'd0;r_pulse_period <= 30'd0;endelsebeginif( r_is_rise_trigger )begin r_pulse_period_count <= 30'd0;r_pulse_width_count <= 30'd0;endif( r_is_pulse_width_count_enable )r_pulse_width_count <= r_pulse_width_count + 1'b1;elsebeginr_pulse_width <= r_pulse_width_count;endif( r_is_pulse_period_count_enable )r_pulse_period_count <= r_pulse_period_count + 1'b1;elsebeginr_pulse_period <= r_pulse_period_count;endend
end/*! -------------------------------------------------------------------------- */
/*! output pulse handle */
reg [30:0] r_out_cnt;
reg r_ttl_out;
always @ ( posedge sys_clk or negedge reset_n )
beginif( !reset_n ) beginr_ttl_out <= 1'b0;r_out_cnt <= 1'b0;endelsebegin//if( r_pulse_period > MAX_PULSE_PERIOD_COUNT || r_pulse_width > MAX_PULSE_WIDTH_COUNT)// begin// r_ttl_out <= 1'b0;// r_out_cnt <= 1'b0;// end//elseif(r_pulse_period == 0 || r_pulse_width == 0)beginr_out_cnt <= 1'b0;endelsebeginif( r_pulse_width <= TIME_1US + 4'd10 )//*note in <1.1us casebeginif( r_out_cnt < TIME_300NS )//0.3usbeginr_ttl_out <= 1'b1;r_out_cnt <= r_out_cnt + 1'b1;endelse if ( r_out_cnt < r_pulse_period )beginr_ttl_out <= 1'b0;r_out_cnt <= r_out_cnt + 1'b1; endelsebeginr_ttl_out <= 1'b0; r_out_cnt <= 1'b0; endendelsebeginif( r_out_cnt < r_pulse_width - TIME_1US)//*note -1usbeginr_ttl_out <= 1'b1;r_out_cnt <= r_out_cnt + 1'b1;endelse if ( r_out_cnt < r_pulse_period )beginr_ttl_out <= 1'b0;r_out_cnt <= r_out_cnt + 1'b1; endelsebeginr_ttl_out <= 1'b0; r_out_cnt <= 1'b0; endendendend
end/*! -------------------------------------------------------------------------- */
/*! output assign handle */
assign ttl_out = r_ttl_out;endmodule