[libre-riscv-dev] SV branch operation

Luke Kenneth Casson Leighton lkcl at lkcl.net
Mon Oct 8 09:39:40 BST 2018


so i started implementing the parallel branch instruction as
envisaged, where the immediate from BEQ etc. would be "reinterpreted".
this is a standard branch:
BEQ a0, a1, offset(pc)

and this was the plan:
predication_target_register = (offset & 0x1f)
for i in range(VL):
   if cmp(rs1+i, rs2+i)
      regs[predication_target_register] |= 1<<i

however.... unfortunately.... when it came to writing the assembly
code for the unit tests, i learned that it is not possible to write
arbitrary offsets.  rather than modify binutils (which would need
maintenance), i decided instead to go with it and take the predication
target from looking up *rs2* in the predication CSR table.

the pseudocode is listed here:
https://libre-riscv.org/simple_v_extension/specification/#standard_branch

the nice thing is, by leaving the branch offset alone, we might as
well make use of it.  so consequently, if *all* registers tested
successfully pass, the branch goes ahead just as it would for a scalar
(single-compare) branch.  if a branch is not actually needed, then the
branch should be to the following instruction.  a little redundant but
it works.

so:

* if rs1 has a predicate associated with it, that is used to predicate
the compare
* if rs2 has a predicate associated with it, that is used to record
the results of the compares, as a bitfield.
* the branch goes ahead if all tests that are carried out are "true"

thoughts appreciated.

l.



More information about the libre-riscv-dev mailing list