Your code simulates two multiplexers. These are actually asynchronous components. The fact that Verilog requires data1_temp
and data2_temp
to be declared as reg
's is a quirk of Verilog syntax and your choice of coding style, and doesn't mean these signals would be the outputs of storage elements in a physical implementation.
If you want to capture these values in actual registers, you need to add those explicitly:
reg [7:0] data1, data2;
always @(posedge someclock) begin
data1 <= data1_tmp;
data2 <= data2_tmp;
end
But I would like to know what this mini register file would be made of in hardware. Particularly, the 4x8 bit array consisting of k0,k1,k2,k3.
You haven't shown how these variables are assigned, so it's not possible to say how they are implemented. As your code showed, just declaring them as reg
doesn't guarantee they are implemented with actual storage elements. If you assign them inside a block that begins always @(posedge clk)
then very likely they are flip-flops, but there are ways you could code them that would make them synthesize differently.
I thought when it came to registers and arrays like this, you need a clock to read out data, like RAM?
You need a clock to update a (physical) register. You can read it out at any time. For example:
wire [8:0] sum;
assign sum = k0 + k1;
is perfectly valid code. sum
will change whenever any of its inputs changes. If k0
and k1
are the outputs of flip-flops, their values will only change when there is a clock edge.
For another example, you could equally well describe your multiplexers with code like this:
reg [7:0] k0, k1, k2, k3;
wire [7:0] data1_tmp;
reg [1:0] reg1;
// k<n> and reg1 are assigned elsewhere.
assign data1_tmp = (reg1 == 0) ? k0 :
(reg1 == 1) ? k1 :
(reg1 == 2) ? k2 : k3;
how do I read from this tag_array and do the comparison all within the same clock cycle?
Let me repeat a key point for emphasis: You need to use a clock to assign a new value to a register (an actual hardware register or group of flip-flops). It's output is available at any time.
RAMs are different and how you access the contents of a RAM will depend on details of the type of RAM you use.
I got confused because frankly I don't know enough about memory hardware and how that's possible.
Another key strategy: When you are learning digital logic, I recommend you learn about the physical hardware first, and then work out or study how to simulate it in HDL second. So first, learn what a physical flip-flop is, then learn the standard Verilog methods of describing a flip-flop. Especially if you are trying to write HDL for synthesis, trying to write good code before you learn the capabilities of the underlying hardware will lead you down a lot of dead-end paths.
This answer is valid for ASICs.
After reading few references on the net I discovered that the question "sync or async" is a kind of "iOS or Android" question. All the below is my opinion on the subject which is biased.
Async resets are pain in the neck because:
- They are glitch sensitive
- They must be deasserted synchronously
- They must be deasserted synchronously, to all flops, at the same clock cycle
- They can cause metastability problems if there are flops which are not reset
While section 1 and 2 are easy to handle, the rest are major issues which require thorough understanding and a whole lot of tools for validation.
And now the painful truth: async resets are still preferable for large systems. The advantages of async resets are:
- Async resets have priority over any other signal
- Async resets do not share combinational paths with other signals
- Async resets do not require clocks
The fact that all the flops are reset, and that all the flops are out of reset at the same clock cycle is a major advantage (and if it does not happen on the same cycle, then this is indicated by tools and awaits for designer's decision). In complex designs (containing many clock domains where each clock is gated tens or hundred of times) it is very difficult to ensure that there are no corner cases when sync resets are used. Async resets are agnostic to these issues (there is still one place where async resets meet clocks - in the deassertion logic, which must be distinct for each clock domain).
The warning you see suggests that all your flops should be reset asynchronously. However, it is a matter of micro-architectural decision which kind of reset to use, and this should be consistent across some defined boundary. Still, if you're sure that non-standard reset is more appropriate in some place - use it and waive the warning.
EDIT:
During scan insertion all the flops in a scan chain are required to function properly. If you're using an externally fed async reset then the above condition is very simple to satisfy - just tie the external net to a non-reset value.
In a sync reset designs the above condition must also be satisfied. This is achieved in the same manner, but since sync resets may share combinational paths with other logic, the tools may erroneously detect flops which can get reset during scan (or not erroneously).
In light of the additional information provided in comments (no async resets at all and this warning is reported for all flops), I believe that you can disable this rule completely. On the other hand, you might want to ensure that your Lint DFT supports sync resets (i.e. it has parallel rules for sync resets, and these rules are enabled)
EDIT2:
I found this great article on the Web. I've never been to SNUG myself, but it seems like there are many designers who favor sync reset schemes. You can find pretty deep analysis of sync and async schemes in the above article, along with many practical advices.
Best Answer
always @ ( signal 1, signal 2......) is a construct used in behavioural modelling.
The code which is present in the block following this construct will run only when any of the signals in the sensitivity list viz signal 1, signal 2... changes.
If you put only posedge clock in the list, the code will run only when there is a positive clock edge and not otherwise. You can use this to create clocked circuits which respond to no other signals but clock. For synchronous reset, then you will write
For your case, you want asynchronous reset. Asynchronous reset means that your circuit should reset whenever reset signal is active 'Irrespective' of clock. Naturally, this should be included in the sensitivity list.