200MHz延时150ms输出pwm波 verilog

说明:板子时钟频率200MHz,pwm波周期为1ms,频率为1k的方波信号;

功能:使用计数器延时的方法,延迟150ms输出pwm波

`timescale 1ns / 1ns
module optional_pwm_module
(
	input clk, input rst_n, input[2:0]Option_Key,
	output pwm_out
);

//定义200MHz频率定时3.9us的常量
	parameter SEGMENT=10'd780;    //200MHz跳多少下得到3.9us
	reg[1:0] pwm_out;
	reg[9:0] C1;
	always@(posedge clk or negedge rst_n)
		if(!rst_n)
			C1<=10'd0;
		else if(C1==SEGMENT)
			C1<=10'd0;
		else 
			C1<=C1+1'b1;
	
	
//3.9us计数器,产生1k脉冲的周期为1ms将其分成256块
	reg[7:0]System_Seg;	 
	/*System_Seg是自动递增的pwm块,每3.9us都会自动递增
	* 当增加到0-255时说明1ms计时结束即一个周期结束,然后又从下一个周期开始*/
	
	always@(posedge clk or negedge rst_n)
		if(!rst_n)
			System_Seg<=8'd0;
		else if(System_Seg==8'd255)
			System_Seg<=8'd0;
		else if(C1==SEGMENT)
			System_Seg<=System_Seg+1'b1;
			
			
/*************************按键控制产生pwm脉冲的模块	***************************************/				
	reg[7:0]Option_Seg;
	always@(posedge clk or negedge rst_n)
		if(!rst_n)
			Option_Seg<=8'd0;
			
		else if(Option_Key[2])	//Key Up=Segment+10
			if(Option_Seg<8'd245)Option_Seg<=Option_Seg+8'd10;
			else Option_Seg<=8'd255;
			
		else if(Option_Key[1])  //Key_Down=SEGMENT-10
			if(Option_Seg>8'd10)Option_Seg<=Option_Seg-8'd10;
			else Option_Seg<=8'd0;
		
		else if(Option_Key[0])
			Option_Seg<=8'd127;


    reg[17:0] Count1;	//用来对延迟计数,18位寄存器用于进行1ms的计时;
    reg[6:0] T100MS;	//100ms计数器用来使pwm延迟100ms输出
    always@(posedge clk or negedge rst_n)
        if(!rst_n) Count1<=18'd0;
        else if(Count1>=18'd199_999)	//1ms counter
            Count1<=18'd0;
        else begin Count1<=Count1+18'd1;end

    always@(posedge clk or negedge rst_n)       //延迟100ms输出
        if(!rst_n)
        begin 
            T100MS<=7'd0;
            pwm_out<=1'b0;
        end
        else if(T100MS>=7'd99)			
        begin	
            T100MS<=7'd0;
//            pwm_out<=1'b0;
            assign pwm_out= (System_Seg<Option_Seg)?1'b1:1'b0;
        end
        else begin
            pwm_out<=1'b0;
//            assign pwm_out= (System_Seg<Option_Seg)?1'b1:1'b0;
            T100MS<=T100MS+7'd1;
        end

//    always@(posedge clk or negedge rst_n)
当System_Seg计数器从0-127递增时,由于Ssystem_Seg<Option_Seg,		
//        assign pwm_out= (System_Seg<Option_Seg)?1'b1:1'b0;
Option_Seg相当于一个对比常量,当system_seg<option_seg时pwm_out为高电平,反之为低电平。

endmodule	

其他生成PWM延迟的方法

//用多位寄存器移位传输数据
input pulse_in;
wire pulse_out;
reg[9:0] pulse_tmp;
reg[3:0] Count;			//10ns延迟输出pulse_out

always@(posedge clk or negedge rst_n)
begin
	if(!rst_n)
		pulse_tmp<=10'd0;
		
	else if(Count>=4'd0&&Count<=4'd10)
		pulse_tmp<=10'd0;
		pulse_in==1'b0;
		
	else(Count>=4'd10)
		pulse_in==1'b1
		pulse_tmp<={pulse_tmp[8:0],pulse_in};
end
assign pulse_out<=pulse_tmp[9];

//计数器延时
//原理为采样到输入脉冲后将flag信号置为1,开始计数,计数到需要的延时
//后,输出一个脉冲信号,同时清除计数,清零flag信号
module pusle_delay(
	input clk, 
	input rst_n,
	input Delay_In,
	output Delay_Out
);

	reg[7:0] delay_plus;
	reg Delay_plus;
	reg plus_flag;
	
	assign Delay_Out=Delay_plus;
	always@(posedge clk or negedge rst_n) begin
		if(!rst_n)
			plus_flag<=1'b0;
		else if(Delay_In==1'b1)
			plus_flag<=1'b1;
		else if(delay_plus[7:0]==16'h8)
			plus_flag<=1'0;
		end
	always@(posedge clk or negedge rst_n)
	begin 
		if(!rst_n)
		begin 
			delay_plus[7:0]<=8'd0;
			Delay_plus<=1'b0;
		end
		else if(delay_plus[7:0]==16'h87&plus_flag==1'b1)//延时时间
		begin 
			delay_plus[7:0]<=8'd0;
			Delay_plus<=1'b1;
		end
		else if(plus_flag==1'b1)begin 
			Delay_plus<=1'b0;
			delay_plus[7:0]<=delay_plus[7:0]+1'b1;
		end
		else begin 
			delay_plus[7:0]<=8'd0;
			Delay_plus<=1'b0;
		end
	end
endmodule

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小菜鸡变形记

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值