差别
这里会显示出您选择的修订版和当前版本之间的差别。
后一修订版 | 前一修订版 | ||
pulse_gen [2021/09/13 10:58] gongyu 创建 |
pulse_gen [2021/09/13 22:49] (当前版本) gongyu |
||
---|---|---|---|
行 7: | 行 7: | ||
### 2. 设计要求 | ### 2. 设计要求 | ||
- | - 掌握Verilog子模块的调用 | + | - 掌握[[Verilog]]子模块的调用 |
- | - 掌握PWM和脉冲发生的原理 | + | - 掌握[[PWM]]和脉冲发生的原理 |
- 基于[[STEP-Baseboard]]平台实现脉冲发生器的设计,周期可调,占空比可调 | - 基于[[STEP-Baseboard]]平台实现脉冲发生器的设计,周期可调,占空比可调 | ||
行 151: | 行 151: | ||
- | ====参考文档==== | + | ### 9. 参考文档 |
* [[按键消抖]] | * [[按键消抖]] | ||
- | * {{:machxo2familydatasheet.pdf|Lattice MachXO2数据手册}} | + | * {{:machxo2familydatasheet.pdf|Lattice MachXO2数据手册}} |
- | + | ### 10. 相关代码 | |
+ | #### 10.1 脉冲发生器代码 | ||
+ | 可下载文件:[[Pulse_gen.v|脉冲发生器Top文件]] | ||
+ | <code verilog> | ||
+ | // -------------------------------------------------------------------- | ||
+ | // >>>>>>>>>>>>>>>>>>>>>>>>> COPYRIGHT NOTICE <<<<<<<<<<<<<<<<<<<<<<<<< | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Module: Pulse_gen | ||
+ | // | ||
+ | // Author: Step | ||
+ | // | ||
+ | // Description: Pulse generate module | ||
+ | // | ||
+ | // Web: www.ecbcamp.com | ||
+ | // | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Code Revision History : | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Version: |Mod. Date: |Changes Made: | ||
+ | // V1.0 |2015/11/11 |Initial ver | ||
+ | // -------------------------------------------------------------------- | ||
+ | module Pulse_gen | ||
+ | ( | ||
+ | input clk_in, | ||
+ | input rst_n_in, | ||
+ | input key_menu, | ||
+ | input key_up, | ||
+ | input key_down, | ||
+ | output menu_state, | ||
+ | output reg pulse_out | ||
+ | ); | ||
- | ====相关文档==== | + | //Debounce for key |
+ | wire [2:0] key_state,key_pulse; | ||
+ | Debounce1 Debounce_uut | ||
+ | ( | ||
+ | .clk(clk_in), | ||
+ | .rst_n(rst_n_in), | ||
+ | .key_n({key_menu,key_up,key_down}), | ||
+ | .key_state(key_state), | ||
+ | .key_pulse(key_pulse) | ||
+ | ); | ||
- | ^ **文件名称** | **功能** | | + | wire menu_state = key_state[2]; |
- | ^ **[[Pulse_gen.v]]** | **脉冲发生器TOP文件** | | + | wire up_pulse = key_pulse[1]; |
- | ^ **[[Debounce1.v]]** | **按键消抖** | | + | wire down_pulse = key_pulse[0]; |
+ | |||
+ | reg [3:0] cycle; | ||
+ | reg [3:0] duty; | ||
+ | //Control cycle and duty cycle | ||
+ | always @(posedge clk_in or negedge rst_n_in) begin | ||
+ | if(!rst_n_in) begin | ||
+ | cycle<=4'd8; | ||
+ | duty<=4'd4; | ||
+ | end else begin | ||
+ | if(menu_state) begin | ||
+ | if(up_pulse && (cycle<4'd15)) cycle <= cycle + 4'd1; | ||
+ | else if(down_pulse && (cycle>(duty+4'd1))) cycle <= cycle - 4'd1; | ||
+ | else cycle <= cycle; | ||
+ | end else begin | ||
+ | if(up_pulse && (cycle>(duty+4'd1))) duty <= duty + 4'd1; | ||
+ | else if(down_pulse && (duty>4'd0)) duty <= duty - 4'd1; | ||
+ | else duty <= duty; | ||
+ | end | ||
+ | end | ||
+ | end | ||
+ | |||
+ | reg [3:0] cnt; | ||
+ | //counter for cycle | ||
+ | always @(posedge clk_in or negedge rst_n_in) begin | ||
+ | if(!rst_n_in) begin | ||
+ | cnt<=4'd0; | ||
+ | end else begin | ||
+ | if(cnt>=cycle) cnt<=4'd0; | ||
+ | else cnt <= cnt + 4'd1; | ||
+ | end | ||
+ | end | ||
+ | |||
+ | //pulse generate with duty | ||
+ | always @(posedge clk_in or negedge rst_n_in) begin | ||
+ | if(!rst_n_in) begin | ||
+ | pulse_out<=1'b1; | ||
+ | end else begin | ||
+ | if(cnt<=duty) pulse_out<=1'b1; | ||
+ | else pulse_out<=1'b0; | ||
+ | end | ||
+ | end | ||
+ | |||
+ | endmodule | ||
+ | </code> | ||
+ | |||
+ | #### 10.2 按键消抖部分的代码 | ||
+ | 可下载代码:[[Debounce1.v|按键消抖设计代码]] | ||
+ | <code verilog> | ||
+ | // -------------------------------------------------------------------- | ||
+ | // >>>>>>>>>>>>>>>>>>>>>>>>> COPYRIGHT NOTICE <<<<<<<<<<<<<<<<<<<<<<<<< | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Module: Debounce1 | ||
+ | // | ||
+ | // Author: Step | ||
+ | // | ||
+ | // Description: Debounce for button with FPGA/CPLD | ||
+ | // | ||
+ | // Web: www.ecbcamp.com | ||
+ | // | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Code Revision History : | ||
+ | // -------------------------------------------------------------------- | ||
+ | // Version: |Mod. Date: |Changes Made: | ||
+ | // V1.0 |2015/11/11 |Initial ver | ||
+ | // -------------------------------------------------------------------- | ||
+ | module Debounce1(clk,rst_n,key_n,key_pulse,key_state); | ||
+ | |||
+ | input clk; //system clock | ||
+ | input rst_n; //system reset | ||
+ | input [2:0] key_n; //button input | ||
+ | output [2:0] key_pulse; //Debounce pulse output | ||
+ | output reg [2:0] key_state; //Debounce state output | ||
+ | |||
+ | reg [2:0] key_rst; | ||
+ | //Register key_rst, lock key_n to next clk | ||
+ | always @(posedge clk or negedge rst_n) | ||
+ | if (!rst_n) key_rst <= 3'b111; | ||
+ | else key_rst <=key_n; | ||
+ | |||
+ | //Detect the edge of key_n | ||
+ | wire key_an = (key_rst==key_n)? 0:1; | ||
+ | |||
+ | reg[18:0] cnt; | ||
+ | //Count the number of clk when a edge of key_n is occured | ||
+ | always @ (posedge clk or negedge rst_n) | ||
+ | if (!rst_n) cnt <= 19'd0; | ||
+ | else if(key_an) cnt <=19'd0; | ||
+ | else cnt <= cnt + 1'b1; | ||
+ | |||
+ | reg [2:0] low_sw; | ||
+ | //Lock the status to register low_sw when cnt count to 19'd500000 | ||
+ | always @(posedge clk or negedge rst_n) | ||
+ | if (!rst_n) low_sw <= 3'b111; | ||
+ | else if (cnt == 19'd500000) | ||
+ | low_sw <= key_n; | ||
+ | |||
+ | reg [2:0] low_sw_r; | ||
+ | //Register low_sw_r, lock low_sw to next clk | ||
+ | always @ ( posedge clk or negedge rst_n ) | ||
+ | if (!rst_n) low_sw_r <= 3'b111; | ||
+ | else low_sw_r <= low_sw; | ||
+ | |||
+ | wire [2:0] key_pulse; | ||
+ | //Detect the negedge of low_sw, generate pulse | ||
+ | assign key_pulse= low_sw_r & ( ~low_sw); | ||
+ | |||
+ | //Detect the negedge of low_sw, generate state | ||
+ | always @(posedge clk or negedge rst_n) | ||
+ | if (!rst_n) key_state <= 3'b111; | ||
+ | else if(key_pulse[0]) key_state[0] <= ~key_state[0]; | ||
+ | else if(key_pulse[1]) key_state[1] <= ~key_state[1]; | ||
+ | else if(key_pulse[2]) key_state[2] <= ~key_state[2]; | ||
+ | else key_state <= key_state; | ||
+ | |||
+ | endmodule | ||
+ | |||
+ | </code> |