On 1/16/24 09:25, Mary Bennett wrote:
Spec: 
github.com/openhwgroup/core-v-sw/blob/master/specifications/corev-builtin-spec.md

Contributors:
   Mary Bennett <mary.benn...@embecosm.com>
   Nandni Jamnadas <nandni.jamna...@embecosm.com>
   Pietra Ferreira <pietra.ferre...@embecosm.com>
   Charlie Keaney
   Jessica Mills
   Craig Blackmore <craig.blackm...@embecosm.com>
   Simon Cook <simon.c...@embecosm.com>
   Jeremy Bennett <jeremy.benn...@embecosm.com>
   Helene Chelin <helene.che...@embecosm.com>

gcc/ChangeLog:
        * common/config/riscv/riscv-common.cc: Add XCVbitmanip.
        * config/riscv/constraints.md: Likewise.
        * config/riscv/corev.def: Likewise.
        * config/riscv/corev.md: Likewise.
        * config/riscv/predicates.md: Likewise.
        * config/riscv/riscv-builtins.cc (AVAIL): Likewise.
        * config/riscv/riscv-ftypes.def: Likewise.
        * config/riscv/riscv.opt: Likewise.
        * doc/extend.texi: Add XCVbitmanip builtin documentation.
        * doc/sourcebuild.texi: Likewise.

gcc/testsuite/ChangeLog:
        * gcc.target/riscv/cv-bitmanip-compile-bclr.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-bclrr.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-bitrev.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-bset.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-bsetr.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-clb.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-cnt.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-extract.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-extractr.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-extractu.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-extractur.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-ff1.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-fl1.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-insert.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-insertr.c: New test.
        * gcc.target/riscv/cv-bitmanip-compile-ror.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-bclr.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-bitrev.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-bset.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-extract.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-extractu.c: New test.
        * gcc.target/riscv/cv-bitmanip-fail-compile-insert.c: New test.
        * lib/target-supports.exp: Add proc for the XCVbitmanip extension.
---




diff --git a/gcc/config/riscv/corev.md b/gcc/config/riscv/corev.md
index adad2409fb6..9afd69ec080 100644
--- a/gcc/config/riscv/corev.md
+++ b/gcc/config/riscv/corev.md
@@ -706,3 +710,163 @@
[(set_attr "type" "load")
    (set_attr "mode" "SI")])
+
+;; XCVBITMANIP builtins
+
+(define_insn "riscv_cv_bitmanip_extract"
+  [(set (match_operand:SI 0 "register_operand" "=r,r")
+        (sign_extend:SI (and:SI (rotate:SI (ashift:SI (const_int 1)
+                                (ashiftrt:HI
+                                        (match_operand:HI 2 "bit_extract_operand" 
"CV_bit_si10,r")
+                                        (const_int 5)))
+                        (and:HI (match_dup 2)
+                                (const_int 31)))
+               (match_operand:SI 1 "register_operand" "r,r"))))]
So it looks like the you've got an ashift:SI where the shift amount of the result of an ashiftrt:HI -- note the difference in the modes. That doesn't seem right. It also looks like the indentation on the RTL pattern is wrong -- that ashiftrt is an argument of the ashift:SI, so it should line up with the (const_int 1) argument.

It looks like the same issue is repeated on the extractu pattern. Which leads to a second comment. I think the two patterns can be combined. There'a an "any_extend" iterator that you could use in place of the sign_extend/zero_extend. And there's a "u" iterator that you can use in the output template to conditionally emit a "u".

The insertion, bclr, and bset patterns seem to be goofy on their modes in a similar way.


+
+(define_insn "riscv_cv_bitmanip_ff1"
+  [(set (match_operand:QI 0 "register_operand" "=r")
+        (if_then_else (eq:SI (match_operand:SI 1 "register_operand" "r") 
(const_int 0))
+                      (const_int 32)
+                      (minus:SI (ffs:SI (match_dup 1))
+                                (const_int 1))))]
Presumably this is an if-then-else to deal with the case when the input value is zero? Is there any way to use ctz/clz in combination with C[LT]Z_DEFINED_VALUE_AT_ZERO instead of ffs with a conditional?

More generally, can we avoid the UNSPECs in here by defining these operations in terms of ffs, clz, ctz?


+
+(define_insn "riscv_cv_bitmanip_cnt"
+  [(set (match_operand:QI 0 "register_operand" "=r")
+        (truncate:QI (popcount:SI (match_operand:SI 1 "register_operand" 
"r"))))]
+
+  "TARGET_XCVBITMANIP && !TARGET_64BIT"
+  "cv.cnt\t%0,%1"
+  [(set_attr "type" "bitmanip")
+  (set_attr "mode" "SI")])
Interesting truncation here? Does the cv.cnt instruction really just write the result in QImode? Or are you trying to express that the number of bits must be in the range 0..32 inclusive? The former would make your code correct, the latter is better left to the generic VRP optimizer to discover.


+
+(define_insn "riscv_cv_bitmanip_bitrev"
+  [(set (match_operand:SI 0 "register_operand" "=r")
+        (unspec:SI [(match_operand:SI 1 "register_operand" "r")
+                    (match_operand:QI 2 "const_csr_operand" "K")
+                    (match_operand:QI 3 "const_int2_operand" "D03")]
+         UNSPEC_CV_BITMANIP_BITREV))]
Note I think there's a bitreverse opcode now.


Jeff

Reply via email to