I need to divide my clock by 10, can someone confirm if my verilog module will work:
//divide oscillator clock by 10 (xc9536) module clk_div10 (in,out) input in; output out; reg[0..3] cnt; always @ (in) begin cnt=cnt+1; if (cnt ==10) begin cnt =0; out =out +1; end end endmodule
I can see a few issues. Do you need a 50% duty cycle on the output clock? That would bring up another issue.
I'll be generous and assume this is not homework, but if it is, realise you're not really learning anything if you don't make your own mistakes; that way the lesson sticks ;)
assign out = cnt[3]; // map MSB to output - previous code needed a // reg // statement, which may or may not have // been absorbed. // always @ (in) always @ (posedge in) // use the edge. The previous statement was a //static sensitivity list, as used in // combinational assignments begin // cnt=cnt+1; // let's not use a blocking assignment
if (cnt[3] & (cnt[2:0])) // test for increment or // reset at top begin cnt
Since you toggle "out" every time your counter reaches 10, you are actually creating a waveform with twice the period you intended. Also, because counting starts at 0 and you compare with 10, there are actually
11 counts between toggles instead of 10.
So, unless I am mistaken (I have not touched verilog much, everything I have worked on so far has been in VHDL), your code would be dividing the clock by 22 instead of 10, assuming it is otherwise functional.
Does "always @(x)" work on _any_ change, i.e. it should react twice on each clock, which would make it right, or does it default to positive edge, which would make it twice the period?
As I said, I have only poked into verilog with a pole... I overlooked that little detail and yes, this does appear to be equivalent to clk'event in VHDL.
In this case, try synthesizing your code with free tools from most FPGA vendors and I think you will get an error saying that you have to pick an edge - the FFs in all FPGAs I know of do not work with both edges, even the DDR IOBs are implemented with two register banks clocked on opposite edges.
It might work the way you intended in simulation but I am almost 100% certain that it will fail in synthesis.
always @(*) will synthesize, at least in some situations, as I have done it before and had no problem. This was with ISE, I can't speak for other synthesis engines.
Sorry, ignore my last post, I looked back and saw that you refering to an actual signal not a catch all, which will also work, if you test the value in the always block, but will create a level sensitive instead of edge triggered (combinatiorial vs sequential) circuit. Here are my corrections to the OP's code and the reasons behind them.
//divide oscillator clock by 10 (xc9536) module clk_div10 (>>>> Correction, this is wrong
There are many things that will synthesize that you really don't want to use. If it makes a transparent latch out of CLB logic, you might not. I don't know what it would do with a FF triggered on both edges.
ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here.
All logos and trade names are the property of their respective owners.