Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Index overflow in FF register file in RV32E configuration #2030

Open
BlooHoosker opened this issue May 11, 2023 · 3 comments
Open

Index overflow in FF register file in RV32E configuration #2030

BlooHoosker opened this issue May 11, 2023 · 3 comments
Labels

Comments

@BlooHoosker
Copy link

Observed Behavior

In the FF register file there is following assignment:
assign rdata_a_o = rf_reg[raddr_a_i];
assign rdata_b_o = rf_reg[raddr_b_i];

When LW instruction is executed and immediate offset is >15, it causes index overflow in rf_reg[raddr_b_i]. This causes X values to propagate through out the CPU from this assignment.

It also causes IbexDataReqPayloadX assert to trigger.

Expected Behavior

It appears that in the LATCH register file this is avoided by:
assign raddr_a_int = raddr_a_i[ADDR_WIDTH-1:0];
assign raddr_b_int = raddr_b_i[ADDR_WIDTH-1:0];
assign waddr_a_int = waddr_a_i[ADDR_WIDTH-1:0];

assign rdata_a_o = mem[raddr_a_int];
assign rdata_b_o = mem[raddr_b_int];

Steps to reproduce the issue

Configure IBEX core with FF register file and RV32E instruction set.

For example following instructions decode will cause the issue:
0x03412783 lw a5,52(sp)

This instruction will cause 20(dec) to be inserted into the rf_reg[20] but that array has only size of 16.

My Environment

I am using the IBEX core with RV32E extension. (reduced register file)

Version of the Ibex source code:
It appears the latest version of FF register file on GIT still has the assignments in question.

assign rdata_a_o = rf_reg[raddr_a_i];
assign rdata_b_o = rf_reg[raddr_b_i];

@BlooHoosker BlooHoosker added the Type:Bug Bugs label May 11, 2023
@rswarbrick
Copy link
Contributor

Hmm, that's odd. Could you generate a simple example firmware (a few lines of assembly!) that shows the problem and paste the code here?

I'm also a bit confused because you're looking at (e.g.) the rdata_a_o output from the register file (filled by reading a register) and executing an LW instruction (which writes to a register). Something seems to be a little amiss!

@BlooHoosker
Copy link
Author

I am looking at rdata_b_o specifically because, while it is an output of register file, it does not seem to be "filled when reading a register" but rather filled with values of register selected by the raddr_b_i address vector. Because it is a purely combinational path.

This is exactly why this seems to happen during LW instruction which does not read any register, but the part of the instruction which is used for raddr_b_i value happens to (sometimes) exceed the value 15 when using RV32E instruction set because there is only 16 registers.

assign rdata_b_o = rf_reg[raddr_b_i]; - this particular assignment ends up with the raddr_b_i index being out of range of rf_reg array. That causes rdata_b_o end up with Xs

Assembly example:
add sp,sp,-64
sw ra,0(sp)
sw t0,4(sp)
sw t1,8(sp)
sw t2,12(sp)
sw a0,16(sp)
sw a1,20(sp)
sw a2,24(sp)
sw a3,28(sp)
sw a4,32(sp)
sw a5,36(sp)
lw ra,0(sp)
lw t0,4(sp)
lw t1,8(sp)
lw t2,12(sp)
lw a0,16(sp) - instruction causing the issue
lw a1,20(sp)
lw a2,24(sp)
lw a3,28(sp)
lw a4,32(sp)
lw a5,36(sp)
add sp,sp,64
mret

@rswarbrick
Copy link
Contributor

Ok, thanks for the response. I'm afraid that I still don't quite understand what's wrong with what you're seeing. Please could you follow up with an example of some firmware, together with the unexpected behaviour? Ideally the behaviour we're talking about should be in terms of architectural registers: it's possible that some other nets in the design will be (correctly) X in some situations.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants