Verilog Inferred RAM
Submitted by abettino on Mon, 03/22/2010 - 16:32When doing an FPGA design, it is sometimes useful to write some HDL code to infer a block RAM element. Most synthesizers will support this construct. The following snippet demonstrates how to infer a block ram in Verilog.
module verilog_ram_infr #(parameter ADDR_WIDTH=8, DATA_WIDTH=8, DEPTH=256) ( input clk, // clock signal. input [ADDR_WIDTH-1:0] addr, // address signal. input we, // write enable signal. input [DATA_WIDTH-1:0] data_in, // data input.
Verilog Concatenation
Submitted by abettino on Sun, 03/21/2010 - 12:35Concatenation is a useful feature in Verilog. It allows multiple signals to be combined into one signal. Concatenation in Verilog is achieved by using the curly braces with the signals to be concatenated separated by commas inside as demonstrated in the following snippet.
module verilog_concat; reg [7:0] register_a; reg [3:0] register_b; reg [3:0] register_c; reg [2:0] register_d; initial begin register_b = 4'hA; register_c = 4'hF; register_d = 3'h7; // concat register b and register c into register a register_a = {register_b,register_c};
Verilog Display with No Newline ($write statment)
Submitted by abettino on Sun, 03/21/2010 - 11:55Sometimes it is desired to output some text to the standard output without displaying a newline character. The Verilog command $display() will display text in a printf fashion, but it always comes with a newline. Conversely, the $write() command behaves just as the $display() command but does not include the new line. The following example uses the $write() command to display a table of the numbers 0-99.
module no_newline; integer ii,jj; initial begin for(ii=0;ii<10;ii=ii+1) begin for(jj=0;jj<10;jj=jj+1) begin $write("%d ",jj+ii*10); end
Verilog Dual Edge Detector
Submitted by abettino on Sun, 03/21/2010 - 09:56It is often necessary to detect when a particular signal is transitioning from high to low or low to high. It is also sometimes useful to get a pulse that is a single clock cycle wide to trigger other logic in the system. This snippet demonstrates how a single cycle wide pulse can be generated on the falling edge of a signal or the rising edge of a signal.
module dual_edge_detect ( input clk, input signal, output pulse ); reg signal_prev; always @(posedge clk) signal_prev <= signal;
Verilog Falling Edge Detector
Submitted by abettino on Sun, 03/21/2010 - 09:52It is often necessary to detect when a particular signal is transitioning from high to low. It is also sometimes useful to get a pulse that is a single clock cycle wide to trigger other logic in the system. This snippet demonstrates how a single cycle wide pulse can be generated on the falling edge of a signal.
module falling_edge_detect ( input clk, input signal, output pulse ); reg signal_prev; always @(posedge clk) signal_prev <= signal; assign pulse = ~signal & signal_prev; endmodule
Verilog Rising Edge Detector
Submitted by abettino on Sun, 03/21/2010 - 09:46It is often necessary to detect when a particular signal is transitioning from low to high. It is also sometimes useful to get a pulse that is a single clock cycle wide to trigger other logic in the system. This snippet demonstrates how a single cycle wide pulse can be generated on the rising edge of a signal.
module rising_edge_detect ( input clk, input signal, output pulse ); reg signal_prev; always @(posedge clk) signal_prev <= signal; assign pulse = signal & ~signal_prev; endmodule
SystemVerilog Multiplexor
Submitted by abettino on Sun, 03/21/2010 - 09:36A multiplexor written in SystemVerilog can take advantage of a few of SystemVerilog's keywords. For instance, the always_comb block is used to indicate combinational logic and the unique case statement makes it clear to the sythesizer and simulator that only one branch in the case statement should ever be taken. Also check out the Verilog implementation of the multiplexor.
module mux4_2 ( input logic a,b,c,d, input logic [1:0] sel, output logic z ); always_comb begin unique case (sel)
Verilog JK Flip Flop
Submitted by abettino on Thu, 03/18/2010 - 21:24A JK flip flop can be considered the "universal" flip flop since any other flip flop can be constructed from it. While this is an interesting point, it does not have any real world implications since digital electronics is dominated by the D flip flop. Nevertheless, it makes for an interesting discussion.
Here is a snippet for the JK flip flop.
module jk_flip_flop ( input clk, input j, input k, output reg q ); always @(posedge clk) case ({j,k}) 2'b11 : q <= ~q; // toggle.
SystemVerilog always_comb
Submitted by abettino on Thu, 03/18/2010 - 20:59The always_comb block in SystemVerilog provides a means to prevent simulation and synthesis mismatches. The idea is that both the simulator and synthesizer will be able to analyze this block and determine if it properly infers combinational logic. If it does not, an error can be thrown. This snippet demonstrates the most basic usage of this type of block and it also demonstrates the usage of the unique keyword. This keyword ensure that only one branch of the case statement is active at any time.
module systemverilog_always_comb ( input logic [3:0] data_input,
SystemVerilog always_ff
Submitted by abettino on Thu, 03/18/2010 - 20:41The always_ff block in SystemVerilog provides a means to prevent simulation and synthesis mismatches. The idea is that both the simulator and synthesizer will be able to analyze this block and determine if it properly infers sequential logic. If it does not, an error can be thrown. This snippet demonstrates the most basic usage of this type of block.
module systemverilog_always_ff ( input logic clk, input logic d, output logic q ); always_ff @(posedge clk) // always_ff begin : sysverilog_always_ff // optional label. q <= d;
