//`timescale 1ns / 1ps ////////////////////////////////////////////////////////////////////////////////// // Company: // Engineer: // // Create Date: 10:02:35 04/20/2020 // Design Name: // Module Name: PulseGen // Project Name: // Target Devices: // Tool versions: // Description: // // Dependencies: // // Revision: // Revision 0.01 - File Created // Additional Comments: // ////////////////////////////////////////////////////////////////////////////////// module PulseGen #( parameter CmdRegWidth = 32 ) ( input Rst_i, input Clk_i, input EnPulse_i, input PulsePol_i, input EnEdge_i, input [CmdRegWidth-29:0] Mode_i, input [CmdRegWidth-1:0] P1Del_i, input [CmdRegWidth-1:0] P2Del_i, input [CmdRegWidth-1:0] P3Del_i, input [CmdRegWidth-1:0] P1Width_i, input [CmdRegWidth-1:0] P2Width_i, input [CmdRegWidth-1:0] P3Width_i, output Pulse_o ); //================================================================================ // LOCALPARAM localparam IDLE = 2'h0; localparam DELAY = 2'h1; localparam PULSE = 2'h2; localparam DISABLED = 8'd0; localparam SINGLE = 8'd1; localparam DOUBLE = 8'd2; localparam TRIPPLE = 8'd3; localparam BURST = 8'd4; localparam CONTINIOUS = 8'd5; //================================================================================ reg pulse; wire [31:0] delArray [2:0]; wire [31:0] widthArray [2:0]; reg [31:0] pulseCnt; reg [31:0] delayCnt; reg [31:0] widthCnt; reg [31:0] currWidthValue; reg [31:0] currDelValue; reg [1:0] currState; reg [1:0] nextState; reg pulseDone; wire delayDone = (currState == DELAY)? delayCnt==currDelValue-1:1'b0; wire zeroDelay = (P1Del_i==0); reg patternDone; reg enPulseR; wire enPulsePos = (!enPulseR&EnPulse_i); wire enPulseNeg = (enPulseR&!EnPulse_i); wire enPulse = (EnEdge_i)? enPulseNeg:enPulsePos; wire enPulseEn = (Mode_i != 0)? enPulse:1'b0; //================================================================================ // ASSIGNMENTS assign delArray [0] = P1Del_i; assign delArray [1] = P2Del_i; assign delArray [2] = P3Del_i; assign widthArray [0] = P1Width_i; assign widthArray [1] = P2Width_i; assign widthArray [2] = P3Width_i; assign Pulse_o = (PulsePol_i)? ~pulse:pulse; //================================================================================ // CODING always @(posedge Clk_i) begin if (!Rst_i) begin enPulseR <= EnPulse_i; end else begin enPulseR <= 1'b0; end end always @(posedge Clk_i) begin if (!Rst_i) begin if (Mode_i >=1 & Mode_i<=3) begin if (currState != IDLE) begin delayCnt <= delayCnt+1; end else begin delayCnt <= 0; end end else begin if (currState == DELAY) begin delayCnt <= delayCnt+1; end else begin delayCnt <= 0; end end end else begin delayCnt <= 0; end end always @(posedge Clk_i) begin if (!Rst_i) begin if (currState == PULSE) begin widthCnt <= widthCnt+1; end else begin widthCnt <= 0; end end else begin widthCnt <= 0; end end always @(*) begin if (!Rst_i) begin if (currState == PULSE) begin if (widthCnt==currWidthValue-1) begin pulseDone = 1'b1; end else begin pulseDone = 1'b0; end end else begin pulseDone = 1'b0; end end else begin pulseDone = 1'b0; end end always @(posedge Clk_i) begin if (!Rst_i) begin if (pulseDone) begin if (!patternDone) begin pulseCnt <= pulseCnt+1; end else begin pulseCnt <= 0; end end end else begin pulseCnt <= 0; end end always @(posedge Clk_i) begin if (!Rst_i) begin if (Mode_i == 0) begin currDelValue <= 0; currWidthValue <= 0; end else begin if (Mode_i >=1 & Mode_i<=3) begin currDelValue <= delArray[pulseCnt]; currWidthValue <= widthArray[pulseCnt]; end else begin if (Mode_i == 4|Mode_i == 5) begin if (currState == IDLE) begin currDelValue <= delArray[0]; currWidthValue <= widthArray[0]; end else if (currState == PULSE & pulseDone) begin currDelValue <= delArray[1]; currWidthValue <= widthArray[0]; end end end end end else begin currDelValue <= 0; currWidthValue <= 0; end end always @(*) begin if (!Rst_i) begin if (currState != IDLE) begin case(Mode_i) 8'd0: begin patternDone = 0; end 8'd1: begin patternDone = ((pulseCnt==Mode_i-1)&pulseDone); end 8'd2: begin patternDone = ((pulseCnt==Mode_i-1)&pulseDone); end 8'd3: begin patternDone = ((pulseCnt==Mode_i-1)&pulseDone); end 8'd4: begin patternDone = ((pulseCnt==P2Width_i-1)&pulseDone); end 8'd5: begin patternDone = 0; end default :begin patternDone = 0; end endcase end else begin patternDone = 0; end end else begin patternDone = 0; end end always @(posedge Clk_i) begin if (!Rst_i) begin currState <= nextState; end else begin currState <= IDLE; end end always @(*) begin nextState = IDLE; case(currState) IDLE : begin if (enPulseEn) begin if (zeroDelay) begin nextState = PULSE; end else begin nextState = DELAY; end end else begin nextState = IDLE; end end DELAY : begin if (delayDone) begin nextState = PULSE; end else begin nextState = DELAY; end end PULSE : begin if (pulseDone) begin if (!patternDone) begin nextState = DELAY; end else begin nextState = IDLE; end end else begin nextState = PULSE; end end endcase end always @(*) begin if (!Rst_i) begin if (Mode_i != 0) begin case(currState) IDLE: begin pulse = 1'b0; end DELAY: begin pulse = 1'b0; end PULSE: begin pulse = 1'b1; end default:begin pulse = 1'b0; end endcase end else begin pulse = 1'b0; end end else begin pulse = 1'b0; end end endmodule