1;;- Instruction patterns for the System z vector facility builtins. 2;; Copyright (C) 2015-2020 Free Software Foundation, Inc. 3;; Contributed by Andreas Krebbel (Andreas.Krebbel@de.ibm.com) 4 5;; This file is part of GCC. 6 7;; GCC is free software; you can redistribute it and/or modify it under 8;; the terms of the GNU General Public License as published by the Free 9;; Software Foundation; either version 3, or (at your option) any later 10;; version. 11 12;; GCC is distributed in the hope that it will be useful, but WITHOUT ANY 13;; WARRANTY; without even the implied warranty of MERCHANTABILITY or 14;; FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15;; for more details. 16 17;; You should have received a copy of the GNU General Public License 18;; along with GCC; see the file COPYING3. If not see 19;; <http://www.gnu.org/licenses/>. 20 21; The patterns in this file are enabled with -mzvector 22 23(define_mode_iterator V_HW_32_64 [V4SI V2DI V2DF (V4SF "TARGET_VXE")]) 24(define_mode_iterator VI_HW_SD [V4SI V2DI]) 25(define_mode_iterator V_HW_4 [V4SI V4SF]) 26; Full size vector modes with more than one element which are directly supported in vector registers by the hardware. 27(define_mode_iterator VEC_HW [V16QI V8HI V4SI V2DI V2DF (V4SF "TARGET_VXE")]) 28(define_mode_iterator VECF_HW [(V4SF "TARGET_VXE") V2DF]) 29 30; The element type of the vector with floating point modes translated 31; to int modes of the same size. 32(define_mode_attr non_vec_int[(V1QI "QI") (V2QI "QI") (V4QI "QI") (V8QI "QI") (V16QI "QI") 33 (V1HI "HI") (V2HI "HI") (V4HI "HI") (V8HI "HI") 34 (V1SI "SI") (V2SI "SI") (V4SI "SI") 35 (V1DI "DI") (V2DI "DI") 36 (V1SF "SI") (V2SF "SI") (V4SF "SI") 37 (V1DF "DI") (V2DF "DI")]) 38 39; Condition code modes generated by int comparisons 40(define_mode_iterator VICMP [CCVEQ CCVIH CCVIHU]) 41 42; Comparisons supported by the vec_cmp* builtins 43(define_code_iterator intcmp [eq gt gtu ge geu lt ltu le leu]) 44(define_code_iterator fpcmp [eq gt ge lt le]) 45 46; Comparisons supported by the vec_all/any* builtins 47(define_code_iterator intcmpcc [eq ne gt ge lt le gtu geu ltu leu]) 48(define_code_iterator fpcmpcc [eq ne gt ge unle unlt lt le]) 49 50; Flags for vector string instructions (vfae all 4, vfee only ZS and CS, vstrc all 4) 51(define_constants 52 [(VSTRING_FLAG_IN 8) ; invert result 53 (VSTRING_FLAG_RT 4) ; result type 54 (VSTRING_FLAG_ZS 2) ; zero search 55 (VSTRING_FLAG_CS 1)]) ; condition code set 56 57; Rounding modes as being used for e.g. VFI 58(define_constants 59 [(VEC_RND_CURRENT 0) 60 (VEC_RND_NEAREST_AWAY_FROM_ZERO 1) 61 (VEC_RND_SHORT_PREC 3) 62 (VEC_RND_NEAREST_TO_EVEN 4) 63 (VEC_RND_TO_ZERO 5) 64 (VEC_RND_TO_INF 6) 65 (VEC_RND_TO_MINF 7)]) 66 67; Inexact suppression facility flag as being used for e.g. VFI 68(define_constants 69 [(VEC_INEXACT 0) 70 (VEC_NOINEXACT 4)]) 71 72 73; Vector gather element 74 75; vgef, vgeg 76(define_insn "vec_gather_element<mode>" 77 [(set (match_operand:V_HW_32_64 0 "register_operand" "=v") 78 (unspec:V_HW_32_64 [(match_operand:V_HW_32_64 1 "register_operand" "0") 79 (match_operand:<tointvec> 2 "register_operand" "v") 80 (match_operand:BLK 3 "memory_operand" "R") 81 (match_operand:QI 4 "const_mask_operand" "C")] 82 UNSPEC_VEC_GATHER))] 83 "TARGET_VX && UINTVAL (operands[4]) < GET_MODE_NUNITS (<V_HW_32_64:MODE>mode)" 84 "vge<bhfgq>\t%0,%O3(%v2,%R3),%b4" 85 [(set_attr "op_type" "VRV")]) 86 87(define_expand "vec_genmask<mode>" 88 [(match_operand:VI_HW 0 "register_operand" "=v") 89 (match_operand:QI 1 "const_int_operand" "C") 90 (match_operand:QI 2 "const_int_operand" "C")] 91 "TARGET_VX" 92{ 93 int bitlen = GET_MODE_UNIT_BITSIZE (<VI_HW:MODE>mode); 94 /* To bit little endian style. */ 95 int end = bitlen - 1 - INTVAL (operands[1]); 96 int start = bitlen - 1 - INTVAL (operands[2]); 97 int i; 98 unsigned HOST_WIDE_INT mask; 99 bool swapped_p = false; 100 101 if (start > end) 102 { 103 i = start - 1; start = end + 1; end = i; 104 swapped_p = true; 105 } 106 if (end == 63) 107 mask = HOST_WIDE_INT_M1U; 108 else 109 mask = (HOST_WIDE_INT_1U << (end + 1)) - 1; 110 111 mask &= ~((HOST_WIDE_INT_1U << start) - 1); 112 113 if (swapped_p) 114 mask = ~mask; 115 116 rtx mask_rtx = gen_int_mode (mask, GET_MODE_INNER (<VI_HW:MODE>mode)); 117 118 emit_insn (gen_rtx_SET (operands[0], 119 gen_const_vec_duplicate (<VI_HW:MODE>mode, 120 mask_rtx))); 121 DONE; 122}) 123 124(define_expand "vec_genbytemaskv16qi" 125 [(match_operand:V16QI 0 "register_operand" "") 126 (match_operand:HI 1 "const_int_operand" "")] 127 "TARGET_VX" 128{ 129 int i; 130 unsigned mask = 0x8000; 131 rtx const_vec[16]; 132 unsigned HOST_WIDE_INT byte_mask = UINTVAL (operands[1]); 133 134 for (i = 0; i < 16; i++) 135 { 136 if (mask & byte_mask) 137 const_vec[i] = constm1_rtx; 138 else 139 const_vec[i] = const0_rtx; 140 mask = mask >> 1; 141 } 142 emit_insn (gen_rtx_SET (operands[0], 143 gen_rtx_CONST_VECTOR (V16QImode, 144 gen_rtvec_v (16, const_vec)))); 145 DONE; 146}) 147 148(define_expand "vec_splats<mode>" 149 [(set (match_operand:VEC_HW 0 "register_operand" "") 150 (vec_duplicate:VEC_HW (match_operand:<non_vec> 1 "general_operand" "")))] 151 "TARGET_VX") 152 153(define_expand "vec_insert<mode>" 154 [(set (match_operand:VEC_HW 0 "register_operand" "") 155 (unspec:VEC_HW [(match_operand:<non_vec> 2 "register_operand" "") 156 (match_operand:SI 3 "nonmemory_operand" "") 157 (match_operand:VEC_HW 1 "register_operand" "")] 158 UNSPEC_VEC_SET))] 159 "TARGET_VX" 160 "") 161 162; This is vec_set + modulo arithmetic on the element selector (op 2) 163(define_expand "vec_promote<mode>" 164 [(set (match_operand:VEC_HW 0 "register_operand" "") 165 (unspec:VEC_HW [(match_operand:<non_vec> 1 "register_operand" "") 166 (match_operand:SI 2 "nonmemory_operand" "") 167 (match_dup 0)] 168 UNSPEC_VEC_SET))] 169 "TARGET_VX" 170 "") 171 172; vec_extract is also an RTL standard name -> vector.md 173 174; vllezb, vllezh, vllezf, vllezg 175(define_insn "vec_insert_and_zero<mode>" 176 [(set (match_operand:VEC_HW 0 "register_operand" "=v") 177 (unspec:VEC_HW [(match_operand:<non_vec> 1 "memory_operand" "R")] 178 UNSPEC_VEC_INSERT_AND_ZERO))] 179 "TARGET_VX" 180 "vllez<bhfgq>\t%v0,%1" 181 [(set_attr "op_type" "VRX")]) 182 183; vec_revb (vec_insert_and_zero(x)) bswap-and-replicate-1.c 184; vllebrzh, vllebrzf, vllebrzg 185(define_insn "*vec_insert_and_zero_bswap<mode>" 186 [(set (match_operand:V_HW_HSD 0 "register_operand" "=v") 187 (bswap:V_HW_HSD (unspec:V_HW_HSD 188 [(match_operand:<non_vec> 1 "memory_operand" "R")] 189 UNSPEC_VEC_INSERT_AND_ZERO))) 190 (use (match_operand:V16QI 2 "permute_pattern_operand" "X"))] 191 "TARGET_VXE2" 192 "vllebrz<bhfgq>\t%v0,%1" 193 [(set_attr "op_type" "VRX")]) 194 195 196(define_insn "vlbb" 197 [(set (match_operand:V16QI 0 "register_operand" "=v") 198 (unspec:V16QI [(match_operand:BLK 1 "memory_operand" "R") 199 (match_operand:QI 2 "const_mask_operand" "C")] 200 UNSPEC_VEC_LOAD_BNDRY))] 201 "TARGET_VX && UINTVAL (operands[2]) < 7" 202 "vlbb\t%v0,%1,%2" 203 [(set_attr "op_type" "VRX")]) 204 205; Vector load rightmost with length 206 207(define_expand "vlrlrv16qi" 208 [(set (match_operand:V16QI 0 "register_operand" "") 209 (unspec:V16QI [(match_operand:BLK 2 "memory_operand" "") 210 (match_operand:SI 1 "nonmemory_operand" "")] 211 UNSPEC_VEC_LOAD_LEN_R))] 212 "TARGET_VXE" 213{ 214 /* vlrlr sets all length values beyond 15 to 15. Emulate the same 215 behavior for immediate length operands. vlrl would trigger a 216 SIGILL for too large immediate operands. */ 217 if (CONST_INT_P (operands[1]) 218 && (UINTVAL (operands[1]) & 0xffffffff) > 15) 219 operands[1] = GEN_INT (15); 220}) 221 222(define_insn "*vlrlrv16qi" 223 [(set (match_operand:V16QI 0 "register_operand" "=v, v, v") 224 (unspec:V16QI [(match_operand:BLK 2 "memory_operand" "Q, R, Q") 225 (match_operand:SI 1 "nonmemory_operand" "d,j>f,jb4")] 226 UNSPEC_VEC_LOAD_LEN_R))] 227 "TARGET_VXE" 228 "@ 229 vlrlr\t%v0,%1,%2 230 vl\t%v0,%2%A2 231 vlrl\t%v0,%2,%1" 232 [(set_attr "op_type" "VRS,VRX,VSI")]) 233 234 235; FIXME: The following two patterns might using vec_merge. But what is 236; the canonical form: (vec_select (vec_merge op0 op1)) or (vec_merge 237; (vec_select op0) (vec_select op1) 238; vmrhb, vmrhh, vmrhf, vmrhg 239(define_insn "vec_mergeh<mode>" 240 [(set (match_operand:V_128_NOSINGLE 0 "register_operand" "=v") 241 (unspec:V_128_NOSINGLE [(match_operand:V_128_NOSINGLE 1 "register_operand" "v") 242 (match_operand:V_128_NOSINGLE 2 "register_operand" "v")] 243 UNSPEC_VEC_MERGEH))] 244 "TARGET_VX" 245 "vmrh<bhfgq>\t%v0,%1,%2" 246 [(set_attr "op_type" "VRR")]) 247 248; vmrlb, vmrlh, vmrlf, vmrlg 249(define_insn "vec_mergel<mode>" 250 [(set (match_operand:V_128_NOSINGLE 0 "register_operand" "=v") 251 (unspec:V_128_NOSINGLE [(match_operand:V_128_NOSINGLE 1 "register_operand" "v") 252 (match_operand:V_128_NOSINGLE 2 "register_operand" "v")] 253 UNSPEC_VEC_MERGEL))] 254 "TARGET_VX" 255 "vmrl<bhfgq>\t%v0,%1,%2" 256 [(set_attr "op_type" "VRR")]) 257 258 259; Vector pack 260 261; vpkh, vpkf, vpkg 262(define_insn "vec_pack<mode>" 263 [(set (match_operand:<vec_half> 0 "register_operand" "=v") 264 (unspec:<vec_half> [(match_operand:VI_HW_HSD 1 "register_operand" "v") 265 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 266 UNSPEC_VEC_PACK))] 267 "TARGET_VX" 268 "vpk<bhfgq>\t%v0,%v1,%v2" 269 [(set_attr "op_type" "VRR")]) 270 271 272; Vector pack saturate 273 274; vpksh, vpksf, vpksg 275(define_insn "vec_packs<mode>" 276 [(set (match_operand:<vec_half> 0 "register_operand" "=v") 277 (unspec:<vec_half> [(match_operand:VI_HW_HSD 1 "register_operand" "v") 278 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 279 UNSPEC_VEC_PACK_SATURATE))] 280 "TARGET_VX" 281 "vpks<bhfgq>\t%v0,%v1,%v2" 282 [(set_attr "op_type" "VRR")]) 283 284 285; This is vec_packs_cc + loading cc into a caller specified memory location. 286(define_expand "vec_packs_cc<mode>" 287 [(parallel 288 [(set (reg:CCRAW CC_REGNUM) 289 (unspec:CCRAW [(match_operand:VI_HW_HSD 1 "register_operand" "") 290 (match_operand:VI_HW_HSD 2 "register_operand" "")] 291 UNSPEC_VEC_PACK_SATURATE_GENCC)) 292 (set (match_operand:<vec_half> 0 "register_operand" "") 293 (unspec:<vec_half> [(match_dup 1) (match_dup 2)] 294 UNSPEC_VEC_PACK_SATURATE_CC))]) 295 (set (match_dup 4) 296 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT)) 297 (set (match_operand:SI 3 "memory_operand" "") 298 (match_dup 4))] 299 "TARGET_VX" 300{ 301 operands[4] = gen_reg_rtx (SImode); 302}) 303 304; vpksh, vpksf, vpksg 305(define_insn "*vec_packs_cc<mode>" 306 [(set (reg:CCRAW CC_REGNUM) 307 (unspec:CCRAW [(match_operand:VI_HW_HSD 1 "register_operand" "v") 308 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 309 UNSPEC_VEC_PACK_SATURATE_GENCC)) 310 (set (match_operand:<vec_half> 0 "register_operand" "=v") 311 (unspec:<vec_half> [(match_dup 1) (match_dup 2)] 312 UNSPEC_VEC_PACK_SATURATE_CC))] 313 "TARGET_VX" 314 "vpks<bhfgq>s\t%v0,%v1,%v2" 315 [(set_attr "op_type" "VRR")]) 316 317 318; Vector pack logical saturate 319 320; vpklsh, vpklsf, vpklsg 321(define_insn "vec_packsu<mode>" 322 [(set (match_operand:<vec_half> 0 "register_operand" "=v") 323 (unspec:<vec_half> [(match_operand:VI_HW_HSD 1 "register_operand" "v") 324 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 325 UNSPEC_VEC_PACK_UNSIGNED_SATURATE))] 326 "TARGET_VX" 327 "vpkls<bhfgq>\t%v0,%v1,%v2" 328 [(set_attr "op_type" "VRR")]) 329 330; Emulate saturate unsigned pack on signed operands. 331; Zero out negative elements and continue with the unsigned saturating pack. 332(define_expand "vec_packsu_u<mode>" 333 [(set (match_operand:<vec_half> 0 "register_operand" "=v") 334 (unspec:<vec_half> [(match_operand:VI_HW_HSD 1 "register_operand" "v") 335 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 336 UNSPEC_VEC_PACK_UNSIGNED_SATURATE))] 337 "TARGET_VX" 338{ 339 rtx null_vec = CONST0_RTX(<MODE>mode); 340 machine_mode half_mode; 341 switch (<MODE>mode) 342 { 343 case E_V8HImode: half_mode = V16QImode; break; 344 case E_V4SImode: half_mode = V8HImode; break; 345 case E_V2DImode: half_mode = V4SImode; break; 346 default: gcc_unreachable (); 347 } 348 s390_expand_vcond (operands[1], operands[1], null_vec, 349 GE, operands[1], null_vec); 350 s390_expand_vcond (operands[2], operands[2], null_vec, 351 GE, operands[2], null_vec); 352 emit_insn (gen_rtx_SET (operands[0], 353 gen_rtx_UNSPEC (half_mode, 354 gen_rtvec (2, operands[1], operands[2]), 355 UNSPEC_VEC_PACK_UNSIGNED_SATURATE))); 356 DONE; 357}) 358 359; This is vec_packsu_cc + loading cc into a caller specified memory location. 360; FIXME: The reg to target mem copy should be issued by reload?! 361(define_expand "vec_packsu_cc<mode>" 362 [(parallel 363 [(set (reg:CCRAW CC_REGNUM) 364 (unspec:CCRAW [(match_operand:VI_HW_HSD 1 "register_operand" "") 365 (match_operand:VI_HW_HSD 2 "register_operand" "")] 366 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC)) 367 (set (match_operand:<vec_half> 0 "register_operand" "") 368 (unspec:<vec_half> [(match_dup 1) (match_dup 2)] 369 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC))]) 370 (set (match_dup 4) 371 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT)) 372 (set (match_operand:SI 3 "memory_operand" "") 373 (match_dup 4))] 374 "TARGET_VX" 375{ 376 operands[4] = gen_reg_rtx (SImode); 377}) 378 379; vpklsh, vpklsf, vpklsg 380(define_insn "*vec_packsu_cc<mode>" 381 [(set (reg:CCRAW CC_REGNUM) 382 (unspec:CCRAW [(match_operand:VI_HW_HSD 1 "register_operand" "v") 383 (match_operand:VI_HW_HSD 2 "register_operand" "v")] 384 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_GENCC)) 385 (set (match_operand:<vec_half> 0 "register_operand" "=v") 386 (unspec:<vec_half> [(match_dup 1) (match_dup 2)] 387 UNSPEC_VEC_PACK_UNSIGNED_SATURATE_CC))] 388 "TARGET_VX" 389 "vpkls<bhfgq>s\t%v0,%v1,%v2" 390 [(set_attr "op_type" "VRR")]) 391 392 393; Vector permute 394 395; vec_perm is also RTL standard name, but we can only use it for V16QI 396 397(define_insn "vec_zperm<mode>" 398 [(set (match_operand:V_HW_HSD 0 "register_operand" "=v") 399 (unspec:V_HW_HSD [(match_operand:V_HW_HSD 1 "register_operand" "v") 400 (match_operand:V_HW_HSD 2 "register_operand" "v") 401 (match_operand:V16QI 3 "register_operand" "v")] 402 UNSPEC_VEC_PERM))] 403 "TARGET_VX" 404 "vperm\t%v0,%v1,%v2,%v3" 405 [(set_attr "op_type" "VRR")]) 406 407(define_expand "vec_permi<mode>" 408 [(set (match_operand:V_HW_64 0 "register_operand" "") 409 (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "") 410 (match_operand:V_HW_64 2 "register_operand" "") 411 (match_operand:QI 3 "const_mask_operand" "")] 412 UNSPEC_VEC_PERMI))] 413 "TARGET_VX" 414{ 415 HOST_WIDE_INT val = INTVAL (operands[3]); 416 operands[3] = GEN_INT ((val & 1) | (val & 2) << 1); 417}) 418 419(define_insn "*vec_permi<mode>" 420 [(set (match_operand:V_HW_64 0 "register_operand" "=v") 421 (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "v") 422 (match_operand:V_HW_64 2 "register_operand" "v") 423 (match_operand:QI 3 "const_mask_operand" "C")] 424 UNSPEC_VEC_PERMI))] 425 "TARGET_VX && (UINTVAL (operands[3]) & 10) == 0" 426 "vpdi\t%v0,%v1,%v2,%b3" 427 [(set_attr "op_type" "VRR")]) 428 429 430; Vector replicate 431 432 433; Replicate from vector element 434(define_expand "vec_splat<mode>" 435 [(set (match_operand:V_HW 0 "register_operand" "") 436 (vec_duplicate:V_HW (vec_select:<non_vec> 437 (match_operand:V_HW 1 "register_operand" "") 438 (parallel 439 [(match_operand:QI 2 "const_mask_operand" "")]))))] 440 "TARGET_VX") 441 442; Vector scatter element 443 444; vscef, vsceg 445 446; A 64 bit target address generated from 32 bit elements 447(define_insn "vec_scatter_element<V_HW_4:mode>_DI" 448 [(set (mem:<non_vec> 449 (plus:DI (zero_extend:DI 450 (unspec:SI [(match_operand:V4SI 1 "register_operand" "v") 451 (match_operand:QI 3 "const_mask_operand" "C")] 452 UNSPEC_VEC_EXTRACT)) 453 (match_operand:SI 2 "address_operand" "ZQ"))) 454 (unspec:<non_vec> [(match_operand:V_HW_4 0 "register_operand" "v") 455 (match_dup 3)] UNSPEC_VEC_EXTRACT))] 456 "TARGET_VX && TARGET_64BIT && UINTVAL (operands[3]) < 4" 457 "vscef\t%v0,%O2(%v1,%R2),%3" 458 [(set_attr "op_type" "VRV")]) 459 460; A 31 bit target address is generated from 64 bit elements 461; vsceg 462(define_insn "vec_scatter_element<V_HW_64:mode>_SI" 463 [(set (mem:<non_vec> 464 (plus:SI (subreg:SI 465 (unspec:<non_vec_int> [(match_operand:V_HW_64 1 "register_operand" "v") 466 (match_operand:QI 3 "const_mask_operand" "C")] 467 UNSPEC_VEC_EXTRACT) 4) 468 (match_operand:SI 2 "address_operand" "ZQ"))) 469 (unspec:<non_vec> [(match_operand:V_HW_64 0 "register_operand" "v") 470 (match_dup 3)] UNSPEC_VEC_EXTRACT))] 471 "TARGET_VX && !TARGET_64BIT && UINTVAL (operands[3]) < GET_MODE_NUNITS (<V_HW_64:MODE>mode)" 472 "vsce<V_HW_64:bhfgq>\t%v0,%O2(%v1,%R2),%3" 473 [(set_attr "op_type" "VRV")]) 474 475; Element size and target address size is the same 476; vscef, vsceg 477(define_insn "vec_scatter_element<mode>_<non_vec_int>" 478 [(set (mem:<non_vec> 479 (plus:<non_vec_int> (unspec:<non_vec_int> 480 [(match_operand:<tointvec> 1 "register_operand" "v") 481 (match_operand:QI 3 "const_mask_operand" "C")] 482 UNSPEC_VEC_EXTRACT) 483 (match_operand:DI 2 "address_operand" "ZQ"))) 484 (unspec:<non_vec> [(match_operand:V_HW_32_64 0 "register_operand" "v") 485 (match_dup 3)] UNSPEC_VEC_EXTRACT))] 486 "TARGET_VX && UINTVAL (operands[3]) < GET_MODE_NUNITS (<V_HW_32_64:MODE>mode)" 487 "vsce<bhfgq>\t%v0,%O2(%v1,%R2),%3" 488 [(set_attr "op_type" "VRV")]) 489 490; Depending on the address size we have to expand a different pattern. 491; This however cannot be represented in s390-builtins.def so we do the 492; multiplexing here in the expander. 493(define_expand "vec_scatter_element<V_HW_32_64:mode>" 494 [(match_operand:V_HW_32_64 0 "register_operand" "") 495 (match_operand:<tointvec> 1 "register_operand" "") 496 (match_operand 2 "address_operand" "") 497 (match_operand:QI 3 "const_mask_operand" "")] 498 "TARGET_VX" 499{ 500 if (TARGET_64BIT) 501 { 502 PUT_MODE (operands[2], DImode); 503 emit_insn ( 504 gen_vec_scatter_element<V_HW_32_64:mode>_DI (operands[0], operands[1], 505 operands[2], operands[3])); 506 } 507 else 508 { 509 PUT_MODE (operands[2], SImode); 510 emit_insn ( 511 gen_vec_scatter_element<V_HW_32_64:mode>_SI (operands[0], operands[1], 512 operands[2], operands[3])); 513 } 514 DONE; 515}) 516 517 518; Vector select 519 520; for all b in bits op0[b] = op3[b] == 0 ? op2[b] : op1[b] 521; implemented as: op0 = (op1 & op3) | (op2 & ~op3) 522 523; Used to expand the vec_sel builtin. Operands op1 and op2 already got 524; swapped in s390-c.c when we get here. 525 526(define_insn "vsel<mode>" 527 [(set (match_operand:V_HW 0 "register_operand" "=v") 528 (ior:V_HW 529 (and:V_HW (match_operand:V_HW 1 "register_operand" "v") 530 (match_operand:V_HW 3 "register_operand" "v")) 531 (and:V_HW (not:V_HW (match_dup 3)) 532 (match_operand:V_HW 2 "register_operand" "v"))))] 533 "TARGET_VX" 534 "vsel\t%v0,%1,%2,%3" 535 [(set_attr "op_type" "VRR")]) 536 537 538; Vector sign extend to doubleword 539 540; Sign extend of right most vector element to respective double-word 541; vsegb, vsegh, vsegf 542(define_insn "vec_extend<mode>" 543 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 544 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 545 UNSPEC_VEC_EXTEND))] 546 "TARGET_VX" 547 "vseg<bhfgq>\t%v0,%1" 548 [(set_attr "op_type" "VRR")]) 549 550 551; Vector store with length 552 553; Store bytes in OP1 from OP0 with the highest indexed byte to be 554; stored from OP0 given by OP2 555(define_insn "vstl<mode>" 556 [(set (match_operand:BLK 2 "memory_operand" "=Q") 557 (unspec:BLK [(match_operand:V 0 "register_operand" "v") 558 (match_operand:SI 1 "register_operand" "d")] 559 UNSPEC_VEC_STORE_LEN))] 560 "TARGET_VX" 561 "vstl\t%v0,%1,%2" 562 [(set_attr "op_type" "VRS")]) 563 564; Vector store rightmost with length 565 566(define_expand "vstrlrv16qi" 567 [(set (match_operand:BLK 2 "memory_operand" "") 568 (unspec:BLK [(match_operand:V16QI 0 "register_operand" "") 569 (match_operand:SI 1 "nonmemory_operand" "")] 570 UNSPEC_VEC_STORE_LEN_R))] 571 "TARGET_VXE" 572{ 573 /* vstrlr sets all length values beyond 15 to 15. Emulate the same 574 behavior for immediate length operands. vstrl would trigger a 575 SIGILL for too large immediate operands. */ 576 if (CONST_INT_P (operands[1]) 577 && (UINTVAL (operands[1]) & 0xffffffff) > 15) 578 operands[1] = GEN_INT (15); 579}) 580 581(define_insn "*vstrlrv16qi" 582 [(set (match_operand:BLK 2 "memory_operand" "=Q, R, Q") 583 (unspec:BLK [(match_operand:V16QI 0 "register_operand" "v, v, v") 584 (match_operand:SI 1 "nonmemory_operand" "d,j>f,jb4")] 585 UNSPEC_VEC_STORE_LEN_R))] 586 "TARGET_VXE" 587 "@ 588 vstrlr\t%v0,%1,%2 589 vst\t%v0,%2%A2 590 vstrl\t%v0,%2,%1" 591 [(set_attr "op_type" "VRS,VRX,VSI")]) 592 593 594 595; vector bit permute 596 597(define_insn "vbpermv16qi" 598 [(set (match_operand:V2DI 0 "register_operand" "=v") 599 (unspec:V2DI [(match_operand:V16QI 1 "register_operand" "v") 600 (match_operand:V16QI 2 "register_operand" "v")] 601 UNSPEC_VEC_VBPERM))] 602 "TARGET_VXE" 603 "vbperm\t%v0,%v1,%v2" 604 [(set_attr "op_type" "VRR")]) 605 606; Vector unpack high 607 608; vuphb, vuphh, vuphf 609(define_insn "vec_unpackh<mode>" 610 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 611 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 612 UNSPEC_VEC_UNPACKH))] 613 "TARGET_VX" 614 "vuph<bhfgq>\t%v0,%v1" 615 [(set_attr "op_type" "VRR")]) 616 617; vuplhb, vuplhh, vuplhf 618(define_insn "vec_unpackh_l<mode>" 619 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 620 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 621 UNSPEC_VEC_UNPACKH_L))] 622 "TARGET_VX" 623 "vuplh<bhfgq>\t%v0,%v1" 624 [(set_attr "op_type" "VRR")]) 625 626 627; Vector unpack low 628 629; vuplb, vuplhw, vuplf 630(define_insn "vec_unpackl<mode>" 631 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 632 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 633 UNSPEC_VEC_UNPACKL))] 634 "TARGET_VX" 635 "vupl<bhfgq><w>\t%v0,%v1" 636 [(set_attr "op_type" "VRR")]) 637 638; vupllb, vupllh, vupllf 639(define_insn "vec_unpackl_l<mode>" 640 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 641 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 642 UNSPEC_VEC_UNPACKL_L))] 643 "TARGET_VX" 644 "vupll<bhfgq>\t%v0,%v1" 645 [(set_attr "op_type" "VRR")]) 646 647 648; Vector add 649 650; Vector add compute carry 651 652; vaccb, vacch, vaccf, vaccg, vaccq 653(define_insn "vacc<bhfgq>_<mode>" 654 [(set (match_operand:VIT_HW 0 "register_operand" "=v") 655 (unspec:VIT_HW [(match_operand:VIT_HW 1 "register_operand" "v") 656 (match_operand:VIT_HW 2 "register_operand" "v")] 657 UNSPEC_VEC_ADDC))] 658 "TARGET_VX" 659 "vacc<bhfgq>\t%v0,%v1,%v2" 660 [(set_attr "op_type" "VRR")]) 661 662; Vector add with carry 663 664(define_insn "vacq" 665 [(set (match_operand:TI 0 "register_operand" "=v") 666 (unspec:TI [(match_operand:TI 1 "register_operand" "v") 667 (match_operand:TI 2 "register_operand" "v") 668 (match_operand:TI 3 "register_operand" "v")] 669 UNSPEC_VEC_ADDE_U128))] 670 "TARGET_VX" 671 "vacq\t%v0,%v1,%v2,%v3" 672 [(set_attr "op_type" "VRR")]) 673 674 675; Vector add with carry compute carry 676 677(define_insn "vacccq" 678 [(set (match_operand:TI 0 "register_operand" "=v") 679 (unspec:TI [(match_operand:TI 1 "register_operand" "v") 680 (match_operand:TI 2 "register_operand" "v") 681 (match_operand:TI 3 "register_operand" "v")] 682 UNSPEC_VEC_ADDEC_U128))] 683 "TARGET_VX" 684 "vacccq\t%v0,%v1,%v2,%v3" 685 [(set_attr "op_type" "VRR")]) 686 687 688; Vector and 689 690; Vector and with complement 691 692; vnc 693(define_insn "vec_andc<mode>3" 694 [(set (match_operand:VT_HW 0 "register_operand" "=v") 695 (and:VT_HW (not:VT_HW (match_operand:VT_HW 2 "register_operand" "v")) 696 (match_operand:VT_HW 1 "register_operand" "v")))] 697 "TARGET_VX" 698 "vnc\t%v0,%v1,%v2" 699 [(set_attr "op_type" "VRR")]) 700 701 702; Vector average 703 704; vavgb, vavgh, vavgf, vavgg 705(define_insn "vec_avg<mode>" 706 [(set (match_operand:VI_HW 0 "register_operand" "=v") 707 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "v") 708 (match_operand:VI_HW 2 "register_operand" "v")] 709 UNSPEC_VEC_AVG))] 710 "TARGET_VX" 711 "vavg<bhfgq>\t%v0,%v1,%v2" 712 [(set_attr "op_type" "VRR")]) 713 714; Vector average logical 715 716; vavglb, vavglh, vavglf, vavglg 717(define_insn "vec_avgu<mode>" 718 [(set (match_operand:VI_HW 0 "register_operand" "=v") 719 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "v") 720 (match_operand:VI_HW 2 "register_operand" "v")] 721 UNSPEC_VEC_AVGU))] 722 "TARGET_VX" 723 "vavgl<bhfgq>\t%v0,%v1,%v2" 724 [(set_attr "op_type" "VRR")]) 725 726 727; Vector checksum 728 729(define_insn "vec_checksum" 730 [(set (match_operand:V4SI 0 "register_operand" "=v") 731 (unspec:V4SI [(match_operand:V4SI 1 "register_operand" "v") 732 (match_operand:V4SI 2 "register_operand" "v")] 733 UNSPEC_VEC_CHECKSUM))] 734 "TARGET_VX" 735 "vcksm\t%v0,%v1,%v2" 736 [(set_attr "op_type" "VRR")]) 737 738;; 739;; Vector compare 740;; 741 742; vec_all/any int compares 743 744(define_expand "vec_all_<intcmpcc:code><VI_HW:mode>" 745 [(match_operand:SI 0 "register_operand" "") 746 (intcmpcc (match_operand:VI_HW 1 "register_operand" "") 747 (match_operand:VI_HW 2 "register_operand" ""))] 748 "TARGET_VX" 749{ 750 s390_expand_vec_compare_cc (operands[0], 751 <intcmpcc:CODE>, 752 operands[1], 753 operands[2], 754 true); 755 DONE; 756}) 757 758(define_expand "vec_any_<intcmpcc:code><VI_HW:mode>" 759 [(match_operand:SI 0 "register_operand" "") 760 (intcmpcc (match_operand:VI_HW 1 "register_operand" "") 761 (match_operand:VI_HW 2 "register_operand" ""))] 762 "TARGET_VX" 763{ 764 s390_expand_vec_compare_cc (operands[0], 765 <intcmpcc:CODE>, 766 operands[1], 767 operands[2], 768 false); 769 DONE; 770}) 771 772; vec_all/any fp compares 773 774(define_expand "vec_all_<fpcmpcc:code><mode>" 775 [(match_operand:SI 0 "register_operand" "") 776 (fpcmpcc (match_operand:VECF_HW 1 "register_operand" "") 777 (match_operand:VECF_HW 2 "register_operand" ""))] 778 "TARGET_VX" 779{ 780 s390_expand_vec_compare_cc (operands[0], 781 <fpcmpcc:CODE>, 782 operands[1], 783 operands[2], 784 true); 785 DONE; 786}) 787 788(define_expand "vec_any_<fpcmpcc:code><mode>" 789 [(match_operand:SI 0 "register_operand" "") 790 (fpcmpcc (match_operand:VECF_HW 1 "register_operand" "") 791 (match_operand:VECF_HW 2 "register_operand" ""))] 792 "TARGET_VX" 793{ 794 s390_expand_vec_compare_cc (operands[0], 795 <fpcmpcc:CODE>, 796 operands[1], 797 operands[2], 798 false); 799 DONE; 800}) 801 802 803; Compare without generating CC 804 805(define_expand "vec_cmp<intcmp:code><VI_HW:mode>" 806 [(set (match_operand:VI_HW 0 "register_operand" "=v") 807 (intcmp:VI_HW (match_operand:VI_HW 1 "register_operand" "v") 808 (match_operand:VI_HW 2 "register_operand" "v")))] 809 "TARGET_VX" 810{ 811 s390_expand_vec_compare (operands[0], <intcmp:CODE>, operands[1], operands[2]); 812 DONE; 813}) 814 815(define_expand "vec_cmp<fpcmp:code><mode>" 816 [(set (match_operand:<tointvec> 0 "register_operand" "=v") 817 (fpcmp:<tointvec> (match_operand:VF_HW 1 "register_operand" "v") 818 (match_operand:VF_HW 2 "register_operand" "v")))] 819 "TARGET_VX" 820{ 821 s390_expand_vec_compare (operands[0], <fpcmp:CODE>, operands[1], operands[2]); 822 DONE; 823}) 824 825 826; Vector count leading zeros 827 828; vec_cntlz -> clz 829; vec_cnttz -> ctz 830 831; Vector xor 832 833; vec_xor -> xor 834 835; Vector Galois field multiply sum 836 837; vgfmb, vgfmh, vgfmf 838(define_insn "vec_gfmsum<mode>" 839 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 840 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 841 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 842 UNSPEC_VEC_GFMSUM))] 843 "TARGET_VX" 844 "vgfm<bhfgq>\t%v0,%v1,%v2" 845 [(set_attr "op_type" "VRR")]) 846 847(define_insn "vec_gfmsum_128" 848 [(set (match_operand:V16QI 0 "register_operand" "=v") 849 (unspec:V16QI [(match_operand:V2DI 1 "register_operand" "v") 850 (match_operand:V2DI 2 "register_operand" "v")] 851 UNSPEC_VEC_GFMSUM_128))] 852 "TARGET_VX" 853 "vgfmg\t%v0,%v1,%v2" 854 [(set_attr "op_type" "VRR")]) 855 856; vgfmab, vgfmah, vgfmaf 857(define_insn "vec_gfmsum_accum<mode>" 858 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 859 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v") 860 (match_operand:VI_HW_QHS 2 "register_operand" "v") 861 (match_operand:<vec_double> 3 "register_operand" "v")] 862 UNSPEC_VEC_GFMSUM_ACCUM))] 863 "TARGET_VX" 864 "vgfma<bhfgq>\t%v0,%v1,%v2,%v3" 865 [(set_attr "op_type" "VRR")]) 866 867(define_insn "vec_gfmsum_accum_128" 868 [(set (match_operand:V16QI 0 "register_operand" "=v") 869 (unspec:V16QI [(match_operand:V2DI 1 "register_operand" "v") 870 (match_operand:V2DI 2 "register_operand" "v") 871 (match_operand:V16QI 3 "register_operand" "v")] 872 UNSPEC_VEC_GFMSUM_ACCUM_128))] 873 "TARGET_VX" 874 "vgfmag\t%v0,%v1,%v2,%v3" 875 [(set_attr "op_type" "VRR")]) 876 877 878; FIXME: vec_neg ? 879 880; Vector load positive: vec_abs -> abs 881; Vector maximum vec_max -> smax, logical vec_max -> umax 882; Vector maximum vec_min -> smin, logical vec_min -> umin 883 884 885; Vector multiply and add high 886 887; vec_mladd -> vec_vmal 888; vmalb, vmalh, vmalf, vmalg 889(define_insn "vec_vmal<mode>" 890 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 891 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 892 (match_operand:VI_HW_QHS 2 "register_operand" "v") 893 (match_operand:VI_HW_QHS 3 "register_operand" "v")] 894 UNSPEC_VEC_VMAL))] 895 "TARGET_VX" 896 "vmal<bhfgq><w>\t%v0,%v1,%v2,%v3" 897 [(set_attr "op_type" "VRR")]) 898 899; vec_mhadd -> vec_vmah/vec_vmalh 900 901; vmahb; vmahh, vmahf, vmahg 902(define_insn "vec_vmah<mode>" 903 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 904 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 905 (match_operand:VI_HW_QHS 2 "register_operand" "v") 906 (match_operand:VI_HW_QHS 3 "register_operand" "v")] 907 UNSPEC_VEC_VMAH))] 908 "TARGET_VX" 909 "vmah<bhfgq>\t%v0,%v1,%v2,%v3" 910 [(set_attr "op_type" "VRR")]) 911 912; vmalhb; vmalhh, vmalhf, vmalhg 913(define_insn "vec_vmalh<mode>" 914 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 915 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 916 (match_operand:VI_HW_QHS 2 "register_operand" "v") 917 (match_operand:VI_HW_QHS 3 "register_operand" "v")] 918 UNSPEC_VEC_VMALH))] 919 "TARGET_VX" 920 "vmalh<bhfgq>\t%v0,%v1,%v2,%v3" 921 [(set_attr "op_type" "VRR")]) 922 923; vec_meadd -> vec_vmae/vec_vmale 924 925; vmaeb; vmaeh, vmaef, vmaeg 926(define_insn "vec_vmae<mode>" 927 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 928 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v") 929 (match_operand:VI_HW_QHS 2 "register_operand" "v") 930 (match_operand:<vec_double> 3 "register_operand" "v")] 931 UNSPEC_VEC_VMAE))] 932 "TARGET_VX" 933 "vmae<bhfgq>\t%v0,%v1,%v2,%v3" 934 [(set_attr "op_type" "VRR")]) 935 936; vmaleb; vmaleh, vmalef, vmaleg 937(define_insn "vec_vmale<mode>" 938 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 939 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v") 940 (match_operand:VI_HW_QHS 2 "register_operand" "v") 941 (match_operand:<vec_double> 3 "register_operand" "v")] 942 UNSPEC_VEC_VMALE))] 943 "TARGET_VX" 944 "vmale<bhfgq>\t%v0,%v1,%v2,%v3" 945 [(set_attr "op_type" "VRR")]) 946 947; vec_moadd -> vec_vmao/vec_vmalo 948 949; vmaob; vmaoh, vmaof, vmaog 950(define_insn "vec_vmao<mode>" 951 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 952 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v") 953 (match_operand:VI_HW_QHS 2 "register_operand" "v") 954 (match_operand:<vec_double> 3 "register_operand" "v")] 955 UNSPEC_VEC_VMAO))] 956 "TARGET_VX" 957 "vmao<bhfgq>\t%v0,%v1,%v2,%v3" 958 [(set_attr "op_type" "VRR")]) 959 960; vmalob; vmaloh, vmalof, vmalog 961(define_insn "vec_vmalo<mode>" 962 [(set (match_operand:<vec_double> 0 "register_operand" "=v") 963 (unspec:<vec_double> [(match_operand:VI_HW_QHS 1 "register_operand" "v") 964 (match_operand:VI_HW_QHS 2 "register_operand" "v") 965 (match_operand:<vec_double> 3 "register_operand" "v")] 966 UNSPEC_VEC_VMALO))] 967 "TARGET_VX" 968 "vmalo<bhfgq>\t%v0,%v1,%v2,%v3" 969 [(set_attr "op_type" "VRR")]) 970 971 972; Vector multiply high 973 974; vec_mulh -> vec_smulh/vec_umulh 975 976; vmhb, vmhh, vmhf 977(define_insn "vec_smulh<mode>" 978 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 979 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 980 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 981 UNSPEC_VEC_SMULT_HI))] 982 "TARGET_VX" 983 "vmh<bhfgq>\t%v0,%v1,%v2" 984 [(set_attr "op_type" "VRR")]) 985 986; vmlhb, vmlhh, vmlhf 987(define_insn "vec_umulh<mode>" 988 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 989 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 990 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 991 UNSPEC_VEC_UMULT_HI))] 992 "TARGET_VX" 993 "vmlh<bhfgq>\t%v0,%v1,%v2" 994 [(set_attr "op_type" "VRR")]) 995 996 997; Vector multiply low 998 999; vec_mule -> vec_widen_umult_even/vec_widen_smult_even 1000; vec_mulo -> vec_widen_umult_odd/vec_widen_smult_odd 1001 1002 1003; Vector nor 1004 1005(define_insn "vec_nor<mode>3" 1006 [(set (match_operand:VT_HW 0 "register_operand" "=v") 1007 (not:VT_HW 1008 (ior:VT_HW (match_operand:VT_HW 1 "register_operand" "v") 1009 (match_operand:VT_HW 2 "register_operand" "v"))))] 1010 "TARGET_VX" 1011 "vno\t%v0,%v1,%v2" 1012 [(set_attr "op_type" "VRR")]) 1013 1014 1015; Vector or 1016 1017; Vector population count vec_popcnt -> popcount 1018; Vector element rotate left logical vec_rl -> vrotl, vec_rli -> rot 1019 1020; Vector element rotate and insert under mask 1021 1022; verimb, verimh, verimf, verimg 1023(define_insn "verim<mode>" 1024 [(set (match_operand:VI_HW 0 "register_operand" "=v") 1025 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "0") 1026 (match_operand:VI_HW 2 "register_operand" "v") 1027 (match_operand:VI_HW 3 "register_operand" "v") 1028 (match_operand:QI 4 "const_int_operand" "C")] 1029 UNSPEC_VEC_RL_MASK))] 1030 "TARGET_VX" 1031 "verim<bhfgq>\t%v0,%v2,%v3,%b4" 1032 [(set_attr "op_type" "VRI")]) 1033 1034 1035; Vector shift left 1036 1037(define_insn "vec_sll<VI_HW:mode><VI_HW_QHS:mode>" 1038 [(set (match_operand:VI_HW 0 "register_operand" "=v") 1039 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "v") 1040 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 1041 UNSPEC_VEC_SLL))] 1042 "TARGET_VX" 1043 "vsl\t%v0,%v1,%v2" 1044 [(set_attr "op_type" "VRR")]) 1045 1046 1047; Vector shift left by byte 1048 1049; Pattern definition in vector.md, see vec_vslb 1050(define_expand "vec_slb<mode>" 1051 [(set (match_operand:V_HW 0 "register_operand" "") 1052 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "") 1053 (match_operand:<tointvec> 2 "register_operand" "")] 1054 UNSPEC_VEC_SLB))] 1055 "TARGET_VX" 1056{ 1057 PUT_MODE (operands[2], V16QImode); 1058}) 1059 1060; Vector shift left double by byte 1061 1062(define_insn "vec_sld<mode>" 1063 [(set (match_operand:V_HW 0 "register_operand" "=v") 1064 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "v") 1065 (match_operand:V_HW 2 "register_operand" "v") 1066 (match_operand:QI 3 "const_int_operand" "C")] 1067 UNSPEC_VEC_SLDBYTE))] 1068 "TARGET_VX" 1069 "vsldb\t%v0,%v1,%v2,%b3" 1070 [(set_attr "op_type" "VRI")]) 1071 1072(define_expand "vec_sldw<mode>" 1073 [(set (match_operand:V_HW 0 "register_operand" "") 1074 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "") 1075 (match_operand:V_HW 2 "register_operand" "") 1076 (match_operand:QI 3 "const_int_operand" "")] 1077 UNSPEC_VEC_SLDBYTE))] 1078 "TARGET_VX" 1079{ 1080 operands[3] = GEN_INT (INTVAL (operands[3]) << 2); 1081}) 1082 1083; Vector shift left double by bit 1084 1085(define_insn "vec_sldb<mode>" 1086 [(set (match_operand:V_HW 0 "register_operand" "=v") 1087 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "v") 1088 (match_operand:V_HW 2 "register_operand" "v") 1089 (match_operand:QI 3 "const_int_operand" "C")] 1090 UNSPEC_VEC_SLDBIT))] 1091 "TARGET_VXE2" 1092 "vsld\t%v0,%v1,%v2,%b3" 1093 [(set_attr "op_type" "VRI")]) 1094 1095; Vector shift right double by bit 1096 1097(define_insn "vec_srdb<mode>" 1098 [(set (match_operand:V_HW 0 "register_operand" "=v") 1099 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "v") 1100 (match_operand:V_HW 2 "register_operand" "v") 1101 (match_operand:QI 3 "const_int_operand" "C")] 1102 UNSPEC_VEC_SRDBIT))] 1103 "TARGET_VXE2" 1104 "vsrd\t%v0,%v1,%v2,%b3" 1105 [(set_attr "op_type" "VRI")]) 1106 1107; Vector shift right arithmetic 1108 1109(define_insn "vec_sral<VI_HW:mode><VI_HW_QHS:mode>" 1110 [(set (match_operand:VI_HW 0 "register_operand" "=v") 1111 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "v") 1112 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 1113 UNSPEC_VEC_SRAL))] 1114 "TARGET_VX" 1115 "vsra\t%v0,%v1,%v2" 1116 [(set_attr "op_type" "VRR")]) 1117 1118 1119; Vector shift right arithmetic by byte 1120 1121(define_insn "vec_srab<mode>" 1122 [(set (match_operand:V_HW 0 "register_operand" "=v") 1123 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "v") 1124 (match_operand:<tointvec> 2 "register_operand" "v")] 1125 UNSPEC_VEC_SRAB))] 1126 "TARGET_VX" 1127 "vsrab\t%v0,%v1,%v2" 1128 [(set_attr "op_type" "VRR")]) 1129 1130 1131; Vector shift right logical 1132 1133(define_insn "vec_srl<VI_HW:mode><VI_HW_QHS:mode>" 1134 [(set (match_operand:VI_HW 0 "register_operand" "=v") 1135 (unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "v") 1136 (match_operand:VI_HW_QHS 2 "register_operand" "v")] 1137 UNSPEC_VEC_SRL))] 1138 "TARGET_VX" 1139 "vsrl\t%v0,%v1,%v2" 1140 [(set_attr "op_type" "VRR")]) 1141 1142 1143; Vector shift right logical by byte 1144 1145; Pattern definition in vector.md, see vec_vsrb 1146(define_expand "vec_srb<mode>" 1147 [(set (match_operand:V_HW 0 "register_operand" "") 1148 (unspec:V_HW [(match_operand:V_HW 1 "register_operand" "") 1149 (match_operand:<tointvec> 2 "register_operand" "")] 1150 UNSPEC_VEC_SRLB))] 1151 "TARGET_VX" 1152{ 1153 PUT_MODE (operands[2], V16QImode); 1154}) 1155 1156; Vector subtract 1157 1158; Vector subtract compute borrow indication 1159 1160; vscbib, vscbih, vscbif, vscbig, vscbiq 1161(define_insn "vscbi<bhfgq>_<mode>" 1162 [(set (match_operand:VIT_HW 0 "register_operand" "=v") 1163 (unspec:VIT_HW [(match_operand:VIT_HW 1 "register_operand" "v") 1164 (match_operand:VIT_HW 2 "register_operand" "v")] 1165 UNSPEC_VEC_SUBC))] 1166 "TARGET_VX" 1167 "vscbi<bhfgq>\t%v0,%v1,%v2" 1168 [(set_attr "op_type" "VRR")]) 1169 1170; Vector subtract with borrow indication 1171 1172(define_insn "vsbiq" 1173 [(set (match_operand:TI 0 "register_operand" "=v") 1174 (unspec:TI [(match_operand:TI 1 "register_operand" "v") 1175 (match_operand:TI 2 "register_operand" "v") 1176 (match_operand:TI 3 "register_operand" "v")] 1177 UNSPEC_VEC_SUBE_U128))] 1178 "TARGET_VX" 1179 "vsbiq\t%v0,%v1,%v2,%v3" 1180 [(set_attr "op_type" "VRR")]) 1181 1182 1183; Vector subtract with borrow compute and borrow indication 1184 1185(define_insn "vsbcbiq" 1186 [(set (match_operand:TI 0 "register_operand" "=v") 1187 (unspec:TI [(match_operand:TI 1 "register_operand" "v") 1188 (match_operand:TI 2 "register_operand" "v") 1189 (match_operand:TI 3 "register_operand" "v")] 1190 UNSPEC_VEC_SUBEC_U128))] 1191 "TARGET_VX" 1192 "vsbcbiq\t%v0,%v1,%v2,%v3" 1193 [(set_attr "op_type" "VRR")]) 1194 1195 1196; Vector sum across 1197 1198; Sum across DImode parts of the 1st operand and add the rightmost 1199; element of 2nd operand 1200; vsumgh, vsumgf 1201(define_expand "vec_sum2<mode>" 1202 [(set (match_operand:V2DI 0 "register_operand" "") 1203 (unspec:V2DI [(match_operand:VI_HW_HS 1 "register_operand" "") 1204 (match_operand:VI_HW_HS 2 "register_operand" "")] 1205 UNSPEC_VEC_VSUMG))] 1206 "TARGET_VX") 1207 1208; vsumqh, vsumqf 1209(define_insn "vec_sum_u128<mode>" 1210 [(set (match_operand:V2DI 0 "register_operand" "=v") 1211 (unspec:V2DI [(match_operand:VI_HW_SD 1 "register_operand" "v") 1212 (match_operand:VI_HW_SD 2 "register_operand" "v")] 1213 UNSPEC_VEC_VSUMQ))] 1214 "TARGET_VX" 1215 "vsumq<bhfgq>\t%v0,%v1,%v2" 1216 [(set_attr "op_type" "VRR")]) 1217 1218; vsumb, vsumh 1219(define_expand "vec_sum4<mode>" 1220 [(set (match_operand:V4SI 0 "register_operand" "") 1221 (unspec:V4SI [(match_operand:VI_HW_QH 1 "register_operand" "") 1222 (match_operand:VI_HW_QH 2 "register_operand" "")] 1223 UNSPEC_VEC_VSUM))] 1224 "TARGET_VX") 1225 1226 1227; Vector test under mask 1228 1229(define_expand "vec_test_mask_int<mode>" 1230 [(set (reg:CCRAW CC_REGNUM) 1231 (unspec:CCRAW [(match_operand:V_HW 1 "register_operand" "") 1232 (match_operand:<tointvec> 2 "register_operand" "")] 1233 UNSPEC_VEC_TEST_MASK)) 1234 (set (match_operand:SI 0 "register_operand" "") 1235 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1236 "TARGET_VX") 1237 1238(define_insn "*vec_test_mask<mode>" 1239 [(set (reg:CCRAW CC_REGNUM) 1240 (unspec:CCRAW [(match_operand:V_HW 0 "register_operand" "v") 1241 (match_operand:<tointvec> 1 "register_operand" "v")] 1242 UNSPEC_VEC_TEST_MASK))] 1243 "TARGET_VX" 1244 "vtm\t%v0,%v1" 1245 [(set_attr "op_type" "VRR")]) 1246 1247 1248; Vector multiply sum logical 1249 1250(define_insn "vec_msumv2di" 1251 [(set (match_operand:V16QI 0 "register_operand" "=v") 1252 (unspec:V16QI [(match_operand:V2DI 1 "register_operand" "v") 1253 (match_operand:V2DI 2 "register_operand" "v") 1254 (match_operand:V16QI 3 "register_operand" "v") 1255 (match_operand:QI 4 "const_mask_operand" "C")] 1256 UNSPEC_VEC_MSUM))] 1257 "TARGET_VXE" 1258 "vmslg\t%v0,%v1,%v2,%v3,%4" 1259 [(set_attr "op_type" "VRR")]) 1260 1261(define_insn "vmslg" 1262 [(set (match_operand:TI 0 "register_operand" "=v") 1263 (unspec:TI [(match_operand:V2DI 1 "register_operand" "v") 1264 (match_operand:V2DI 2 "register_operand" "v") 1265 (match_operand:TI 3 "register_operand" "v") 1266 (match_operand:QI 4 "const_mask_operand" "C")] 1267 UNSPEC_VEC_MSUM))] 1268 "TARGET_VXE" 1269 "vmslg\t%v0,%v1,%v2,%v3,%4" 1270 [(set_attr "op_type" "VRR")]) 1271 1272 1273; Vector find any element equal 1274 1275; vfaeb, vfaeh, vfaef 1276; vfaezb, vfaezh, vfaezf 1277(define_insn "vfae<mode>" 1278 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1279 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1280 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1281 (match_operand:QI 3 "const_mask_operand" "C")] 1282 UNSPEC_VEC_VFAE))] 1283 "TARGET_VX" 1284{ 1285 unsigned HOST_WIDE_INT flags = UINTVAL (operands[3]); 1286 1287 if (flags & VSTRING_FLAG_ZS) 1288 { 1289 flags &= ~VSTRING_FLAG_ZS; 1290 operands[3] = GEN_INT (flags); 1291 return "vfaez<bhfgq>\t%v0,%v1,%v2,%b3"; 1292 } 1293 return "vfae<bhfgq>\t%v0,%v1,%v2,%b3"; 1294} 1295[(set_attr "op_type" "VRR")]) 1296 1297; vfaebs, vfaehs, vfaefs 1298; vfaezbs, vfaezhs, vfaezfs 1299(define_insn "*vfaes<mode>" 1300 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1301 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1302 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1303 (match_operand:QI 3 "const_mask_operand" "C")] 1304 UNSPEC_VEC_VFAE)) 1305 (set (reg:CCRAW CC_REGNUM) 1306 (unspec:CCRAW [(match_dup 1) 1307 (match_dup 2) 1308 (match_dup 3)] 1309 UNSPEC_VEC_VFAECC))] 1310 "TARGET_VX" 1311{ 1312 unsigned HOST_WIDE_INT flags = UINTVAL (operands[3]); 1313 1314 if (flags & VSTRING_FLAG_ZS) 1315 { 1316 flags &= ~VSTRING_FLAG_ZS; 1317 operands[3] = GEN_INT (flags); 1318 return "vfaez<bhfgq>s\t%v0,%v1,%v2,%b3"; 1319 } 1320 return "vfae<bhfgq>s\t%v0,%v1,%v2,%b3"; 1321} 1322 [(set_attr "op_type" "VRR")]) 1323 1324(define_expand "vfaez<mode>" 1325 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1326 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1327 (match_operand:VI_HW_QHS 2 "register_operand" "") 1328 (match_operand:QI 3 "const_mask_operand" "")] 1329 UNSPEC_VEC_VFAE))] 1330 "TARGET_VX" 1331{ 1332 operands[3] = GEN_INT (INTVAL (operands[3]) | VSTRING_FLAG_ZS); 1333}) 1334 1335(define_expand "vfaes<mode>" 1336 [(parallel 1337 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1338 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1339 (match_operand:VI_HW_QHS 2 "register_operand" "") 1340 (match_operand:QI 3 "const_mask_operand" "")] 1341 UNSPEC_VEC_VFAE)) 1342 (set (reg:CCRAW CC_REGNUM) 1343 (unspec:CCRAW [(match_dup 1) 1344 (match_dup 2) 1345 (match_dup 3)] 1346 UNSPEC_VEC_VFAECC))]) 1347 (set (match_operand:SI 4 "memory_operand" "") 1348 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1349 "TARGET_VX" 1350{ 1351 operands[3] = GEN_INT (INTVAL (operands[3]) | VSTRING_FLAG_CS); 1352}) 1353 1354(define_expand "vfaezs<mode>" 1355 [(parallel 1356 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1357 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1358 (match_operand:VI_HW_QHS 2 "register_operand" "") 1359 (match_operand:SI 3 "const_mask_operand" "")] 1360 UNSPEC_VEC_VFAE)) 1361 (set (reg:CCRAW CC_REGNUM) 1362 (unspec:CCRAW [(match_dup 1) 1363 (match_dup 2) 1364 (match_dup 3)] 1365 UNSPEC_VEC_VFAECC))]) 1366 (set (match_operand:SI 4 "memory_operand" "") 1367 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1368 "TARGET_VX" 1369{ 1370 operands[3] = GEN_INT (INTVAL (operands[3]) | VSTRING_FLAG_CS | VSTRING_FLAG_ZS); 1371}) 1372 1373 1374; Vector find element equal 1375 1376; vfeebs, vfeehs, vfeefs 1377; vfeezbs, vfeezhs, vfeezfs 1378(define_insn "*vfees<mode>" 1379 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1380 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1381 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1382 (match_operand:QI 3 "const_mask_operand" "C")] 1383 UNSPEC_VEC_VFEE)) 1384 (set (reg:CCRAW CC_REGNUM) 1385 (unspec:CCRAW [(match_dup 1) 1386 (match_dup 2) 1387 (match_dup 3)] 1388 UNSPEC_VEC_VFEECC))] 1389 "TARGET_VX" 1390{ 1391 unsigned HOST_WIDE_INT flags = UINTVAL (operands[3]); 1392 1393 gcc_assert (!(flags & ~(VSTRING_FLAG_ZS | VSTRING_FLAG_CS))); 1394 flags &= ~VSTRING_FLAG_CS; 1395 1396 if (flags == VSTRING_FLAG_ZS) 1397 return "vfeez<bhfgq>s\t%v0,%v1,%v2"; 1398 return "vfee<bhfgq>s\t%v0,%v1,%v2,%b3"; 1399} 1400 [(set_attr "op_type" "VRR")]) 1401 1402; vfeeb, vfeeh, vfeef 1403(define_insn "vfee<mode>" 1404 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1405 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1406 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1407 (const_int 0)] 1408 UNSPEC_VEC_VFEE))] 1409 "TARGET_VX" 1410 "vfee<bhfgq>\t%v0,%v1,%v2,0" 1411 [(set_attr "op_type" "VRR")]) 1412 1413; vfeezb, vfeezh, vfeezf 1414(define_insn "vfeez<mode>" 1415 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1416 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1417 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1418 (const_int VSTRING_FLAG_ZS)] 1419 UNSPEC_VEC_VFEE))] 1420 "TARGET_VX" 1421 "vfeez<bhfgq>s\t%v0,%v1,%v2,2" 1422 [(set_attr "op_type" "VRR")]) 1423 1424(define_expand "vfees<mode>" 1425 [(parallel 1426 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1427 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1428 (match_operand:VI_HW_QHS 2 "register_operand" "") 1429 (const_int VSTRING_FLAG_CS)] 1430 UNSPEC_VEC_VFEE)) 1431 (set (reg:CCRAW CC_REGNUM) 1432 (unspec:CCRAW [(match_dup 1) 1433 (match_dup 2) 1434 (const_int VSTRING_FLAG_CS)] 1435 UNSPEC_VEC_VFEECC))]) 1436 (set (match_operand:SI 3 "memory_operand" "") 1437 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1438 "TARGET_VX") 1439 1440(define_expand "vfeezs<mode>" 1441 [(parallel 1442 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1443 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1444 (match_operand:VI_HW_QHS 2 "register_operand" "") 1445 (match_dup 4)] 1446 UNSPEC_VEC_VFEE)) 1447 (set (reg:CCRAW CC_REGNUM) 1448 (unspec:CCRAW [(match_dup 1) 1449 (match_dup 2) 1450 (match_dup 4)] 1451 UNSPEC_VEC_VFEECC))]) 1452 (set (match_operand:SI 3 "memory_operand" "") 1453 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1454 "TARGET_VX" 1455{ 1456 operands[4] = GEN_INT (VSTRING_FLAG_ZS | VSTRING_FLAG_CS); 1457}) 1458 1459; Vector find element not equal 1460 1461; vfeneb, vfeneh, vfenef 1462(define_insn "vfene<mode>" 1463 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1464 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1465 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1466 (const_int 0)] 1467 UNSPEC_VEC_VFENE))] 1468 "TARGET_VX" 1469 "vfene<bhfgq>\t%v0,%v1,%v2,0" 1470 [(set_attr "op_type" "VRR")]) 1471 1472; vec_vfenes can be found in vector.md since it is used for strlen 1473 1474; vfenezb, vfenezh, vfenezf 1475(define_insn "vfenez<mode>" 1476 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1477 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1478 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1479 (const_int VSTRING_FLAG_ZS)] 1480 UNSPEC_VEC_VFENE))] 1481 "TARGET_VX" 1482 "vfenez<bhfgq>\t%v0,%v1,%v2" 1483 [(set_attr "op_type" "VRR")]) 1484 1485(define_expand "vfenes<mode>" 1486 [(parallel 1487 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1488 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1489 (match_operand:VI_HW_QHS 2 "register_operand" "") 1490 (const_int VSTRING_FLAG_CS)] 1491 UNSPEC_VEC_VFENE)) 1492 (set (reg:CCRAW CC_REGNUM) 1493 (unspec:CCRAW [(match_dup 1) 1494 (match_dup 2) 1495 (const_int VSTRING_FLAG_CS)] 1496 UNSPEC_VEC_VFENECC))]) 1497 (set (match_operand:SI 3 "memory_operand" "") 1498 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1499 "TARGET_VX") 1500 1501(define_expand "vfenezs<mode>" 1502 [(parallel 1503 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1504 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1505 (match_operand:VI_HW_QHS 2 "register_operand" "") 1506 (match_dup 4)] 1507 UNSPEC_VEC_VFENE)) 1508 (set (reg:CCRAW CC_REGNUM) 1509 (unspec:CCRAW [(match_dup 1) 1510 (match_dup 2) 1511 (match_dup 4)] 1512 UNSPEC_VEC_VFENECC))]) 1513 (set (match_operand:SI 3 "memory_operand" "") 1514 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1515 "TARGET_VX" 1516{ 1517 operands[4] = GEN_INT (VSTRING_FLAG_ZS | VSTRING_FLAG_CS); 1518}) 1519 1520; Vector isolate string 1521 1522; vistrb, vistrh, vistrf 1523(define_insn "vistr<mode>" 1524 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1525 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 1526 UNSPEC_VEC_VISTR))] 1527 "TARGET_VX" 1528 "vistr<bhfgq>\t%v0,%v1" 1529 [(set_attr "op_type" "VRR")]) 1530 1531; vistrbs, vistrhs, vistrfs 1532(define_insn "*vistrs<mode>" 1533 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1534 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")] 1535 UNSPEC_VEC_VISTR)) 1536 (set (reg:CCRAW CC_REGNUM) 1537 (unspec:CCRAW [(match_dup 1)] UNSPEC_VEC_VISTRCC))] 1538 "TARGET_VX" 1539 "vistr<bhfgq>s\t%v0,%v1" 1540 [(set_attr "op_type" "VRR")]) 1541 1542(define_expand "vistrs<mode>" 1543 [(parallel 1544 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1545 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")] 1546 UNSPEC_VEC_VISTR)) 1547 (set (reg:CCRAW CC_REGNUM) 1548 (unspec:CCRAW [(match_dup 1)] 1549 UNSPEC_VEC_VISTRCC))]) 1550 (set (match_operand:SI 2 "memory_operand" "") 1551 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1552 "TARGET_VX") 1553 1554 1555; Vector compare range 1556 1557; vstrcb, vstrch, vstrcf 1558; vstrczb, vstrczh, vstrczf 1559(define_insn "vstrc<mode>" 1560 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1561 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1562 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1563 (match_operand:VI_HW_QHS 3 "register_operand" "v") 1564 (match_operand:QI 4 "const_mask_operand" "C")] 1565 UNSPEC_VEC_VSTRC))] 1566 "TARGET_VX" 1567{ 1568 unsigned HOST_WIDE_INT flags = UINTVAL (operands[4]); 1569 1570 if (flags & VSTRING_FLAG_ZS) 1571 { 1572 flags &= ~VSTRING_FLAG_ZS; 1573 operands[4] = GEN_INT (flags); 1574 return "vstrcz<bhfgq>\t%v0,%v1,%v2,%v3,%b4"; 1575 } 1576 return "vstrc<bhfgq>\t%v0,%v1,%v2,%v3,%b4"; 1577} 1578[(set_attr "op_type" "VRR")]) 1579 1580; vstrcbs, vstrchs, vstrcfs 1581; vstrczbs, vstrczhs, vstrczfs 1582(define_insn "*vstrcs<mode>" 1583 [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v") 1584 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1585 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1586 (match_operand:VI_HW_QHS 3 "register_operand" "v") 1587 (match_operand:QI 4 "const_mask_operand" "C")] 1588 UNSPEC_VEC_VSTRC)) 1589 (set (reg:CCRAW CC_REGNUM) 1590 (unspec:CCRAW [(match_dup 1) 1591 (match_dup 2) 1592 (match_dup 3) 1593 (match_dup 4)] 1594 UNSPEC_VEC_VSTRCCC))] 1595 "TARGET_VX" 1596{ 1597 unsigned HOST_WIDE_INT flags = UINTVAL (operands[4]); 1598 1599 if (flags & VSTRING_FLAG_ZS) 1600 { 1601 flags &= ~VSTRING_FLAG_ZS; 1602 operands[4] = GEN_INT (flags); 1603 return "vstrcz<bhfgq>s\t%v0,%v1,%v2,%v3,%b4"; 1604 } 1605 return "vstrc<bhfgq>s\t%v0,%v1,%v2,%v3,%b4"; 1606} 1607 [(set_attr "op_type" "VRR")]) 1608 1609(define_expand "vstrcz<mode>" 1610 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1611 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1612 (match_operand:VI_HW_QHS 2 "register_operand" "") 1613 (match_operand:VI_HW_QHS 3 "register_operand" "") 1614 (match_operand:QI 4 "const_mask_operand" "")] 1615 UNSPEC_VEC_VSTRC))] 1616 "TARGET_VX" 1617{ 1618 operands[4] = GEN_INT (INTVAL (operands[4]) | VSTRING_FLAG_ZS); 1619}) 1620 1621(define_expand "vstrcs<mode>" 1622 [(parallel 1623 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1624 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1625 (match_operand:VI_HW_QHS 2 "register_operand" "") 1626 (match_operand:VI_HW_QHS 3 "register_operand" "") 1627 (match_operand:QI 4 "const_mask_operand" "")] 1628 UNSPEC_VEC_VSTRC)) 1629 (set (reg:CCRAW CC_REGNUM) 1630 (unspec:CCRAW [(match_dup 1) 1631 (match_dup 2) 1632 (match_dup 3) 1633 (match_dup 4)] 1634 UNSPEC_VEC_VSTRCCC))]) 1635 (set (match_operand:SI 5 "memory_operand" "") 1636 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1637 "TARGET_VX" 1638{ 1639 operands[4] = GEN_INT (INTVAL (operands[4]) | VSTRING_FLAG_CS); 1640}) 1641 1642(define_expand "vstrczs<mode>" 1643 [(parallel 1644 [(set (match_operand:VI_HW_QHS 0 "register_operand" "") 1645 (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "") 1646 (match_operand:VI_HW_QHS 2 "register_operand" "") 1647 (match_operand:VI_HW_QHS 3 "register_operand" "") 1648 (match_operand:QI 4 "const_mask_operand" "")] 1649 UNSPEC_VEC_VSTRC)) 1650 (set (reg:CCRAW CC_REGNUM) 1651 (unspec:CCRAW [(match_dup 1) 1652 (match_dup 2) 1653 (match_dup 3) 1654 (match_dup 4)] 1655 UNSPEC_VEC_VSTRCCC))]) 1656 (set (match_operand:SI 5 "memory_operand" "") 1657 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1658 "TARGET_VX" 1659{ 1660 operands[4] = GEN_INT (INTVAL (operands[4]) | VSTRING_FLAG_CS | VSTRING_FLAG_ZS); 1661}) 1662 1663; Vector string search 1664 1665(define_expand "vstrs<mode>" 1666 [(parallel 1667 [(set (match_operand:V16QI 0 "register_operand" "") 1668 (unspec:V16QI [(match_operand:VI_HW_QHS 1 "register_operand" "") 1669 (match_operand:VI_HW_QHS 2 "register_operand" "") 1670 (match_operand:V16QI 3 "register_operand" "") 1671 (const_int 0)] 1672 UNSPEC_VEC_VSTRS)) 1673 (set (reg:CCRAW CC_REGNUM) 1674 (unspec:CCRAW [(match_dup 1) 1675 (match_dup 2) 1676 (match_dup 3) 1677 (const_int 0)] 1678 UNSPEC_VEC_VSTRSCC))]) 1679 (set (match_operand:SI 4 "memory_operand" "") 1680 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1681 "TARGET_VXE2") 1682 1683(define_expand "vstrsz<mode>" 1684 [(parallel 1685 [(set (match_operand:V16QI 0 "register_operand" "") 1686 (unspec:V16QI [(match_operand:VI_HW_QHS 1 "register_operand" "") 1687 (match_operand:VI_HW_QHS 2 "register_operand" "") 1688 (match_operand:V16QI 3 "register_operand" "") 1689 (const_int VSTRING_FLAG_ZS)] 1690 UNSPEC_VEC_VSTRS)) 1691 (set (reg:CCRAW CC_REGNUM) 1692 (unspec:CCRAW [(match_dup 1) 1693 (match_dup 2) 1694 (match_dup 3) 1695 (const_int VSTRING_FLAG_ZS)] 1696 UNSPEC_VEC_VSTRSCC))]) 1697 (set (match_operand:SI 4 "memory_operand" "") 1698 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1699 "TARGET_VXE2") 1700 1701; vstrsb, vstrsh, vstrsf 1702; vstrszb, vstrszh, vstrszf 1703(define_insn "vec_vstrs<mode>" 1704 [(set (match_operand:V16QI 0 "register_operand" "=v") 1705 (unspec:V16QI [(match_operand:VI_HW_QHS 1 "register_operand" "v") 1706 (match_operand:VI_HW_QHS 2 "register_operand" "v") 1707 (match_operand:V16QI 3 "register_operand" "v") 1708 (match_operand:QI 4 "const_mask_operand" "C")] 1709 UNSPEC_VEC_VSTRS)) 1710 (set (reg:CCRAW CC_REGNUM) 1711 (unspec:CCRAW [(match_dup 1) 1712 (match_dup 2) 1713 (match_dup 3) 1714 (match_dup 4)] 1715 UNSPEC_VEC_VSTRSCC))] 1716 "TARGET_VXE2" 1717{ 1718 unsigned HOST_WIDE_INT flags = UINTVAL (operands[4]); 1719 1720 gcc_assert (!(flags & ~VSTRING_FLAG_ZS)); 1721 1722 if (flags == VSTRING_FLAG_ZS) 1723 return "vstrsz<bhfgq>\t%v0,%v1,%v2,%v3"; 1724 return "vstrs<bhfgq>\t%v0,%v1,%v2,%v3"; 1725} 1726 [(set_attr "op_type" "VRR")]) 1727 1728 1729; Vector convert int<->float 1730 1731(define_insn "vcdgb" 1732 [(set (match_operand:V2DF 0 "register_operand" "=v") 1733 (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "v") 1734 (match_operand:QI 2 "const_mask_operand" "C") ; inexact suppression 1735 (match_operand:QI 3 "const_mask_operand" "C")] ; rounding mode 1736 UNSPEC_VEC_VCDGB))] 1737 "TARGET_VX && UINTVAL (operands[3]) != 2 && UINTVAL (operands[3]) <= 7" 1738 "vcdgb\t%v0,%v1,%b2,%b3" 1739 [(set_attr "op_type" "VRR")]) 1740 1741 1742; The result needs to be multiplied with 2**-op2 1743(define_expand "vec_ctd_s64" 1744 [(set (match_operand:V2DF 0 "register_operand" "") 1745 (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "") 1746 (const_int VEC_NOINEXACT) 1747 (const_int VEC_RND_CURRENT)] 1748 UNSPEC_VEC_VCDGB)) 1749 (use (match_operand:QI 2 "const_int_operand" "")) 1750 (set (match_dup 0) (mult:V2DF (match_dup 0) (match_dup 3)))] 1751 "TARGET_VX" 1752{ 1753 REAL_VALUE_TYPE f; 1754 rtx c; 1755 1756 real_2expN (&f, -INTVAL (operands[2]), DFmode); 1757 c = const_double_from_real_value (f, DFmode); 1758 1759 operands[3] = gen_const_vec_duplicate (V2DFmode, c); 1760 operands[3] = force_reg (V2DFmode, operands[3]); 1761}) 1762 1763(define_insn "vcdlgb" 1764 [(set (match_operand:V2DF 0 "register_operand" "=v") 1765 (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "v") 1766 (match_operand:QI 2 "const_mask_operand" "C") ; inexact suppression 1767 (match_operand:QI 3 "const_mask_operand" "C")] ; rounding mode 1768 UNSPEC_VEC_VCDLGB))] 1769 "TARGET_VX && UINTVAL (operands[3]) != 2 && UINTVAL (operands[3]) <= 7" 1770 "vcdlgb\t%v0,%v1,%b2,%b3" 1771 [(set_attr "op_type" "VRR")]) 1772 1773; The result needs to be multiplied with 2**-op2 1774(define_expand "vec_ctd_u64" 1775 [(set (match_operand:V2DF 0 "register_operand" "") 1776 (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "") 1777 (const_int VEC_NOINEXACT) 1778 (const_int VEC_RND_CURRENT)] 1779 UNSPEC_VEC_VCDLGB)) 1780 (use (match_operand:QI 2 "const_int_operand" "")) 1781 (set (match_dup 0) (mult:V2DF (match_dup 0) (match_dup 3)))] 1782 "TARGET_VX" 1783{ 1784 REAL_VALUE_TYPE f; 1785 rtx c; 1786 1787 real_2expN (&f, -INTVAL (operands[2]), DFmode); 1788 c = const_double_from_real_value (f, DFmode); 1789 1790 operands[3] = gen_const_vec_duplicate (V2DFmode, c); 1791 operands[3] = force_reg (V2DFmode, operands[3]); 1792}) 1793 1794(define_insn "vcgdb" 1795 [(set (match_operand:V2DI 0 "register_operand" "=v") 1796 (unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v") 1797 (match_operand:QI 2 "const_mask_operand" "C") 1798 (match_operand:QI 3 "const_mask_operand" "C")] 1799 UNSPEC_VEC_VCGDB))] 1800 "TARGET_VX && UINTVAL (operands[3]) != 2 && UINTVAL (operands[3]) <= 7" 1801 "vcgdb\t%v0,%v1,%b2,%b3" 1802 [(set_attr "op_type" "VRR")]) 1803 1804; The input needs to be multiplied with 2**op2 1805(define_expand "vec_ctsl" 1806 [(use (match_operand:QI 2 "const_int_operand" "")) 1807 (set (match_dup 4) (mult:V2DF (match_operand:V2DF 1 "register_operand" "") 1808 (match_dup 3))) 1809 (set (match_operand:V2DI 0 "register_operand" "") 1810 (unspec:V2DI [(match_dup 4) 1811 (const_int VEC_NOINEXACT) 1812 (const_int VEC_RND_CURRENT)] 1813 UNSPEC_VEC_VCGDB))] 1814 "TARGET_VX" 1815{ 1816 REAL_VALUE_TYPE f; 1817 rtx c; 1818 1819 real_2expN (&f, INTVAL (operands[2]), DFmode); 1820 c = const_double_from_real_value (f, DFmode); 1821 1822 operands[3] = gen_const_vec_duplicate (V2DFmode, c); 1823 operands[3] = force_reg (V2DFmode, operands[3]); 1824 operands[4] = gen_reg_rtx (V2DFmode); 1825}) 1826 1827(define_insn "vclgdb" 1828 [(set (match_operand:V2DI 0 "register_operand" "=v") 1829 (unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v") 1830 (match_operand:QI 2 "const_mask_operand" "C") 1831 (match_operand:QI 3 "const_mask_operand" "C")] 1832 UNSPEC_VEC_VCLGDB))] 1833 "TARGET_VX && UINTVAL (operands[3]) != 2 && UINTVAL (operands[3]) <= 7" 1834 "vclgdb\t%v0,%v1,%b2,%b3" 1835 [(set_attr "op_type" "VRR")]) 1836 1837; The input needs to be multiplied with 2**op2 1838(define_expand "vec_ctul" 1839 [(use (match_operand:QI 2 "const_int_operand" "")) 1840 (set (match_dup 4) (mult:V2DF (match_operand:V2DF 1 "register_operand" "") 1841 (match_dup 3))) 1842 (set (match_operand:V2DI 0 "register_operand" "") 1843 (unspec:V2DI [(match_dup 4) 1844 (const_int VEC_NOINEXACT) 1845 (const_int VEC_RND_CURRENT)] 1846 UNSPEC_VEC_VCLGDB))] 1847 "TARGET_VX" 1848{ 1849 REAL_VALUE_TYPE f; 1850 rtx c; 1851 1852 real_2expN (&f, INTVAL (operands[2]), DFmode); 1853 c = const_double_from_real_value (f, DFmode); 1854 1855 operands[3] = gen_const_vec_duplicate (V2DFmode, c); 1856 operands[3] = force_reg (V2DFmode, operands[3]); 1857 operands[4] = gen_reg_rtx (V2DFmode); 1858}) 1859 1860; Vector load fp integer - IEEE inexact exception is suppressed 1861; vfisb, vfidb, wfisb, wfidb, wfixb 1862(define_insn "vec_fpint<mode>" 1863 [(set (match_operand:VFT 0 "register_operand" "=v") 1864 (unspec:VFT [(match_operand:VFT 1 "register_operand" "v") 1865 (match_operand:QI 2 "const_mask_operand" "C") ; inexact suppression control 1866 (match_operand:QI 3 "const_mask_operand" "C")] ; rounding mode 1867 UNSPEC_VEC_VFI))] 1868 "TARGET_VX" 1869 "<vw>fi<sdx>b\t%v0,%v1,%b2,%b3" 1870 [(set_attr "op_type" "VRR")]) 1871 1872 1873; Vector load lengthened - V4SF -> V2DF 1874 1875(define_insn "vflls" 1876 [(set (match_operand:V2DF 0 "register_operand" "=v") 1877 (unspec:V2DF [(match_operand:V4SF 1 "register_operand" "v")] 1878 UNSPEC_VEC_VFLL))] 1879 "TARGET_VX" 1880 "vldeb\t%v0,%v1" 1881 [(set_attr "op_type" "VRR")]) 1882 1883(define_expand "vec_ld2f" 1884 [; Initialize a vector to all zeroes. FIXME: This should not be 1885 ; necessary since all elements of the vector will be set anyway. 1886 ; This is just to make it explicit to the data flow framework. 1887 (set (match_dup 2) (match_dup 3)) 1888 (set (match_dup 2) (unspec:V4SF [(match_operand:SF 1 "memory_operand" "") 1889 (const_int 0) 1890 (match_dup 2)] 1891 UNSPEC_VEC_SET)) 1892 (set (match_dup 2) (unspec:V4SF [(match_dup 4) 1893 (const_int 2) 1894 (match_dup 2)] 1895 UNSPEC_VEC_SET)) 1896 (set (match_operand:V2DF 0 "register_operand" "") 1897 (unspec:V2DF [(match_dup 2)] UNSPEC_VEC_VFLL))] 1898 "TARGET_VX" 1899{ 1900 operands[2] = gen_reg_rtx (V4SFmode); 1901 operands[3] = CONST0_RTX (V4SFmode); 1902 operands[4] = adjust_address (operands[1], SFmode, 4); 1903}) 1904 1905 1906; Vector load rounded - V2DF -> V4SF 1907 1908(define_insn "vflrd" 1909 [(set (match_operand:V4SF 0 "register_operand" "=v") 1910 (unspec:V4SF [(match_operand:V2DF 1 "register_operand" "v") 1911 (match_operand:QI 2 "const_mask_operand" "C") 1912 (match_operand:QI 3 "const_mask_operand" "C")] 1913 UNSPEC_VEC_VFLR))] 1914 "TARGET_VX" 1915 "vledb\t%v0,%v1,%b2,%b3" 1916 [(set_attr "op_type" "VRR")]) 1917 1918(define_expand "vec_st2f" 1919 [(set (match_dup 2) 1920 (unspec:V4SF [(match_operand:V2DF 0 "register_operand" "") 1921 (const_int VEC_INEXACT) 1922 (const_int VEC_RND_CURRENT)] 1923 UNSPEC_VEC_VFLR)) 1924 (set (match_operand:SF 1 "memory_operand" "") 1925 (unspec:SF [(match_dup 2) (const_int 0)] UNSPEC_VEC_EXTRACT)) 1926 (set (match_dup 3) 1927 (unspec:SF [(match_dup 2) (const_int 2)] UNSPEC_VEC_EXTRACT))] 1928 "TARGET_VX" 1929{ 1930 operands[2] = gen_reg_rtx (V4SFmode); 1931 operands[3] = adjust_address (operands[1], SFmode, 4); 1932}) 1933 1934 1935; Vector square root fp vec_sqrt -> sqrt rtx standard name 1936 1937;; Vector FP test data class immediate 1938 1939; vec_all_nan, vec_all_numeric, vec_any_nan, vec_any_numeric 1940; These ignore the vector result and only want CC stored to an int 1941; pointer. 1942 1943; vftcisb, vftcidb 1944(define_insn "*vftci<mode>_cconly" 1945 [(set (reg:CCRAW CC_REGNUM) 1946 (unspec:CCRAW [(match_operand:VECF_HW 1 "register_operand") 1947 (match_operand:HI 2 "const_int_operand")] 1948 UNSPEC_VEC_VFTCICC)) 1949 (clobber (match_scratch:<tointvec> 0))] 1950 "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")" 1951 "vftci<sdx>b\t%v0,%v1,%x2" 1952 [(set_attr "op_type" "VRR")]) 1953 1954(define_expand "vftci<mode>_intcconly" 1955 [(parallel 1956 [(set (reg:CCRAW CC_REGNUM) 1957 (unspec:CCRAW [(match_operand:VECF_HW 0 "register_operand") 1958 (match_operand:HI 1 "const_int_operand")] 1959 UNSPEC_VEC_VFTCICC)) 1960 (clobber (scratch:<tointvec>))]) 1961 (set (match_operand:SI 2 "register_operand" "") 1962 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1963 "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[1]), 'J', \"J\")") 1964 1965; vec_fp_test_data_class wants the result vector and the CC stored to 1966; an int pointer. 1967 1968; vftcisb, vftcidb 1969(define_insn "*vftci<mode>" 1970 [(set (match_operand:VECF_HW 0 "register_operand" "=v") 1971 (unspec:VECF_HW [(match_operand:VECF_HW 1 "register_operand" "v") 1972 (match_operand:HI 2 "const_int_operand" "J")] 1973 UNSPEC_VEC_VFTCI)) 1974 (set (reg:CCRAW CC_REGNUM) 1975 (unspec:CCRAW [(match_dup 1) (match_dup 2)] UNSPEC_VEC_VFTCICC))] 1976 "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")" 1977 "vftci<sdx>b\t%v0,%v1,%x2" 1978 [(set_attr "op_type" "VRR")]) 1979 1980(define_expand "vftci<mode>_intcc" 1981 [(parallel 1982 [(set (match_operand:VECF_HW 0 "register_operand") 1983 (unspec:VECF_HW [(match_operand:VECF_HW 1 "register_operand") 1984 (match_operand:HI 2 "const_int_operand")] 1985 UNSPEC_VEC_VFTCI)) 1986 (set (reg:CCRAW CC_REGNUM) 1987 (unspec:CCRAW [(match_dup 1) (match_dup 2)] UNSPEC_VEC_VFTCICC))]) 1988 (set (match_operand:SI 3 "memory_operand" "") 1989 (unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))] 1990 "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")") 1991 1992;; 1993;; Integer compares 1994;; 1995 1996; All comparisons which produce a CC need fully populated (VI_HW) 1997; vector arguments. Otherwise the any/all CCs would be just bogus. 1998 1999(define_insn "*vec_cmp<VICMP:insn_cmp><VI_HW:mode>_cconly" 2000 [(set (reg:VICMP CC_REGNUM) 2001 (compare:VICMP (match_operand:VI_HW 0 "register_operand" "v") 2002 (match_operand:VI_HW 1 "register_operand" "v"))) 2003 (clobber (match_scratch:VI_HW 2 "=v"))] 2004 "TARGET_VX" 2005 "vc<VICMP:insn_cmp><VI_HW:bhfgq>s\t%v2,%v0,%v1" 2006 [(set_attr "op_type" "VRR")]) 2007 2008; FIXME: The following 2x3 definitions should be merged into 2 with 2009; VICMP like above but I could not find a way to set the comparison 2010; operator (eq) depending on the mode CCVEQ (mode_iterator). Or the 2011; other way around - setting the mode depending on the code 2012; (code_iterator). 2013(define_expand "vec_cmpeq<VI_HW:mode>_cc" 2014 [(parallel 2015 [(set (reg:CCVEQ CC_REGNUM) 2016 (compare:CCVEQ (match_operand:VI_HW 1 "register_operand" "v") 2017 (match_operand:VI_HW 2 "register_operand" "v"))) 2018 (set (match_operand:VI_HW 0 "register_operand" "=v") 2019 (eq:VI_HW (match_dup 1) (match_dup 2)))]) 2020 (set (match_operand:SI 3 "memory_operand" "") 2021 (unspec:SI [(reg:CCVEQ CC_REGNUM)] UNSPEC_CC_TO_INT))] 2022 "TARGET_VX") 2023 2024(define_expand "vec_cmph<VI_HW:mode>_cc" 2025 [(parallel 2026 [(set (reg:CCVIH CC_REGNUM) 2027 (compare:CCVIH (match_operand:VI_HW 1 "register_operand" "v") 2028 (match_operand:VI_HW 2 "register_operand" "v"))) 2029 (set (match_operand:VI_HW 0 "register_operand" "=v") 2030 (gt:VI_HW (match_dup 1) (match_dup 2)))]) 2031 (set (match_operand:SI 3 "memory_operand" "") 2032 (unspec:SI [(reg:CCVIH CC_REGNUM)] UNSPEC_CC_TO_INT))] 2033 "TARGET_VX") 2034 2035(define_expand "vec_cmphl<VI_HW:mode>_cc" 2036 [(parallel 2037 [(set (reg:CCVIHU CC_REGNUM) 2038 (compare:CCVIHU (match_operand:VI_HW 1 "register_operand" "v") 2039 (match_operand:VI_HW 2 "register_operand" "v"))) 2040 (set (match_operand:VI_HW 0 "register_operand" "=v") 2041 (gtu:VI_HW (match_dup 1) (match_dup 2)))]) 2042 (set (match_operand:SI 3 "memory_operand" "") 2043 (unspec:SI [(reg:CCVIHU CC_REGNUM)] UNSPEC_CC_TO_INT))] 2044 "TARGET_VX") 2045 2046 2047(define_insn "*vec_cmpeq<VI_HW:mode>_cc" 2048 [(set (reg:CCVEQ CC_REGNUM) 2049 (compare:CCVEQ (match_operand:VI_HW 0 "register_operand" "v") 2050 (match_operand:VI_HW 1 "register_operand" "v"))) 2051 (set (match_operand:VI_HW 2 "register_operand" "=v") 2052 (eq:VI_HW (match_dup 0) (match_dup 1)))] 2053 "TARGET_VX" 2054 "vceq<VI_HW:bhfgq>s\t%v2,%v0,%v1" 2055 [(set_attr "op_type" "VRR")]) 2056 2057(define_insn "*vec_cmph<VI_HW:mode>_cc" 2058 [(set (reg:CCVIH CC_REGNUM) 2059 (compare:CCVIH (match_operand:VI_HW 0 "register_operand" "v") 2060 (match_operand:VI_HW 1 "register_operand" "v"))) 2061 (set (match_operand:VI_HW 2 "register_operand" "=v") 2062 (gt:VI_HW (match_dup 0) (match_dup 1)))] 2063 "TARGET_VX" 2064 "vch<VI_HW:bhfgq>s\t%v2,%v0,%v1" 2065 [(set_attr "op_type" "VRR")]) 2066 2067(define_insn "*vec_cmphl<VI_HW:mode>_cc" 2068 [(set (reg:CCVIHU CC_REGNUM) 2069 (compare:CCVIHU (match_operand:VI_HW 0 "register_operand" "v") 2070 (match_operand:VI_HW 1 "register_operand" "v"))) 2071 (set (match_operand:VI_HW 2 "register_operand" "=v") 2072 (gtu:VI_HW (match_dup 0) (match_dup 1)))] 2073 "TARGET_VX" 2074 "vchl<VI_HW:bhfgq>s\t%v2,%v0,%v1" 2075 [(set_attr "op_type" "VRR")]) 2076 2077;; 2078;; Floating point compares 2079;; 2080 2081; vfcesbs, vfcedbs, wfcexbs, vfchsbs, vfchdbs, wfchxbs, vfchesbs, vfchedbs, wfchexbs 2082(define_insn "*vec_cmp<insn_cmp><VF_HW:mode>_cconly" 2083 [(set (reg:VFCMP CC_REGNUM) 2084 (compare:VFCMP (match_operand:VF_HW 0 "register_operand" "v") 2085 (match_operand:VF_HW 1 "register_operand" "v"))) 2086 (clobber (match_scratch:<tointvec> 2 "=v"))] 2087 "TARGET_VX" 2088 "<vw>fc<asm_fcmp><sdx>bs\t%v2,%v0,%v1" 2089 [(set_attr "op_type" "VRR")]) 2090 2091; FIXME: Merge the following 2x3 patterns with VFCMP 2092(define_expand "vec_cmpeq<mode>_cc" 2093 [(parallel 2094 [(set (reg:CCVEQ CC_REGNUM) 2095 (compare:CCVEQ (match_operand:VF_HW 1 "register_operand" "v") 2096 (match_operand:VF_HW 2 "register_operand" "v"))) 2097 (set (match_operand:<tointvec> 0 "register_operand" "=v") 2098 (eq:<tointvec> (match_dup 1) (match_dup 2)))]) 2099 (set (match_operand:SI 3 "memory_operand" "") 2100 (unspec:SI [(reg:CCVEQ CC_REGNUM)] UNSPEC_CC_TO_INT))] 2101 "TARGET_VX") 2102 2103(define_expand "vec_cmph<mode>_cc" 2104 [(parallel 2105 [(set (reg:CCVFH CC_REGNUM) 2106 (compare:CCVFH (match_operand:VF_HW 1 "register_operand" "v") 2107 (match_operand:VF_HW 2 "register_operand" "v"))) 2108 (set (match_operand:<tointvec> 0 "register_operand" "=v") 2109 (gt:<tointvec> (match_dup 1) (match_dup 2)))]) 2110 (set (match_operand:SI 3 "memory_operand" "") 2111 (unspec:SI [(reg:CCVIH CC_REGNUM)] UNSPEC_CC_TO_INT))] 2112 "TARGET_VX") 2113 2114(define_expand "vec_cmphe<mode>_cc" 2115 [(parallel 2116 [(set (reg:CCVFHE CC_REGNUM) 2117 (compare:CCVFHE (match_operand:VF_HW 1 "register_operand" "v") 2118 (match_operand:VF_HW 2 "register_operand" "v"))) 2119 (set (match_operand:<tointvec> 0 "register_operand" "=v") 2120 (ge:<tointvec> (match_dup 1) (match_dup 2)))]) 2121 (set (match_operand:SI 3 "memory_operand" "") 2122 (unspec:SI [(reg:CCVFHE CC_REGNUM)] UNSPEC_CC_TO_INT))] 2123 "TARGET_VX") 2124 2125; These 3 cannot be merged as the insn defintion above since it also 2126; requires to rewrite the RTL equality operator that the same time as 2127; the CC mode. 2128 2129; vfcesbs, vfcedbs, wfcexbs 2130(define_insn "*vec_cmpeq<mode>_cc" 2131 [(set (reg:CCVEQ CC_REGNUM) 2132 (compare:CCVEQ (match_operand:VF_HW 0 "register_operand" "v") 2133 (match_operand:VF_HW 1 "register_operand" "v"))) 2134 (set (match_operand:<tointvec> 2 "register_operand" "=v") 2135 (eq:<tointvec> (match_dup 0) (match_dup 1)))] 2136 "TARGET_VX" 2137 "<vw>fce<sdx>bs\t%v2,%v0,%v1" 2138 [(set_attr "op_type" "VRR")]) 2139 2140; vfchsbs, vfchdbs, wfchxbs 2141(define_insn "*vec_cmph<mode>_cc" 2142 [(set (reg:CCVFH CC_REGNUM) 2143 (compare:CCVFH (match_operand:VF_HW 0 "register_operand" "v") 2144 (match_operand:VF_HW 1 "register_operand" "v"))) 2145 (set (match_operand:<tointvec> 2 "register_operand" "=v") 2146 (gt:<tointvec> (match_dup 0) (match_dup 1)))] 2147 "TARGET_VX" 2148 "<vw>fch<sdx>bs\t%v2,%v0,%v1" 2149 [(set_attr "op_type" "VRR")]) 2150 2151; vfchesbs, vfchedbs, wfchexbs 2152(define_insn "*vec_cmphe<mode>_cc" 2153 [(set (reg:CCVFHE CC_REGNUM) 2154 (compare:CCVFHE (match_operand:VF_HW 0 "register_operand" "v") 2155 (match_operand:VF_HW 1 "register_operand" "v"))) 2156 (set (match_operand:<tointvec> 2 "register_operand" "=v") 2157 (ge:<tointvec> (match_dup 0) (match_dup 1)))] 2158 "TARGET_VX" 2159 "<vw>fche<sdx>bs\t%v2,%v0,%v1" 2160 [(set_attr "op_type" "VRR")]) 2161 2162 2163(define_insn "vfmin<mode>" 2164 [(set (match_operand:VF_HW 0 "register_operand" "=v") 2165 (unspec:VF_HW [(match_operand:VF_HW 1 "register_operand" "v") 2166 (match_operand:VF_HW 2 "register_operand" "v") 2167 (match_operand:QI 3 "const_mask_operand" "C")] 2168 UNSPEC_VEC_VFMIN))] 2169 "TARGET_VXE" 2170 "<vw>fmin<sdx>b\t%v0,%v1,%v2,%b3" 2171 [(set_attr "op_type" "VRR")]) 2172 2173(define_insn "vfmax<mode>" 2174 [(set (match_operand:VF_HW 0 "register_operand" "=v") 2175 (unspec:VF_HW [(match_operand:VF_HW 1 "register_operand" "v") 2176 (match_operand:VF_HW 2 "register_operand" "v") 2177 (match_operand:QI 3 "const_mask_operand" "C")] 2178 UNSPEC_VEC_VFMAX))] 2179 "TARGET_VXE" 2180 "<vw>fmax<sdx>b\t%v0,%v1,%v2,%b3" 2181 [(set_attr "op_type" "VRR")]) 2182 2183; The element reversal builtins introduced with z15 have been made 2184; available also for older CPUs down to z13. 2185(define_expand "eltswap<mode>" 2186 [(set (match_operand:VEC_HW 0 "nonimmediate_operand" "") 2187 (unspec:VEC_HW [(match_operand:VEC_HW 1 "nonimmediate_operand" "")] 2188 UNSPEC_VEC_ELTSWAP))] 2189 "TARGET_VX") 2190 2191; The byte element reversal is implemented as 128 bit byte swap. 2192; Alternatively this could be emitted as bswap:V1TI but the required 2193; subregs appear to confuse combine. 2194(define_insn "*eltswapv16qi" 2195 [(set (match_operand:V16QI 0 "nonimmediate_operand" "=v,v,R") 2196 (unspec:V16QI [(match_operand:V16QI 1 "nonimmediate_operand" "v,R,v")] 2197 UNSPEC_VEC_ELTSWAP))] 2198 "TARGET_VXE2" 2199 "@ 2200 # 2201 vlbrq\t%v0,%v1 2202 vstbrq\t%v1,%v0" 2203 [(set_attr "op_type" "*,VRX,VRX")]) 2204 2205; vlerh, vlerf, vlerg, vsterh, vsterf, vsterg 2206(define_insn "*eltswap<mode>" 2207 [(set (match_operand:V_HW_HSD 0 "nonimmediate_operand" "=v,v,R") 2208 (unspec:V_HW_HSD [(match_operand:V_HW_HSD 1 "nonimmediate_operand" "v,R,v")] 2209 UNSPEC_VEC_ELTSWAP))] 2210 "TARGET_VXE2" 2211 "@ 2212 # 2213 vler<bhfgq>\t%v0,%v1 2214 vster<bhfgq>\t%v1,%v0" 2215 [(set_attr "op_type" "*,VRX,VRX")]) 2216 2217; z15 has instructions for doing element reversal from mem to reg 2218; or the other way around. For reg to reg or on pre z15 machines 2219; we have to emulate it with vector permute. 2220(define_insn_and_split "*eltswap<mode>_emu" 2221 [(set (match_operand:VEC_HW 0 "nonimmediate_operand" "=vR") 2222 (unspec:VEC_HW [(match_operand:VEC_HW 1 "nonimmediate_operand" "vR")] 2223 UNSPEC_VEC_ELTSWAP))] 2224 "TARGET_VX && can_create_pseudo_p ()" 2225 "#" 2226 "&& ((!memory_operand (operands[0], <MODE>mode) 2227 && !memory_operand (operands[1], <MODE>mode)) 2228 || !TARGET_VXE2)" 2229 [(set (match_dup 3) 2230 (unspec:V16QI [(match_dup 4) 2231 (match_dup 4) 2232 (match_dup 2)] 2233 UNSPEC_VEC_PERM)) 2234 (set (match_dup 0) (subreg:VEC_HW (match_dup 3) 0))] 2235{ 2236 static char p[4][16] = 2237 { { 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0 }, /* Q */ 2238 { 14, 15, 12, 13, 10, 11, 8, 9, 6, 7, 4, 5, 2, 3, 0, 1 }, /* H */ 2239 { 12, 13, 14, 15, 8, 9, 10, 11, 4, 5, 6, 7, 0, 1, 2, 3 }, /* S */ 2240 { 8, 9, 10, 11, 12, 13, 14, 15, 0, 1, 2, 3, 4, 5, 6, 7 } }; /* D */ 2241 char *perm; 2242 rtx perm_rtx[16], constv; 2243 2244 switch (GET_MODE_SIZE (GET_MODE_INNER (<MODE>mode))) 2245 { 2246 case 1: perm = p[0]; break; 2247 case 2: perm = p[1]; break; 2248 case 4: perm = p[2]; break; 2249 case 8: perm = p[3]; break; 2250 default: gcc_unreachable (); 2251 } 2252 2253 for (int i = 0; i < 16; i++) 2254 perm_rtx[i] = GEN_INT (perm[i]); 2255 2256 operands[1] = force_reg (<MODE>mode, operands[1]); 2257 operands[2] = gen_reg_rtx (V16QImode); 2258 operands[3] = gen_reg_rtx (V16QImode); 2259 operands[4] = simplify_gen_subreg (V16QImode, operands[1], <MODE>mode, 0); 2260 constv = force_const_mem (V16QImode, gen_rtx_CONST_VECTOR (V16QImode, gen_rtvec_v (16, perm_rtx))); 2261 emit_move_insn (operands[2], constv); 2262}) 2263 2264; vec_insert (__builtin_bswap32 (*a), b, 1) set-element-bswap-2.c 2265; b[1] = __builtin_bswap32 (*a) set-element-bswap-3.c 2266; vlebrh, vlebrf, vlebrg 2267(define_insn "*vec_set_bswap_elem<mode>" 2268 [(set (match_operand:V_HW_HSD 0 "register_operand" "=v") 2269 (unspec:V_HW_HSD [(bswap:<non_vec> (match_operand:<non_vec> 1 "memory_operand" "R")) 2270 (match_operand:SI 2 "const_int_operand" "C") 2271 (match_operand:V_HW_HSD 3 "register_operand" "0")] 2272 UNSPEC_VEC_SET))] 2273 "TARGET_VXE2 && UINTVAL (operands[2]) < GET_MODE_NUNITS (<V_HW_HSD:MODE>mode)" 2274 "vlebr<bhfgq>\t%v0,%1,%2" 2275 [(set_attr "op_type" "VRX")]) 2276 2277; vec_revb (vec_insert (*a, vec_revb (b), 1)) set-element-bswap-1.c 2278; vlebrh, vlebrf, vlebrg 2279(define_insn "*vec_set_bswap_vec<mode>" 2280 [(set (match_operand:V_HW_HSD 0 "register_operand" "=v") 2281 (bswap:V_HW_HSD 2282 (unspec:V_HW_HSD [(match_operand:<non_vec> 1 "memory_operand" "R") 2283 (match_operand:SI 2 "const_int_operand" "C") 2284 (bswap:V_HW_HSD (match_operand:V_HW_HSD 3 "register_operand" "0"))] 2285 UNSPEC_VEC_SET))) 2286 (use (match_operand:V16QI 4 "permute_pattern_operand" "X"))] 2287 "TARGET_VXE2 && UINTVAL (operands[2]) < GET_MODE_NUNITS (<V_HW_HSD:MODE>mode)" 2288 "vlebr<bhfgq>\t%v0,%1,%2" 2289 [(set_attr "op_type" "VRX")]) 2290 2291; *a = vec_extract (vec_revb (b), 1); get-element-bswap-3.c 2292; *a = vec_revb (b)[1]; get-element-bswap-4.c 2293; vstebrh, vstebrf, vstebrg 2294(define_insn "*vec_extract_bswap_vec<mode>" 2295 [(set (match_operand:<non_vec> 0 "memory_operand" "=R") 2296 (unspec:<non_vec> [(bswap:V_HW_HSD (match_operand:V_HW_HSD 1 "register_operand" "v")) 2297 (match_operand:SI 2 "const_int_operand" "C")] 2298 UNSPEC_VEC_EXTRACT))] 2299 "TARGET_VXE2 && UINTVAL (operands[2]) < GET_MODE_NUNITS (<V_HW_HSD:MODE>mode)" 2300 "vstebr<bhfgq>\t%v1,%0,%2" 2301 [(set_attr "op_type" "VRX")]) 2302 2303; *a = __builtin_bswap32 (vec_extract (b, 1)); get-element-bswap-1.c 2304; *a = __builtin_bswap32 (b[1]); get-element-bswap-2.c 2305; vstebrh, vstebrf, vstebrg 2306(define_insn "*vec_extract_bswap_elem<mode>" 2307 [(set (match_operand:<non_vec> 0 "memory_operand" "=R") 2308 (bswap:<non_vec> 2309 (unspec:<non_vec> [(match_operand:V_HW_HSD 1 "register_operand" "v") 2310 (match_operand:SI 2 "const_int_operand" "C")] 2311 UNSPEC_VEC_EXTRACT)))] 2312 "TARGET_VXE2 && UINTVAL (operands[2]) < GET_MODE_NUNITS (<V_HW_HSD:MODE>mode)" 2313 "vstebr<bhfgq>\t%v1,%0,%2" 2314 [(set_attr "op_type" "VRX")]) 2315