1 ;; Machine description for RISC-V Bit Manipulation operations.
2 ;; Copyright (C) 2021-2023 Free Software Foundation, Inc.
4 ;; This file is part of GCC.
6 ;; GCC is free software; you can redistribute it and/or modify
7 ;; it under the terms of the GNU General Public License as published by
8 ;; the Free Software Foundation; either version 3, or (at your option)
11 ;; GCC is distributed in the hope that it will be useful,
12 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
13 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 ;; GNU General Public License for more details.
16 ;; You should have received a copy of the GNU General Public License
17 ;; along with GCC; see the file COPYING3. If not see
18 ;; <http://www.gnu.org/licenses/>.
22 (define_insn "*zero_extendsidi2_bitmanip"
23 [(set (match_operand:DI 0 "register_operand" "=r,r")
24 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "r,m")))]
25 "TARGET_64BIT && TARGET_ZBA"
29 [(set_attr "type" "bitmanip,load")
30 (set_attr "mode" "DI")])
32 (define_insn "*shNadd"
33 [(set (match_operand:X 0 "register_operand" "=r")
34 (plus:X (ashift:X (match_operand:X 1 "register_operand" "r")
35 (match_operand:QI 2 "imm123_operand" "Ds3"))
36 (match_operand:X 3 "register_operand" "r")))]
39 [(set_attr "type" "bitmanip")
40 (set_attr "mode" "<X:MODE>")])
42 ; When using strength-reduction, we will reduce a multiplication to a
43 ; sequence of shifts and adds. If this is performed with 32-bit types
44 ; and followed by a division, the lack of w-form sh[123]add will make
45 ; combination impossible and lead to a slli + addw being generated.
46 ; Split the sequence with the knowledge that a w-form div will perform
47 ; implicit sign-extensions.
49 [(set (match_operand:DI 0 "register_operand")
50 (sign_extend:DI (div:SI (plus:SI (ashift:SI (subreg:SI (match_operand:DI 1 "register_operand") 0)
51 (match_operand:QI 2 "imm123_operand"))
52 (subreg:SI (match_operand:DI 3 "register_operand") 0))
53 (subreg:SI (match_operand:DI 4 "register_operand") 0))))
54 (clobber (match_operand:DI 5 "register_operand"))]
55 "TARGET_64BIT && TARGET_ZBA"
56 [(set (match_dup 5) (plus:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))
57 (set (match_dup 0) (sign_extend:DI (div:SI (subreg:SI (match_dup 5) 0) (subreg:SI (match_dup 4) 0))))])
59 ; Zba does not provide W-forms of sh[123]add(.uw)?, which leads to an
60 ; interesting irregularity: we can generate a signed 32-bit result
61 ; using slli(.uw)?+ addw, but a unsigned 32-bit result can be more
62 ; efficiently be generated as sh[123]add+zext.w (the .uw can be
63 ; dropped, if we zero-extend the output anyway).
65 ; To enable this optimization, we split [ slli(.uw)?, addw, zext.w ]
66 ; into [ sh[123]add, zext.w ] for use during combine.
68 [(set (match_operand:DI 0 "register_operand")
69 (zero_extend:DI (plus:SI (ashift:SI (subreg:SI (match_operand:DI 1 "register_operand") 0)
70 (match_operand:QI 2 "imm123_operand"))
71 (subreg:SI (match_operand:DI 3 "register_operand") 0))))]
72 "TARGET_64BIT && TARGET_ZBA"
73 [(set (match_dup 0) (plus:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))
74 (set (match_dup 0) (zero_extend:DI (subreg:SI (match_dup 0) 0)))])
77 [(set (match_operand:DI 0 "register_operand")
78 (zero_extend:DI (plus:SI (subreg:SI (and:DI (ashift:DI (match_operand:DI 1 "register_operand")
79 (match_operand:QI 2 "imm123_operand"))
80 (match_operand:DI 3 "consecutive_bits_operand")) 0)
81 (subreg:SI (match_operand:DI 4 "register_operand") 0))))]
82 "TARGET_64BIT && TARGET_ZBA
83 && riscv_shamt_matches_mask_p (INTVAL (operands[2]), INTVAL (operands[3]))"
84 [(set (match_dup 0) (plus:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 4)))
85 (set (match_dup 0) (zero_extend:DI (subreg:SI (match_dup 0) 0)))])
87 ; Make sure that an andi followed by a sh[123]add remains a two instruction
88 ; sequence--and is not torn apart into slli, slri, add.
89 (define_insn_and_split "*andi_add.uw"
90 [(set (match_operand:DI 0 "register_operand" "=r")
91 (plus:DI (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r")
92 (match_operand:QI 2 "imm123_operand" "Ds3"))
93 (match_operand:DI 3 "consecutive_bits_operand" ""))
94 (match_operand:DI 4 "register_operand" "r")))
95 (clobber (match_scratch:DI 5 "=&r"))]
96 "TARGET_64BIT && TARGET_ZBA
97 && riscv_shamt_matches_mask_p (INTVAL (operands[2]), INTVAL (operands[3]))
98 && SMALL_OPERAND (INTVAL (operands[3]) >> INTVAL (operands[2]))"
100 "&& reload_completed"
101 [(set (match_dup 5) (and:DI (match_dup 1) (match_dup 3)))
102 (set (match_dup 0) (plus:DI (ashift:DI (match_dup 5) (match_dup 2))
105 operands[3] = GEN_INT (INTVAL (operands[3]) >> INTVAL (operands[2]));
107 [(set_attr "type" "bitmanip")])
109 (define_insn "*shNadduw"
110 [(set (match_operand:DI 0 "register_operand" "=r")
112 (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r")
113 (match_operand:QI 2 "imm123_operand" "Ds3"))
114 (match_operand 3 "immediate_operand" "n"))
115 (match_operand:DI 4 "register_operand" "r")))]
116 "TARGET_64BIT && TARGET_ZBA
117 && (INTVAL (operands[3]) >> INTVAL (operands[2])) == 0xffffffff"
118 "sh%2add.uw\t%0,%1,%4"
119 [(set_attr "type" "bitmanip")
120 (set_attr "mode" "DI")])
122 ;; During combine, we may encounter an attempt to combine
123 ;; slli rtmp, rs, #imm
125 ;; sh[123]add rd, rtmp, rs2
126 ;; which will lead to the immediate not satisfying the above constraints.
127 ;; By splitting the compound expression, we can simplify to a slli and a
130 [(set (match_operand:DI 0 "register_operand")
131 (plus:DI (and:DI (ashift:DI (match_operand:DI 1 "register_operand")
132 (match_operand:QI 2 "immediate_operand"))
133 (match_operand:DI 3 "consecutive_bits_operand"))
134 (match_operand:DI 4 "register_operand")))
135 (clobber (match_operand:DI 5 "register_operand"))]
136 "TARGET_64BIT && TARGET_ZBA"
137 [(set (match_dup 5) (ashift:DI (match_dup 1) (match_dup 6)))
138 (set (match_dup 0) (plus:DI (and:DI (ashift:DI (match_dup 5)
143 unsigned HOST_WIDE_INT mask = UINTVAL (operands[3]);
144 /* scale: shift within the sh[123]add.uw */
145 unsigned HOST_WIDE_INT scale = 32 - clz_hwi (mask);
146 /* bias: pre-scale amount (i.e. the prior shift amount) */
147 int bias = ctz_hwi (mask) - scale;
149 /* If the bias + scale don't add up to operand[2], reject. */
150 if ((scale + bias) != UINTVAL (operands[2]))
153 /* If the shift-amount is out-of-range for sh[123]add.uw, reject. */
154 if ((scale < 1) || (scale > 3))
157 /* If there's no bias, the '*shNadduw' pattern should have matched. */
161 operands[6] = GEN_INT (bias);
162 operands[7] = GEN_INT (scale);
163 operands[8] = GEN_INT (0xffffffffULL << scale);
166 (define_insn "*add.uw"
167 [(set (match_operand:DI 0 "register_operand" "=r")
168 (plus:DI (zero_extend:DI
169 (match_operand:SI 1 "register_operand" "r"))
170 (match_operand:DI 2 "register_operand" "r")))]
171 "TARGET_64BIT && TARGET_ZBA"
173 [(set_attr "type" "bitmanip")
174 (set_attr "mode" "DI")])
176 (define_insn "*slliuw"
177 [(set (match_operand:DI 0 "register_operand" "=r")
178 (and:DI (ashift:DI (match_operand:DI 1 "register_operand" "r")
179 (match_operand:QI 2 "immediate_operand" "I"))
180 (match_operand 3 "immediate_operand" "n")))]
181 "TARGET_64BIT && TARGET_ZBA
182 && (INTVAL (operands[3]) >> INTVAL (operands[2])) == 0xffffffff"
184 [(set_attr "type" "bitmanip")
185 (set_attr "mode" "DI")])
189 (define_expand "clzdi2"
190 [(set (match_operand:DI 0 "register_operand")
191 (clz:DI (match_operand:DI 1 "register_operand")))]
192 "TARGET_64BIT && (TARGET_ZBB || TARGET_XTHEADBB)")
194 (define_expand "clzsi2"
195 [(set (match_operand:SI 0 "register_operand")
196 (clz:SI (match_operand:SI 1 "register_operand")))]
197 "TARGET_ZBB || (!TARGET_64BIT && TARGET_XTHEADBB)")
199 (define_expand "ctz<mode>2"
200 [(set (match_operand:GPR 0 "register_operand")
201 (ctz:GPR (match_operand:GPR 1 "register_operand")))]
204 (define_expand "popcount<mode>2"
205 [(set (match_operand:GPR 0 "register_operand")
206 (popcount:GPR (match_operand:GPR 1 "register_operand")))]
209 (define_insn "<optab>_not<mode>3"
210 [(set (match_operand:X 0 "register_operand" "=r")
211 (bitmanip_bitwise:X (not:X (match_operand:X 1 "register_operand" "r"))
212 (match_operand:X 2 "register_operand" "r")))]
213 "TARGET_ZBB || TARGET_ZBKB"
215 [(set_attr "type" "bitmanip")
216 (set_attr "mode" "<X:MODE>")])
218 (define_insn_and_split "*<optab>_not_const<mode>"
219 [(set (match_operand:X 0 "register_operand" "=r")
220 (bitmanip_bitwise:X (not:X (match_operand:X 1 "register_operand" "r"))
221 (match_operand:X 2 "const_arith_operand" "I")))
222 (clobber (match_scratch:X 3 "=&r"))]
223 "(TARGET_ZBB || TARGET_ZBKB) && !TARGET_ZCB
224 && !optimize_function_for_size_p (cfun)"
226 "&& reload_completed"
227 [(set (match_dup 3) (match_dup 2))
228 (set (match_dup 0) (bitmanip_bitwise:X (not:X (match_dup 1)) (match_dup 3)))])
230 ;; '(a >= 0) ? b : 0' is emitted branchless (from if-conversion). Without a
231 ;; bit of extra help for combine (i.e., the below split), we end up emitting
232 ;; not/srai/and instead of combining the not into an andn.
234 [(set (match_operand:DI 0 "register_operand")
235 (and:DI (neg:DI (ge:DI (match_operand:DI 1 "register_operand")
237 (match_operand:DI 2 "register_operand")))
238 (clobber (match_operand:DI 3 "register_operand"))]
239 "TARGET_ZBB || TARGET_ZBKB"
240 [(set (match_dup 3) (ashiftrt:DI (match_dup 1) (const_int 63)))
241 (set (match_dup 0) (and:DI (not:DI (match_dup 3)) (match_dup 2)))])
243 (define_insn "*xor_not<mode>"
244 [(set (match_operand:X 0 "register_operand" "=r")
245 (not:X (xor:X (match_operand:X 1 "register_operand" "r")
246 (match_operand:X 2 "register_operand" "r"))))]
247 "TARGET_ZBB || TARGET_ZBKB"
249 [(set_attr "type" "bitmanip")
250 (set_attr "mode" "<X:MODE>")])
252 (define_insn "*<bitmanip_optab>si2"
253 [(set (match_operand:SI 0 "register_operand" "=r")
254 (clz_ctz_pcnt:SI (match_operand:SI 1 "register_operand" "r")))]
256 "<bitmanip_insn>%~\t%0,%1"
257 [(set_attr "type" "<bitmanip_insn>")
258 (set_attr "mode" "SI")])
260 (define_insn "*<bitmanip_optab>disi2"
261 [(set (match_operand:DI 0 "register_operand" "=r")
263 (clz_ctz_pcnt:SI (match_operand:SI 1 "register_operand" "r"))))]
264 "TARGET_64BIT && TARGET_ZBB"
265 "<bitmanip_insn>w\t%0,%1"
266 [(set_attr "type" "<bitmanip_insn>")
267 (set_attr "mode" "SI")])
269 ;; A SImode clz_ctz_pcnt may be extended to DImode via subreg.
270 (define_insn "*<bitmanip_optab>disi2_sext"
271 [(set (match_operand:DI 0 "register_operand" "=r")
273 (clz_ctz_pcnt:SI (match_operand:SI 1 "register_operand" "r")) 0)
274 (match_operand:DI 2 "const_int_operand")))]
275 "TARGET_64BIT && TARGET_ZBB && ((INTVAL (operands[2]) & 0x3f) == 0x3f)"
276 "<bitmanip_insn>w\t%0,%1"
277 [(set_attr "type" "<bitmanip_insn>")
278 (set_attr "mode" "SI")])
280 (define_insn "*<bitmanip_optab>di2"
281 [(set (match_operand:DI 0 "register_operand" "=r")
282 (clz_ctz_pcnt:DI (match_operand:DI 1 "register_operand" "r")))]
283 "TARGET_64BIT && TARGET_ZBB"
284 "<bitmanip_insn>\t%0,%1"
285 [(set_attr "type" "<bitmanip_insn>")
286 (set_attr "mode" "DI")])
288 (define_insn "*zero_extendhi<GPR:mode>2_bitmanip"
289 [(set (match_operand:GPR 0 "register_operand" "=r,r")
290 (zero_extend:GPR (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
295 [(set_attr "type" "bitmanip,load")
296 (set_attr "mode" "<GPR:MODE>")])
298 (define_insn "*extend<SHORT:mode><SUPERQI:mode>2_bitmanip"
299 [(set (match_operand:SUPERQI 0 "register_operand" "=r,r")
301 (match_operand:SHORT 1 "nonimmediate_operand" " r,m")))]
304 sext.<SHORT:size>\t%0,%1
305 l<SHORT:size>\t%0,%1"
306 [(set_attr "type" "bitmanip,load")
307 (set_attr "mode" "<SUPERQI:MODE>")])
309 (define_expand "rotrdi3"
310 [(set (match_operand:DI 0 "register_operand")
311 (rotatert:DI (match_operand:DI 1 "register_operand")
312 (match_operand:QI 2 "arith_operand")))]
313 "TARGET_64BIT && (TARGET_ZBB || TARGET_XTHEADBB || TARGET_ZBKB)"
315 if (TARGET_XTHEADBB && !immediate_operand (operands[2], VOIDmode))
319 (define_insn "*rotrsi3"
320 [(set (match_operand:SI 0 "register_operand" "=r")
321 (rotatert:SI (match_operand:SI 1 "register_operand" "r")
322 (match_operand:QI 2 "arith_operand" "rI")))]
323 "TARGET_ZBB || TARGET_ZBKB"
325 [(set_attr "type" "bitmanip")])
327 (define_expand "rotrsi3"
328 [(set (match_operand:SI 0 "register_operand" "=r")
329 (rotatert:SI (match_operand:SI 1 "register_operand" "r")
330 (match_operand:QI 2 "arith_operand" "rI")))]
331 "TARGET_ZBB || TARGET_ZBKB || TARGET_XTHEADBB"
333 if (TARGET_XTHEADBB && !immediate_operand (operands[2], VOIDmode))
335 if (TARGET_64BIT && register_operand (operands[2], QImode))
337 rtx t = gen_reg_rtx (DImode);
338 emit_insn (gen_rotrsi3_sext (t, operands[1], operands[2]));
339 t = gen_lowpart (SImode, t);
340 SUBREG_PROMOTED_VAR_P (t) = 1;
341 SUBREG_PROMOTED_SET (t, SRP_SIGNED);
342 emit_move_insn (operands[0], t);
347 (define_insn "*rotrdi3"
348 [(set (match_operand:DI 0 "register_operand" "=r")
349 (rotatert:DI (match_operand:DI 1 "register_operand" "r")
350 (match_operand:QI 2 "arith_operand" "rI")))]
351 "TARGET_64BIT && (TARGET_ZBB || TARGET_ZBKB)"
353 [(set_attr "type" "bitmanip")])
355 (define_insn "rotrsi3_sext"
356 [(set (match_operand:DI 0 "register_operand" "=r")
357 (sign_extend:DI (rotatert:SI (match_operand:SI 1 "register_operand" "r")
358 (match_operand:QI 2 "arith_operand" "rI"))))]
359 "TARGET_64BIT && (TARGET_ZBB || TARGET_ZBKB)"
361 [(set_attr "type" "bitmanip")])
363 (define_insn "*rotlsi3"
364 [(set (match_operand:SI 0 "register_operand" "=r")
365 (rotate:SI (match_operand:SI 1 "register_operand" "r")
366 (match_operand:QI 2 "register_operand" "r")))]
367 "TARGET_ZBB || TARGET_ZBKB"
369 [(set_attr "type" "bitmanip")])
371 (define_expand "rotlsi3"
372 [(set (match_operand:SI 0 "register_operand" "=r")
373 (rotate:SI (match_operand:SI 1 "register_operand" "r")
374 (match_operand:QI 2 "register_operand" "r")))]
375 "TARGET_ZBB || TARGET_ZBKB"
379 rtx t = gen_reg_rtx (DImode);
380 emit_insn (gen_rotlsi3_sext (t, operands[1], operands[2]));
381 t = gen_lowpart (SImode, t);
382 SUBREG_PROMOTED_VAR_P (t) = 1;
383 SUBREG_PROMOTED_SET (t, SRP_SIGNED);
384 emit_move_insn (operands[0], t);
389 (define_insn "rotldi3"
390 [(set (match_operand:DI 0 "register_operand" "=r")
391 (rotate:DI (match_operand:DI 1 "register_operand" "r")
392 (match_operand:QI 2 "register_operand" "r")))]
393 "TARGET_64BIT && (TARGET_ZBB || TARGET_ZBKB)"
395 [(set_attr "type" "bitmanip")])
397 (define_insn "rotlsi3_sext"
398 [(set (match_operand:DI 0 "register_operand" "=r")
399 (sign_extend:DI (rotate:SI (match_operand:SI 1 "register_operand" "r")
400 (match_operand:QI 2 "register_operand" "r"))))]
401 "TARGET_64BIT && (TARGET_ZBB || TARGET_ZBKB)"
403 [(set_attr "type" "bitmanip")])
405 (define_insn_and_split "*<bitmanip_optab><GPR:mode>3_mask"
406 [(set (match_operand:GPR 0 "register_operand" "= r")
408 (match_operand:GPR 1 "register_operand" " r")
409 (match_operator 4 "subreg_lowpart_operator"
411 (match_operand:GPR2 2 "register_operand" "r")
412 (match_operand 3 "<GPR:shiftm1>" "<GPR:shiftm1p>"))])))]
413 "TARGET_ZBB || TARGET_ZBKB"
417 (bitmanip_rotate:GPR (match_dup 1)
419 "operands[2] = gen_lowpart (QImode, operands[2]);"
420 [(set_attr "type" "bitmanip")
421 (set_attr "mode" "<GPR:MODE>")])
423 (define_insn_and_split "*<bitmanip_optab>si3_sext_mask"
424 [(set (match_operand:DI 0 "register_operand" "= r")
425 (sign_extend:DI (bitmanip_rotate:SI
426 (match_operand:SI 1 "register_operand" " r")
427 (match_operator 4 "subreg_lowpart_operator"
429 (match_operand:GPR 2 "register_operand" "r")
430 (match_operand 3 "const_si_mask_operand"))]))))]
431 "TARGET_64BIT && (TARGET_ZBB || TARGET_ZBKB)"
435 (sign_extend:DI (bitmanip_rotate:SI (match_dup 1)
437 "operands[2] = gen_lowpart (QImode, operands[2]);"
438 [(set_attr "type" "bitmanip")
439 (set_attr "mode" "DI")])
441 ;; orc.b (or-combine) is added as an unspec for the benefit of the support
442 ;; for optimized string functions (such as strcmp).
443 (define_insn "orcb<mode>2"
444 [(set (match_operand:X 0 "register_operand" "=r")
445 (unspec:X [(match_operand:X 1 "register_operand" "r")] UNSPEC_ORC_B))]
448 [(set_attr "type" "bitmanip")])
450 (define_expand "bswapdi2"
451 [(set (match_operand:DI 0 "register_operand")
452 (bswap:DI (match_operand:DI 1 "register_operand")))]
453 "TARGET_64BIT && (TARGET_ZBB || TARGET_XTHEADBB || TARGET_ZBKB)")
455 (define_expand "bswapsi2"
456 [(set (match_operand:SI 0 "register_operand")
457 (bswap:SI (match_operand:SI 1 "register_operand")))]
458 "TARGET_ZBB || TARGET_ZBKB || TARGET_XTHEADBB"
460 /* Expose bswapsi2 on TARGET_64BIT so that the gimple store
461 merging pass will create suitable bswap insns. We can actually
462 just FAIL that case when generating RTL and let the generic code
464 if (TARGET_64BIT && !TARGET_XTHEADBB)
469 (define_insn "*bswap<mode>2"
470 [(set (match_operand:X 0 "register_operand" "=r")
471 (bswap:X (match_operand:X 1 "register_operand" "r")))]
472 "TARGET_ZBB || TARGET_ZBKB"
474 [(set_attr "type" "bitmanip")])
476 ;; HI bswap can be emulated using SI/DI bswap followed
477 ;; by a logical shift right
478 ;; SI bswap for TARGET_64BIT is already similarly in
480 (define_expand "bswaphi2"
481 [(set (match_operand:HI 0 "register_operand" "=r")
482 (bswap:HI (match_operand:HI 1 "register_operand" "r")))]
485 rtx tmp = gen_reg_rtx (word_mode);
486 rtx newop1 = gen_lowpart (word_mode, operands[1]);
488 emit_insn (gen_bswapdi2 (tmp, newop1));
490 emit_insn (gen_bswapsi2 (tmp, newop1));
491 rtx tmp1 = gen_reg_rtx (word_mode);
493 emit_insn (gen_lshrdi3 (tmp1, tmp, GEN_INT (64 - 16)));
495 emit_insn (gen_lshrsi3 (tmp1, tmp, GEN_INT (32 - 16)));
496 emit_move_insn (operands[0], gen_lowpart (HImode, tmp1));
500 (define_expand "<bitmanip_optab>di3"
501 [(set (match_operand:DI 0 "register_operand" "=r")
502 (bitmanip_minmax:DI (match_operand:DI 1 "register_operand" "r")
503 (match_operand:DI 2 "register_operand" "r")))]
504 "TARGET_64BIT && TARGET_ZBB")
506 (define_expand "<bitmanip_optab>si3"
507 [(set (match_operand:SI 0 "register_operand" "=r")
508 (bitmanip_minmax:SI (match_operand:SI 1 "register_operand" "r")
509 (match_operand:SI 2 "register_operand" "r")))]
514 rtx t = gen_reg_rtx (DImode);
515 operands[1] = force_reg (DImode, gen_rtx_SIGN_EXTEND (DImode, operands[1]));
516 operands[2] = force_reg (DImode, gen_rtx_SIGN_EXTEND (DImode, operands[2]));
517 emit_insn (gen_<bitmanip_optab>di3 (t, operands[1], operands[2]));
518 emit_move_insn (operands[0], gen_lowpart (SImode, t));
523 (define_insn "*<bitmanip_optab><mode>3"
524 [(set (match_operand:X 0 "register_operand" "=r")
525 (bitmanip_minmax:X (match_operand:X 1 "register_operand" "r")
526 (match_operand:X 2 "reg_or_0_operand" "rJ")))]
528 "<bitmanip_insn>\t%0,%1,%z2"
529 [(set_attr "type" "<bitmanip_insn>")])
531 ;; Optimize the common case of a SImode min/max against a constant
532 ;; that is safe both for sign- and zero-extension.
533 (define_insn_and_split "*minmax"
534 [(set (match_operand:DI 0 "register_operand" "=r")
537 (bitmanip_minmax:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "r"))
538 (match_operand:DI 2 "immediate_operand" "i"))
540 (clobber (match_scratch:DI 3 "=&r"))
541 (clobber (match_scratch:DI 4 "=&r"))]
542 "TARGET_64BIT && TARGET_ZBB && sext_hwi (INTVAL (operands[2]), 32) >= 0"
544 "&& reload_completed"
545 [(set (match_dup 3) (sign_extend:DI (match_dup 1)))
546 (set (match_dup 4) (match_dup 2))
547 (set (match_dup 0) (<minmax_optab>:DI (match_dup 3) (match_dup 4)))]
549 [(set_attr "type" "bitmanip")])
553 (define_insn "*bset<mode>"
554 [(set (match_operand:X 0 "register_operand" "=r")
555 (ior:X (ashift:X (const_int 1)
556 (match_operand:QI 2 "register_operand" "r"))
557 (match_operand:X 1 "register_operand" "r")))]
560 [(set_attr "type" "bitmanip")])
562 (define_insn "*bset<mode>_mask"
563 [(set (match_operand:X 0 "register_operand" "=r")
564 (ior:X (ashift:X (const_int 1)
566 (and:X (match_operand:X 2 "register_operand" "r")
567 (match_operand 3 "<X:shiftm1>" "<X:shiftm1p>")) 0))
568 (match_operand:X 1 "register_operand" "r")))]
571 [(set_attr "type" "bitmanip")])
573 (define_insn "*bset<mode>_1"
574 [(set (match_operand:X 0 "register_operand" "=r")
575 (ashift:X (const_int 1)
576 (match_operand:QI 1 "register_operand" "r")))]
579 [(set_attr "type" "bitmanip")])
581 (define_insn "*bset<mode>_1_mask"
582 [(set (match_operand:X 0 "register_operand" "=r")
583 (ashift:X (const_int 1)
585 (and:X (match_operand:X 1 "register_operand" "r")
586 (match_operand 2 "<X:shiftm1>" "<X:shiftm1p>")) 0)))]
589 [(set_attr "type" "bitmanip")])
591 (define_insn "*bseti<mode>"
592 [(set (match_operand:X 0 "register_operand" "=r")
593 (ior:X (match_operand:X 1 "register_operand" "r")
594 (match_operand:X 2 "single_bit_mask_operand" "DbS")))]
597 [(set_attr "type" "bitmanip")])
599 ;; As long as the SImode operand is not a partial subreg, we can use a
600 ;; bseti without postprocessing, as the middle end is smart enough to
601 ;; stay away from the signbit.
602 (define_insn "*bsetidisi"
603 [(set (match_operand:DI 0 "register_operand" "=r")
604 (ior:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "r"))
605 (match_operand 2 "single_bit_mask_operand" "i")))]
606 "TARGET_ZBS && TARGET_64BIT
607 && !partial_subreg_p (operands[1])"
609 [(set_attr "type" "bitmanip")])
611 (define_insn "*bclr<mode>"
612 [(set (match_operand:X 0 "register_operand" "=r")
613 (and:X (rotate:X (const_int -2)
614 (match_operand:QI 2 "register_operand" "r"))
615 (match_operand:X 1 "register_operand" "r")))]
618 [(set_attr "type" "bitmanip")])
620 (define_insn "*bclri<mode>"
621 [(set (match_operand:X 0 "register_operand" "=r")
622 (and:X (match_operand:X 1 "register_operand" "r")
623 (match_operand:X 2 "not_single_bit_mask_operand" "DnS")))]
626 [(set_attr "type" "bitmanip")])
628 ;; In case we have "val & ~IMM" where ~IMM has 2 bits set.
629 (define_insn_and_split "*bclri<mode>_nottwobits"
630 [(set (match_operand:X 0 "register_operand" "=r")
631 (and:X (match_operand:X 1 "register_operand" "r")
632 (match_operand:X 2 "const_nottwobits_not_arith_operand" "i")))]
633 "TARGET_ZBS && !paradoxical_subreg_p (operands[1])"
635 "&& reload_completed"
636 [(set (match_dup 0) (and:X (match_dup 1) (match_dup 3)))
637 (set (match_dup 0) (and:X (match_dup 0) (match_dup 4)))]
639 unsigned HOST_WIDE_INT bits = ~UINTVAL (operands[2]);
640 unsigned HOST_WIDE_INT topbit = HOST_WIDE_INT_1U << floor_log2 (bits);
642 operands[3] = GEN_INT (~bits | topbit);
643 operands[4] = GEN_INT (~topbit);
645 [(set_attr "type" "bitmanip")])
647 ;; In case of a paradoxical subreg, the sign bit and the high bits are
648 ;; not allowed to be changed
649 (define_insn_and_split "*bclridisi_nottwobits"
650 [(set (match_operand:DI 0 "register_operand" "=r")
651 (and:DI (match_operand:DI 1 "register_operand" "r")
652 (match_operand:DI 2 "const_nottwobits_not_arith_operand" "i")))]
653 "TARGET_64BIT && TARGET_ZBS
654 && clz_hwi (~UINTVAL (operands[2])) > 33"
656 "&& reload_completed"
657 [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 3)))
658 (set (match_dup 0) (and:DI (match_dup 0) (match_dup 4)))]
660 unsigned HOST_WIDE_INT bits = ~UINTVAL (operands[2]);
661 unsigned HOST_WIDE_INT topbit = HOST_WIDE_INT_1U << floor_log2 (bits);
663 operands[3] = GEN_INT (~bits | topbit);
664 operands[4] = GEN_INT (~topbit);
666 [(set_attr "type" "bitmanip")])
668 (define_insn "*binv<mode>"
669 [(set (match_operand:X 0 "register_operand" "=r")
670 (xor:X (ashift:X (const_int 1)
671 (match_operand:QI 2 "register_operand" "r"))
672 (match_operand:X 1 "register_operand" "r")))]
675 [(set_attr "type" "bitmanip")])
677 (define_insn "*binvi<mode>"
678 [(set (match_operand:X 0 "register_operand" "=r")
679 (xor:X (match_operand:X 1 "register_operand" "r")
680 (match_operand:X 2 "single_bit_mask_operand" "DbS")))]
683 [(set_attr "type" "bitmanip")])
685 (define_insn "*bext<mode>"
686 [(set (match_operand:X 0 "register_operand" "=r")
687 (zero_extract:X (match_operand:X 1 "register_operand" "r")
690 (match_operand:QI 2 "register_operand" "r"))))]
693 [(set_attr "type" "bitmanip")])
695 ;; When performing `(a & (1UL << bitno)) ? 0 : -1` the combiner
696 ;; usually has the `bitno` typed as X-mode (i.e. no further
697 ;; zero-extension is performed around the bitno).
698 (define_insn "*bext<mode>"
699 [(set (match_operand:X 0 "register_operand" "=r")
700 (zero_extract:X (match_operand:X 1 "register_operand" "r")
702 (match_operand:X 2 "register_operand" "r")))]
705 [(set_attr "type" "bitmanip")])
707 (define_insn "*bexti"
708 [(set (match_operand:X 0 "register_operand" "=r")
709 (zero_extract:X (match_operand:X 1 "register_operand" "r")
711 (match_operand 2 "immediate_operand" "n")))]
712 "TARGET_ZBS && UINTVAL (operands[2]) < GET_MODE_BITSIZE (<MODE>mode)"
714 [(set_attr "type" "bitmanip")])
716 ;; Split for "(a & (1 << BIT_NO)) ? 0 : 1":
717 ;; We avoid reassociating "(~(a >> BIT_NO)) & 1" into "((~a) >> BIT_NO) & 1",
718 ;; so we don't have to use a temporary. Instead we extract the bit and then
719 ;; invert bit 0 ("a ^ 1") only.
721 [(set (match_operand:X 0 "register_operand")
722 (and:X (not:X (lshiftrt:X (match_operand:X 1 "register_operand")
723 (subreg:QI (match_operand:X 2 "register_operand") 0)))
726 [(set (match_dup 0) (zero_extract:X (match_dup 1)
729 (set (match_dup 0) (xor:X (match_dup 0) (const_int 1)))])
731 ;; We can create a polarity-reversed mask (i.e. bit N -> { set = 0, clear = -1 })
732 ;; using a bext(i) followed by an addi instruction.
733 ;; This splits the canonical representation of "(a & (1 << BIT_NO)) ? 0 : -1".
735 [(set (match_operand:GPR 0 "register_operand")
736 (neg:GPR (eq:GPR (zero_extract:GPR (match_operand:GPR 1 "register_operand")
741 [(set (match_dup 0) (zero_extract:GPR (match_dup 1) (const_int 1) (match_dup 2)))
742 (set (match_dup 0) (plus:GPR (match_dup 0) (const_int -1)))])
744 ;; Catch those cases where we can use a bseti/binvi + ori/xori or
745 ;; bseti/binvi + bseti/binvi instead of a lui + addi + or/xor sequence.
746 (define_insn_and_split "*<or_optab>i<mode>_extrabit"
747 [(set (match_operand:X 0 "register_operand" "=r")
748 (any_or:X (match_operand:X 1 "register_operand" "r")
749 (match_operand:X 2 "uimm_extra_bit_or_twobits" "i")))]
752 "&& reload_completed"
753 [(set (match_dup 0) (<or_optab>:X (match_dup 1) (match_dup 3)))
754 (set (match_dup 0) (<or_optab>:X (match_dup 0) (match_dup 4)))]
756 unsigned HOST_WIDE_INT bits = UINTVAL (operands[2]);
757 unsigned HOST_WIDE_INT topbit = HOST_WIDE_INT_1U << floor_log2 (bits);
759 operands[3] = GEN_INT (bits &~ topbit);
760 operands[4] = GEN_INT (topbit);
762 [(set_attr "type" "bitmanip")])
764 ;; Same to use blcri + andi and blcri + bclri
765 (define_insn_and_split "*andi<mode>_extrabit"
766 [(set (match_operand:X 0 "register_operand" "=r")
767 (and:X (match_operand:X 1 "register_operand" "r")
768 (match_operand:X 2 "not_uimm_extra_bit_or_nottwobits" "i")))]
771 "&& reload_completed"
772 [(set (match_dup 0) (and:X (match_dup 1) (match_dup 3)))
773 (set (match_dup 0) (and:X (match_dup 0) (match_dup 4)))]
775 unsigned HOST_WIDE_INT bits = UINTVAL (operands[2]);
776 unsigned HOST_WIDE_INT topbit = HOST_WIDE_INT_1U << floor_log2 (~bits);
778 operands[3] = GEN_INT (bits | topbit);
779 operands[4] = GEN_INT (~topbit);
781 [(set_attr "type" "bitmanip")])
783 ;; IF_THEN_ELSE: test for 2 bits of opposite polarity
784 (define_insn_and_split "*branch<X:mode>_mask_twobits_equals_singlebit"
787 (match_operator 1 "equality_operator"
788 [(and:X (match_operand:X 2 "register_operand" "r")
789 (match_operand:X 3 "const_twobits_not_arith_operand" "i"))
790 (match_operand:X 4 "single_bit_mask_operand" "i")])
791 (label_ref (match_operand 0 "" ""))
793 (clobber (match_scratch:X 5 "=&r"))
794 (clobber (match_scratch:X 6 "=&r"))]
795 "TARGET_ZBS && TARGET_ZBB"
797 "&& reload_completed"
798 [(set (match_dup 5) (zero_extract:X (match_dup 2)
801 (set (match_dup 6) (zero_extract:X (match_dup 2)
804 (set (match_dup 6) (and:X (not:X (match_dup 6)) (match_dup 5)))
805 (set (pc) (if_then_else (match_op_dup 1 [(match_dup 6) (const_int 0)])
806 (label_ref (match_dup 0))
809 unsigned HOST_WIDE_INT twobits_mask = UINTVAL (operands[3]);
810 unsigned HOST_WIDE_INT singlebit_mask = UINTVAL (operands[4]);
812 /* We should never see an unsatisfiable condition. */
813 gcc_assert (twobits_mask & singlebit_mask);
815 int setbit = ctz_hwi (singlebit_mask);
816 int clearbit = ctz_hwi (twobits_mask & ~singlebit_mask);
818 operands[1] = gen_rtx_fmt_ee (GET_CODE (operands[1]) == NE ? EQ : NE,
819 <X:MODE>mode, operands[6], GEN_INT(0));
821 operands[8] = GEN_INT (setbit);
822 operands[9] = GEN_INT (clearbit);
824 [(set_attr "type" "bitmanip")])
826 ;; IF_THEN_ELSE: test for (a & (1 << BIT_NO))
827 (define_insn_and_split "*branch<X:mode>_bext"
830 (match_operator 1 "equality_operator"
831 [(zero_extract:X (match_operand:X 2 "register_operand" "r")
834 (match_operand:QI 3 "register_operand" "r")))
836 (label_ref (match_operand 0 "" ""))
838 (clobber (match_scratch:X 4 "=&r"))]
841 "&& reload_completed"
842 [(set (match_dup 4) (zero_extract:X (match_dup 2)
844 (zero_extend:X (match_dup 3))))
845 (set (pc) (if_then_else (match_op_dup 1 [(match_dup 4) (const_int 0)])
846 (label_ref (match_dup 0))
849 [(set_attr "type" "bitmanip")])
851 ;; ZBKC or ZBC extension
852 (define_insn "riscv_clmul_<mode>"
853 [(set (match_operand:X 0 "register_operand" "=r")
854 (unspec:X [(match_operand:X 1 "register_operand" "r")
855 (match_operand:X 2 "register_operand" "r")]
857 "TARGET_ZBKC || TARGET_ZBC"
859 [(set_attr "type" "clmul")])
861 (define_insn "riscv_clmulh_<mode>"
862 [(set (match_operand:X 0 "register_operand" "=r")
863 (unspec:X [(match_operand:X 1 "register_operand" "r")
864 (match_operand:X 2 "register_operand" "r")]
866 "TARGET_ZBKC || TARGET_ZBC"
868 [(set_attr "type" "clmul")])
871 (define_insn "riscv_clmulr_<mode>"
872 [(set (match_operand:X 0 "register_operand" "=r")
873 (unspec:X [(match_operand:X 1 "register_operand" "r")
874 (match_operand:X 2 "register_operand" "r")]
878 [(set_attr "type" "clmul")])