2
\$\begingroup\$

Consider the following device; a ripple counter:

module ripple(out2, out1, out0, clk);

input clk;
output reg out2 = 1'b0, out1 = 1'b0, out0 = 1'b0;

always @ (posedge clk) begin
    out0 = out0 + 1'b1;
end

always @ (negedge out0) begin
    out1 = out1 + 1'b1;
end

always @ (negedge out1) begin
    out2 = out2 + 1'b1;
end

endmodule

Is such a construct generally synthesizable? What determines which connections may be used as clocks?

\$\endgroup\$
2
  • \$\begingroup\$ Sure, it can be, but you usually shouldn't. What problem are you trying to solve, and what kind of hardware are you targeting? Maybe consider a uniformly clocked shift register for ripple outputs. \$\endgroup\$
    – TypeIA
    Oct 29, 2021 at 5:57
  • \$\begingroup\$ Not at all recommended in FPGA. If ASIC, physical design and STA has some work to do to make this asynchronous design work. \$\endgroup\$
    – Mitu Raj
    Oct 29, 2021 at 6:05

3 Answers 3

5
\$\begingroup\$

It may be synthesizable but not generally implementable. Tools that layout a synthesized netlist have to meet timing constraints for setup and hold from output of one register to the input of another. If you make too many ripples, it becomes too difficult to use your outputs if they need to feed into logic with another clock.

\$\endgroup\$
3
  • \$\begingroup\$ Also modern FPGAs have dedicated clock routing fabric designed for high fanout and predictable timing. Even when primitives can be clocked by non-clock-fabric inputs, it fails to take full advantage of the hardware. But, it's not clear OP is designing for a modern FPGA. \$\endgroup\$
    – TypeIA
    Oct 29, 2021 at 6:17
  • \$\begingroup\$ Thanks! I was wondering this because someone told me FPGA's have all the DFFs inside them share a clk signal, such that there can only be one clock. That might be what @TypeIA is mentioning. One other question: When I try to simulate this module, out2 and out1 are actually initialized to 1, instead of 0. I think this is because Verilog considers the initial assignment to itself be a negedge. Is there a way to fix this? \$\endgroup\$ Oct 29, 2021 at 6:50
  • \$\begingroup\$ You can almost always have more than one clock (maybe not on the very smallest parts) but perhaps there are limitations like 1 clock per certain amount of logic, and then the tool will have to put your logic pieces farther away from each other if they use different clocks. \$\endgroup\$
    – user253751
    Oct 29, 2021 at 11:27
2
\$\begingroup\$

Regarding the question about reset, here is a slightly modified code, with a reset input instead of "initialization":

module ripple(
    input clk, rst,
    output reg out2, out1, out0
);

always @ (posedge clk, posedge rst) begin
    if (rst)
        out0 <= 1'b0;
    else
        out0 <= ~out0;
end

always @ (negedge out0, posedge rst) begin
    if (rst)
        out1 <= 1'b0;
    else
        out1 <= ~out1;
end

always @ (negedge out1, posedge rst) begin
    if (rst)
        out2 <= 1'b0;
    else
        out2 <= ~out2;
end

endmodule

Which results in the following systhesis (using Vivado for a Zynq-7000):

enter image description here

Note that the FF clock inputs and feedbacks match your expectation for the ripple design.

\$\endgroup\$
-1
\$\begingroup\$

HDLs are not really designed for rippling designs… as you said rippling designs have no clock, however the concept (in Verilog) is represented by dependency lists.

In short each rippling signal for a construct should go in the sensitivity list.

At least that's my theory I actually never tried it :D

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.