I found one issue with constants being zero which turned out to be a software issue. The assembler was encoding constants incorrectly, it was off by one bit. This caused the constant one to appear to be a zero when decoded by the CPU.
I found a second issue with micro-op translation. The raw micro-op was not completely transferred to the cooked version. This caused constants and other information to be omitted. Fixing this issue shows micro-ops being propagated down the pipeline correctly, but still did not fix the zero constants.
All the instructions making it through the front-end were marked as stomped on. In the micro-op translation the code that marks unused micro-ops was not working correctly, and ended up marking all micro-ops unused.
Some of the fields were not correctly assigned at the data input to the functional results queue. This led to ‘X’s in values and incorrect values.
Finally got the constant one to appear as an immediate in the re-order buffer.
Some results almost make it to the register file now. They are coming out of the queue as ‘00000000x’ instead of ‘000000001’. (They do make it to the register file now).
Decoding for oddball instructions was not complete. This showed up as a commit count of zero resulted. The total instruction count was also zero. I had purposely left this decode as something to be done at a later date…
The instruction count is not working. I am mystified as to why. It is very simple logic. The only thing I could think of is of there is a name conflict of some sort. I called the count ‘I’. So I have renamed it to ‘TotInsn’. How can this code go wrong? Cmtcnt is 4, do_commit is 1, irst is zero, and the clock is happening. I is fixed at zero and it should be incrementing by cmtcnt.
Code:
// Total instructions committed.
always_ff @(posedge clk)
if (irst)
TotInsn <= 40'd0;
else begin
if (do_commit)
TotInsn <= TotInsn + cmtcnt;
end