I'm trying to create a Verilog wrapper for a VS counter.
I have written the following SystemVerilog code for the counter:
//counter.sv
interface counter_if(input clk, rstn);
logic [3:0] out;
modport dut(input clk,rstn, output out);
endinterface : counter_if
module counter(counter_if.dut cnt);
always # (posedge cnt.clk) begin
if (! cnt.rstn)
cnt.out <= 0;
else
cnt.out <= cnt.out + 1;
end
endmodule
Also, I've written the following Verilog code:
//wrapper file
module counter_wrapper(clk,rstn,out);
input clk;
input rstn;
output reg [3:0] out;
counter_if cnt (.clk(clk), .rstn(rstn));
counter cnt0 (
.cnt(cnt)
);
endmodule
When I compile it, I get the following error for the Verilog file:
Error: (vlog-2110) Illegal reference to interface "cnt"
So I changed the interface call to the following:
//wrapper file
module counter_wrapper(clk,rstn,out);
input clk;
input rstn;
output reg [3:0] out;
counter_if cnt (.clk(clk), .rstn(rstn));
counter cnt0 (
.cnt(cnt.dut)
);
endmodule
Now the design compiles, but when simulating the following error comes up:
Error: (vsim-3044) Usage of 'cnt.dut' inconsistent with 'modport' object.
Any insight will be highly appreciated!
Standard-compliant Verilog code cannot instantiate a SystemVerilog interface. You'll need to either use an SV wrapper or remove the interface and replace it with normal module ports. Verilog can connect to SV just fine (in most tools) with regular module ports.
//counter.sv
module counter (
input logic clk,
input logic rstn,
output logic [3:0] out
);
always # (posedge clk) begin
if (!rstn)
out <= 0;
else
out <= out + 1;
end
endmodule
Related
I'm trying to build a RegisterFile that utilizes these 3 components. I just don't know how to put them all together. I have the start of the register file module but just have no clue how to top end it. Is there any way anyone could explain, I'm just so lost. I also think there may be an issue with my Register module. I really am a novice with verilog, so I'm very confused on most things.
module Decoder3To8(input enable, input[2:0] in, output[7:0] out);
assign d[0]=(~a[2])&(~a[1])&(~a[0]);
assign d[1]=(~a[2])&(~a[1])&(a[0]);
assign d[2]=(~a[2])&(a[1])&(~a[0]);
assign d[3]=(~a[2])&(a[1])&(a[0]);
assign d[4]=(a[2])&(~a[1])&(~a[0]);
assign d[5]=(a[2])&(~a[1])&(a[0]);
assign d[6]=(a[2])&(a[1])&(~a[0]);
assign d[7]=(a[2])&(a[1])&(a[0]);
endmodule
module Register4Bit(input clock, input clear, input load, input[3:0] in, output reg[3:0] out);
always#(negedge clock or posedge clear)
begin
if(clear)
out<=4′b0000;
else
out[3]<=out[2];
out[2]<=out[1];
out[1]<=out[0];
out[0]<=in[0];
end
endmodule
module Mux4Bit8To1(input[3:0] in0, input[3:0] in1, input[3:0] in2, input[3:0] in3, input[3:0] in4, input[3:0] in5, input[3:0] in6, input[3:0] in7, input[2:0] selector, output reg[3:0] out);
assign S0 = selector[0];
assign S1 = selector[1];
assign S2 = selector[2];
assign out = S2 ? (S[1] ? (S[0] ? in7 : in6) : (S[0] ? in5 : in4)) : (S[1] ? (S[0] ? in3 : in2) : (S[0] ? in1 : in0))
endmodule
module RegisterFile(input clock, input clear, input[3:0] write_data, input[2:0] write_index, input write, input[2:0] read_index, output[3:0] read_data);
reg[7:0] content[3:0]; //this line is initializing the register
integer i;
always #(posedge clear, negedge clock). //this is the senstivity list of the always block
if (clear) begin
for (i = 0; i < 4; i = i + 1)
content[i] = 0; //this line is clearing out all the memory locations
end else if (write)
content[write_index] = write_data. //this line is performing a write operation
else
endmodule
Verilog describes hardware. As a result the final product is set of connected elements. In your case you need to instantiate and connect your modules.
In verilog it looks like the following:
module in(input clk, input data, output reg value);
always #(posedge clk)
value <= data;
endmodule
The above module has clock, input data and output value;
module out(input clk, input value, output reg data);
always #(posedge clk)
data <= ~value;
endmodule
And finally you need to assemble them:
module device(input clk, input datain, output dataout);
wire val;
in in(clk, datain, val);
out out(clk, val, dataout);
endmodule
in the device, two modules are instantiated. The val plays a role of a connecting wire which connects output of module in with input of module out.
So, you can extend this scheme to your model.
I'm writing a verilog module for my CompSci class and this module specifically is the data memory module. Structurally and analytically, I'm looking at it and it should work based off of the other files that I have, but I'm not sure why this one specifically is acting up and giving me all x's. Hoping a fresh set of eyes can help find the error I missed. Thanks in advance.
datamem.v:
module datamem(Ina, Inb, enable, readwrite, dataOut, clk, rst);
input wire [31:0] Ina;
input wire [31:0] Inb;
input wire enable;
input wire readwrite;
input wire clk;
input wire rst;
reg [31:0] memory[0:65535];
output reg [31:0] dataOut;
always #(memory[Ina]) begin
dataOut = memory[Ina];
end
always #(posedge clk) begin
if(1'b1 == readwrite) begin
memory[Ina] = Inb;
end
end
endmodule
datamem_tb.v:
module datamem_tb();
reg [31:0] Ina;
reg [31:0] Inb;
reg enable;
reg readwrite;
reg clk;
reg rst;
wire [31:0] dataOut;
datamem DUT (Ina, Inb, enable, readwrite, dataOut, clk, rst);
initial
begin
Ina <= 32'd0;
Inb <= 32'd0;
enable <= 0;
readwrite <= 0;
#20 Ina <= 32'd1234;
#20 Inb <= 32'd1234;
#20 Ina <= 32'd0517;
#20 Inb <= 32'd10259;
end
always #(Ina or Inb)
#1 $display("| Ina = %d | Inb = %d | dataOut = %d |", Ina, Inb, dataOut);
endmodule
A few things as to why you are getting all 'x:
You never run the clock, you need to add something like the following to have the clock toggle:
initial begin
clk = 1'b0;
forever #5 clk = ~clk;
end
You never assert readwrite which is required to write to your memory module (you set it to 0 on line 20 and never change it). Without being written to, memory will retain its original value of 'x for every element
Aside from that, there are a few other issues with your module:
Use implicit sensitive lists (instead of always #(memory[inA]) use always #(*))
Use non-blocking assignment for your memory write (memory[inA] <= inB)
Consider using $monitor instead of $display for your print statements to avoid timing issues, and you only need call it at the beginning of your initial block in your testbench (http://referencedesigner.com/tutorials/verilog/verilog_09.php)
Your rst and enable arent connected to anything.
Another example of a memory unit implementation can be found here:
Data memory unit
I want to make Frequency Divider with Counter and MUX.
I make 3 module for project
// 4-bit Counter
module Counter (input clk, input reset, output reg[3:0] out);
always#(posedge clk or posedge reset)
begin
if(reset)
out = 4'b0000;
else
begin
if(clk)
if(out < 4'b1111)
out = out + 4'b0001;
else
out = 4'b0000;
end
end
endmodule
//module 4by1 Mux
module Mux (input [3:0] muxin , input [1:0] sel, output reg muxout);
function _4by1mux;
input [3:0] muxin;
input [1:0] sel;
case (sel)
2'b00 : _4by1mux = muxin[0];
2'b01 : _4by1mux = muxin[1];
2'b10 : _4by1mux = muxin[2];
2'b11 : _4by1mux = muxin[3];
endcase
endfunction
assign muxout = _4by1mux(muxin, sel);
endmodule
//module freqDivider
module freqDivider(input clk, input reset, input [1:0] sel, output reg muxout);
wire [3:0]counterbus;
Counter ct1 (clk, reset, counterbus);
Mux mux1 (counterbus, sel, muxout);
endmodule
module freqDivider is top, and I call module Counter and Mux
but module Mux has problem with
Error (10219): Verilog HDL Continuous Assignment error at Mux.v(19):
object "muxout" on left-hand side of assignment must have a net type
this error
ps. input sel will be changed by time
The error is a result of the muxout output having type reg instead of type wire. In verilog, lines can have two overarching types, either nets (like wire type) or variables (like reg types). To assign values/logic to net types, you need to use assign statements and not always blocks. To assign values/logic to variable types, you can only use always blocks and not assign statements. So, you can either make your assign in the Mux module an always block or, for an easier solution, don't make the muxout output a reg, just leave out the reg keyword and it will be a wire.
Error is that you have declared mux_out as reg type, instead of wire type. Default type of any port is wire. You are doing continuous assignment on that net through assign keyword. And on reg type nets, assignment can only be done inside procedural block (initial, always).
Change to mux_out from output reg to output only.
I want to make a module in Verilog which must get a 32 bit wide register variable in port. This variable will be used to count the clock cycle. Then this module will be instantiated in another module. For example: when I fix the value of counter this module must start count from that value.
When I simulate this code I get an error:
Non-net port count cannot be of mode input
module case_1( input clk , input [31:0] counter);
reg [31:0] counter;
always # (posedge clk)
begin
counter <=counter +1
end
endmodule
module counter (input clk , input [31:0] counter )
reg [31:0] counter;
case_1 h1 ( .clk(clk) , .counter(counter) )
endmodule
If a module is an input then you can not drive a value on to it. Driving a value on to an input does not make sense. It needs to be an output.
It think there might be some confusion over the reg and wire types in verilog. These types do not cross module interfaces. a lower (sub) module drives its output as a reg type. the next level up a wire is connected to the port.
From your example a clock received by counter which uses sub module case_1 to implement the counter. Counter value is then driven (first as a reg) then at the top level as a wire.
module case_1(
input clk ,
output reg [31:0] counter
);
initial begin
counter = 'b0;
end
always # (posedge clk) begin
counter <=counter +1;
end
endmodule
module counter (input clk , output wire [31:0] counter );
case_1 h1 ( .clk(clk) , . counter(counter) );
endmodule
Example on EDA Playground.
I am trying to compile my module and it works fine when I remove the badData register from the testbench. However, the moment I add it, verilog complains "Error loading design".
Module Code:
module hamming_code #( parameter TOTAL_LENGTH = 15,
parameter PARITY_BITS = 4
)
(
//inputs
input [TOTAL_LENGTH-1:0] codeword,
//outputs
output [TOTAL_LENGTH-1:0] correctedWord,
output reg badData
);
Testbench code:
`timescale 1ns/1ps
module tb ();
integer pass_count, fail_count;
reg clock;
reg [14:0] cw;
wire [14:0] ccw;
reg error;
integer i;
hamming_code uut (// Inputs
.codeword(cw),
// Outputs
.correctedWord(ccw),
.badData(error)
);
initial begin
// initial values
clock <= 0;
pass_count <= 0;
fail_count <= 0;
error <= 0;
wait(0);
end
always#(*)
#5 clock <= ~clock;
endmodule
BadData is an output from your uut.
It should be connected to a wire in the TB. Also it shouldn't be assigned any value in TB (you are assigning a 0).
When you remove reg error, Its automatically inferred as a wire. that's why there is no error.