➢采用的时钟频率为100MHz,用一个寄存器q来保存时钟的周期数。q值的每一位q(i)就代表100MHz时钟的2^(i+1)次分频。
➢产生一个频率为2kHz的PWM信号,那么它的周期就为0.5ms。FPGA实验板卡提供100MHz的时钟频率,q[15]的周期为0.65536ms,刚刚超0.5ms。
➢可用一个频率为390.625kHz的时钟(q[7] )驱动8位计数器去控制这个PWM信号。得到周期为0.5ms的PWM信号,即:
period=(0.5/0.65536) x 256=195(十六进制数C3)
duty的值可以在00H-C3H范围内变化。
项目代码:
module pwm_2k (
input wire clk,
input wire clr,
input wire [7:0] duty,
output reg pwm,
output wire buzzer
);
wire clk_390k;
reg [7:0] count;
reg [25:0] q;
//计数器q
always @ ( posedge clk or negedge clr )
begin
if ( clr ==0 )
q <= 0;
else
q <= q+1;
end
// assign clk_390k = q[7]; //实际使用
assign clk_390k=q[0] ;//仿真使用
//count计数设置频率
always @ ( posedge clk_390k or negedge clr )
if ( clr == 0 )
count <= 0;
//else if ( count == 194 ) //实际使用
else if ( count == 10 ) //仿真使用
count <= 0;
else
count <= count + 1;
//duty设置占空比
always @ ( * )
if ( count < duty )
pwm <= 1;
else
pwm <= 0;
assign buzzer = pwm ;
endmodule
仿真文件:
module pwm_2k_tb( );
reg CLK;
reg CLR;
reg [7:0] DUTY;
wire PWM;
/*****************begin********************/
// 调用pwm_2k模块
pwm_2k u1(
.clk(CLK),
.clr(CLR),
.duty(DUTY),
.pwm(PWM)
);
// 生成占空比50%的时钟波形
parameter PERIOD = 10;
always #(PERIOD/2) CLK = ~CLK;
// 激励信号随时间变化
initial begin
CLK = 1'b0;
CLR = 1'b0;
DUTY = 3'b111;
#10 CLR = 1'b1;
end
endmodule