1

I'm learning Verilog, and trying to implement the CD54HC40105 chip. The part that's tripping me up is the bubbling logic.

Basically, this is a FIFO chip, and works by bubbling the words through the memory. One bit per word is used to track whether or not a word exists in that slot.

Here's the logic I need to implement: At any moment, if a word exists in some slot i, (which means ctrl[i] == 1), and no word exists in the next slot (ctrl[i + 1] == 0), then move the word in slot i to the next slot i+1, along with the control signal.

It might look something like this:

// Empty word next to B, it will shift right
+---+---+---+---+
| 1 | 1 | 0 | 0 |
+---+---+---+---+
| A | B |   |   |
+---+---+---+---+

// Empty word next to B and A, they will both shift right
+---+---+---+---+
| 1 | 0 | 1 | 0 |
+---+---+---+---+
| A |   | B |   |
+---+---+---+---+

// Empty word next to A, it will shift right
+---+---+---+---+
| 0 | 1 | 0 | 1 |
+---+---+---+---+
|   | A |   | B |
+---+---+---+---+

// No empty words
+---+---+---+---+
| 0 | 0 | 1 | 1 |
+---+---+---+---+
|   |   | A | B |
+---+---+---+---+

Now, this chip has no clock input, nor does it have any internal clock from the block diagram. Therefore, this is all done using some sort of logic that could be implemented in some sort of always block.

My initial intuition would be that this would be in an always block that is sensitive to a change in the ctrl register.

reg[15:0] ctrl;
// ...
always @(ctrl) begin
    for (i = 0; i < 15; i = i + 1) begin
        if (ctrl[i] == 1 && ctrl[i + 1] == 0) begin
            ctrl[i + 1] <= 1;
            mem[i + 1] <= mem[i];
            ctrl[i] <= 0;
        end
    end
end

But I get the error Array ctrl needs an array index here. I can see why that is, but still I have no idea how I would do this otherwise.

Ideally, I need some syntax that does what this pseudosyntax would do:

// for all i's
always @(posedge ctrl[i]) begin
    // there are 16 slots, so we can never bubble the last index
    if (i != 15 && ctrl[i + 1] == 0) begin
        // ...
    end
end

Edit

I realized that the above pseudosolution wouldn't work because it wouldn't do anything when values are shifted out, causing ctrl[15] to become 0. So what do I do here?

Thanks,

2
  • I'm not sure that you're right about the clock thing: "Each work position in the register is clocked by a control flipflop, which stores a marker bit." The documentation you linked has good description what should be done in your code. Commented Jun 5, 2020 at 10:32
  • Take a look at the diagram — the "clocking" that goes on is simply a term they use for opening up the latch. I meant there is no free running clock that triggers bubbling. Commented Jun 5, 2020 at 10:32

1 Answer 1

1

I would use a generate loop. Here is something to get you started (showing only the data path):

reg [0:16] ctrl;
reg [3:0] mem [0:16];

assign ctrl[0] = si_s;
assign mem[0] = d;

for (genvar i = 1; i <= 16; i++) begin : gen_loop
  always @(*) begin
    if (ctrl[i] && ctrl[i-1]) begin
      mem[i] = mem[i-1];
    end 
  end
end

assign q = mem[16];

If you can use SystemVerilog you may want to use the always_latch keyword, to show intent.

Sign up to request clarification or add additional context in comments.

6 Comments

Thanks! Shouldn't the sensitivity on that also include ctrl[i]? Otherwise when data gets shifted out the end, and ctrl[15] is set to 0, this won't be updated.
Also, I've been having some trouble understanding latches in verilog. Why is this a latch?
Sorry, yes the sensitivity list has to be complete, I have changed the answer to have always @(*). There are still details here that you need to work out, however this should get you started. A latch is a storage element that either sends the input transparently though to the output, or retains the old value. This always block describes that behavior.
Thank you! Verilog tutorials were saying that latches cause bugs and should be avoided, so I thought that was a bad thing. But I couldn't see how that was true, so I assumed they were talking about some other type of "latch".
They are talking about the same type of latch - and indeed, use of latches is something you typically want to avoid. This isn't really saying that latches should never be used (the fact that the IC you are trying to model has them, and the existence of the "always_latch" keyword in SystemVerilog certainly speaks to that), but it is difficult to make them work right in silicon and the Verilog language is designed such that latches are easy to make by mistake.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.