amdgcn: Add instruction patterns for conditional min/max operations
gcc/ChangeLog:
* config/gcn/gcn-valu.md (<expander><mode>3_exec): Add patterns for
{s|u}{max|min} in QI, HI and DI modes.
(<expander><mode>3): Add pattern for {s|u}{max|min} in DI mode.
(cond_<fexpander><mode>): Add pattern for cond_f{max|min}.
(cond_<expander><mode>): Add pattern for cond_{s|u}{max|min}.
* config/gcn/gcn.cc (gcn_spill_class): Allow the exec register to be
saved in SGPRs.
gcc/testsuite/ChangeLog:
* gcc.target/gcn/cond_fmaxnm_1.c: New test.
* gcc.target/gcn/cond_fmaxnm_1_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_2.c: New test.
* gcc.target/gcn/cond_fmaxnm_2_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_3.c: New test.
* gcc.target/gcn/cond_fmaxnm_3_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_4.c: New test.
* gcc.target/gcn/cond_fmaxnm_4_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_5.c: New test.
* gcc.target/gcn/cond_fmaxnm_5_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_6.c: New test.
* gcc.target/gcn/cond_fmaxnm_6_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_7.c: New test.
* gcc.target/gcn/cond_fmaxnm_7_run.c: New test.
* gcc.target/gcn/cond_fmaxnm_8.c: New test.
* gcc.target/gcn/cond_fmaxnm_8_run.c: New test.
* gcc.target/gcn/cond_fminnm_1.c: New test.
* gcc.target/gcn/cond_fminnm_1_run.c: New test.
* gcc.target/gcn/cond_fminnm_2.c: New test.
* gcc.target/gcn/cond_fminnm_2_run.c: New test.
* gcc.target/gcn/cond_fminnm_3.c: New test.
* gcc.target/gcn/cond_fminnm_3_run.c: New test.
* gcc.target/gcn/cond_fminnm_4.c: New test.
* gcc.target/gcn/cond_fminnm_4_run.c: New test.
* gcc.target/gcn/cond_fminnm_5.c: New test.
* gcc.target/gcn/cond_fminnm_5_run.c: New test.
* gcc.target/gcn/cond_fminnm_6.c: New test.
* gcc.target/gcn/cond_fminnm_6_run.c: New test.
* gcc.target/gcn/cond_fminnm_7.c: New test.
* gcc.target/gcn/cond_fminnm_7_run.c: New test.
* gcc.target/gcn/cond_fminnm_8.c: New test.
* gcc.target/gcn/cond_fminnm_8_run.c: New test.
* gcc.target/gcn/cond_smax_1.c: New test.
* gcc.target/gcn/cond_smax_1_run.c: New test.
* gcc.target/gcn/cond_smin_1.c: New test.
* gcc.target/gcn/cond_smin_1_run.c: New test.
* gcc.target/gcn/cond_umax_1.c: New test.
* gcc.target/gcn/cond_umax_1_run.c: New test.
* gcc.target/gcn/cond_umin_1.c: New test.
* gcc.target/gcn/cond_umin_1_run.c: New test.
* gcc.target/gcn/smax_1.c: New test.
* gcc.target/gcn/smax_1_run.c: New test.
* gcc.target/gcn/smin_1.c: New test.
* gcc.target/gcn/smin_1_run.c: New test.
* gcc.target/gcn/umax_1.c: New test.
* gcc.target/gcn/umax_1_run.c: New test.
* gcc.target/gcn/umin_1.c: New test.
* gcc.target/gcn/umin_1_run.c: New test.
This commit is contained in:
+136
-1
@@ -2358,6 +2358,34 @@
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_expand "<expander><mode>3_exec"
|
||||
[(set (match_operand:V_QIHI 0 "gcn_valu_dst_operand")
|
||||
(vec_merge:V_QIHI
|
||||
(minmaxop:V_QIHI
|
||||
(match_operand:V_QIHI 1 "gcn_valu_src0_operand")
|
||||
(match_operand:V_QIHI 2 "gcn_valu_src1com_operand"))
|
||||
(match_operand:V_QIHI 3 "gcn_register_or_unspec_operand" "U0")
|
||||
(match_operand:DI 4 "gcn_exec_reg_operand" "e")))]
|
||||
""
|
||||
{
|
||||
enum {smin, umin, smax, umax};
|
||||
bool unsignedp = (<code> == umax || <code> == umin);
|
||||
rtx insi1 = gen_reg_rtx (<VnSI>mode);
|
||||
rtx insi2 = gen_reg_rtx (<VnSI>mode);
|
||||
rtx outsi = gen_reg_rtx (<VnSI>mode);
|
||||
rtx out = operands[0];
|
||||
rtx exec = operands[4];
|
||||
rtx tmp = gen_reg_rtx (<MODE>mode);
|
||||
|
||||
convert_move (insi1, operands[1], unsignedp);
|
||||
convert_move (insi2, operands[2], unsignedp);
|
||||
emit_insn (gen_<code><vnsi>3_exec (outsi, insi1, insi2,
|
||||
gcn_gen_undef(<VnSI>mode), exec));
|
||||
convert_move (tmp, outsi, unsignedp);
|
||||
emit_insn (gen_mov<mode>_exec (out, tmp, operands[3], exec));
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_insn "<expander><vnsi>3<exec>"
|
||||
[(set (match_operand:V_SI 0 "gcn_valu_dst_operand" "= v,RD")
|
||||
(minmaxop:V_SI
|
||||
@@ -2370,6 +2398,71 @@
|
||||
[(set_attr "type" "vop2,ds")
|
||||
(set_attr "length" "8,8")])
|
||||
|
||||
(define_insn_and_split "<expander><mode>3"
|
||||
[(set (match_operand:V_DI 0 "register_operand" "=v")
|
||||
(minmaxop:V_DI
|
||||
(match_operand:V_DI 1 "gcn_alu_operand" " v")
|
||||
(match_operand:V_DI 2 "gcn_alu_operand" " v")))
|
||||
(clobber (reg:DI VCC_REG))]
|
||||
""
|
||||
"#"
|
||||
"reload_completed"
|
||||
[(const_int 0)]
|
||||
{
|
||||
rtx out = operands[0];
|
||||
rtx vcc = gen_rtx_REG (DImode, VCC_REG);
|
||||
|
||||
enum {smin, smax, umin, umax};
|
||||
bool minp = (<code> == smin || <code> == umin);
|
||||
if (<code> == smin || <code> == smax)
|
||||
emit_insn (gen_vec_cmp<mode>di (vcc, minp ? gen_rtx_LT (VOIDmode, 0, 0) :
|
||||
gen_rtx_GT (VOIDmode, 0, 0), operands[1],
|
||||
operands[2]));
|
||||
else
|
||||
emit_insn (gen_vec_cmp<mode>di (vcc, minp ? gen_rtx_LTU (VOIDmode, 0, 0) :
|
||||
gen_rtx_GTU (VOIDmode, 0, 0), operands[1],
|
||||
operands[2]));
|
||||
emit_insn (gen_vcond_mask_<mode>di (out, operands[1], operands[2], vcc));
|
||||
}
|
||||
[(set_attr "type" "mult")])
|
||||
|
||||
(define_insn_and_split "<expander><mode>3_exec"
|
||||
[(set (match_operand:V_DI 0 "register_operand" "= v")
|
||||
(vec_merge:V_DI
|
||||
(minmaxop:V_DI
|
||||
(match_operand:V_DI 1 "gcn_alu_operand" " v")
|
||||
(match_operand:V_DI 2 "gcn_alu_operand" " v"))
|
||||
(match_operand:V_DI 3 "gcn_register_or_unspec_operand" " U0")
|
||||
(match_operand:DI 4 "gcn_exec_reg_operand" "+e")))
|
||||
(clobber (match_scratch:<VnDI> 5 "= &v"))
|
||||
(clobber (reg:DI VCC_REG))]
|
||||
""
|
||||
"#"
|
||||
"reload_completed"
|
||||
[(const_int 0)]
|
||||
{
|
||||
rtx out = operands[0];
|
||||
rtx vcc = gen_rtx_REG (DImode, VCC_REG);
|
||||
rtx exec = operands[4];
|
||||
rtx tmp = operands[5];
|
||||
|
||||
enum {smin, smax, umin, umax};
|
||||
bool minp = (<code> == smin || <code> == umin);
|
||||
if (<code> == smin || <code> == smax)
|
||||
emit_insn (gen_vec_cmp<mode>di_exec (vcc,
|
||||
minp ? gen_rtx_LT (VOIDmode, 0, 0) :
|
||||
gen_rtx_GT (VOIDmode, 0, 0),
|
||||
operands[1], operands[2], exec));
|
||||
else
|
||||
emit_insn (gen_vec_cmp<mode>di_exec (vcc,
|
||||
minp ? gen_rtx_LTU (VOIDmode, 0, 0) :
|
||||
gen_rtx_GTU (VOIDmode, 0, 0),
|
||||
operands[1], operands[2], exec));
|
||||
emit_insn (gen_vcond_mask_<mode>di (tmp, operands[1], operands[2], vcc));
|
||||
emit_insn (gen_mov<mode>_exec (out, tmp, operands[3], exec));
|
||||
}
|
||||
[(set_attr "type" "mult")])
|
||||
|
||||
;; }}}
|
||||
;; {{{ Int unops
|
||||
|
||||
@@ -3468,7 +3561,49 @@
|
||||
DONE;
|
||||
})
|
||||
|
||||
;; TODO smin umin smax umax
|
||||
(define_code_iterator cond_fminmaxop [smin smax])
|
||||
|
||||
(define_expand "cond_<fexpander><mode>"
|
||||
[(match_operand:V_FP 0 "register_operand")
|
||||
(match_operand:DI 1 "register_operand")
|
||||
(cond_fminmaxop:V_FP
|
||||
(match_operand:V_FP 2 "gcn_alu_operand")
|
||||
(match_operand:V_FP 3 "gcn_alu_operand"))
|
||||
(match_operand:V_FP 4 "register_operand")]
|
||||
""
|
||||
{
|
||||
operands[1] = force_reg (DImode, operands[1]);
|
||||
operands[2] = force_reg (<MODE>mode, operands[2]);
|
||||
|
||||
emit_insn (gen_<fexpander><mode>3_exec (operands[0], operands[2],
|
||||
operands[3], operands[4],
|
||||
operands[1]));
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_code_iterator cond_minmaxop [smin smax umin umax])
|
||||
|
||||
(define_expand "cond_<expander><mode>"
|
||||
[(match_operand:V_INT 0 "register_operand")
|
||||
(match_operand:DI 1 "register_operand")
|
||||
(cond_minmaxop:V_INT
|
||||
(match_operand:V_INT 2 "gcn_alu_operand")
|
||||
(match_operand:V_INT 3 "gcn_alu_operand"))
|
||||
(match_operand:V_INT 4 "register_operand")]
|
||||
""
|
||||
{
|
||||
operands[1] = force_reg (DImode, operands[1]);
|
||||
operands[2] = force_reg (<MODE>mode, operands[2]);
|
||||
rtx tmp = gen_reg_rtx (<MODE>mode);
|
||||
|
||||
emit_insn (gen_<expander><mode>3_exec (tmp, operands[2], operands[3],
|
||||
gcn_gen_undef(<MODE>mode),
|
||||
operands[1]));
|
||||
emit_insn (gen_vcond_mask_<mode>di (operands[0], tmp, operands[4],
|
||||
operands[1]));
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_code_iterator cond_bitop [and ior xor])
|
||||
|
||||
(define_expand "cond_<expander><mode>"
|
||||
|
||||
@@ -798,7 +798,7 @@ static reg_class_t
|
||||
gcn_spill_class (reg_class_t c, machine_mode /*mode */ )
|
||||
{
|
||||
if (reg_classes_intersect_p (ALL_CONDITIONAL_REGS, c)
|
||||
|| c == VCC_CONDITIONAL_REG)
|
||||
|| c == VCC_CONDITIONAL_REG || c == EXEC_MASK_REG)
|
||||
return SGPR_REGS;
|
||||
else
|
||||
return NO_REGS;
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifndef FN
|
||||
#define FN(X) __builtin_fmax##X
|
||||
#endif
|
||||
|
||||
#define DEF_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
void __attribute__ ((noipa)) \
|
||||
test_##TYPE##_##NAME (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
PRED_TYPE *__restrict pred, int n) \
|
||||
{ \
|
||||
for (int i = 0; i < n; ++i) \
|
||||
x[i] = pred[i] != 1 ? FN (y[i], CONST) : y[i]; \
|
||||
}
|
||||
|
||||
#define TEST_TYPE(T, FN, TYPE, PRED_TYPE) \
|
||||
T (FN, TYPE, PRED_TYPE, zero, 0) \
|
||||
T (FN, TYPE, PRED_TYPE, one, 1) \
|
||||
T (FN, TYPE, PRED_TYPE, two, 2)
|
||||
|
||||
#define TEST_ALL(T) \
|
||||
TEST_TYPE (T, FN (f32), float, int32_t) \
|
||||
TEST_TYPE (T, FN (f64), double, int64_t)
|
||||
|
||||
TEST_ALL (DEF_LOOP)
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,32 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#include "cond_fmaxnm_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
PRED_TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
test_##TYPE##_##NAME (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != 1 ? FN (y[i], CONST) : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_LOOP)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifndef FN
|
||||
#define FN(X) __builtin_fmax##X
|
||||
#endif
|
||||
|
||||
#define DEF_LOOP(FN, TYPE, NAME, CONST) \
|
||||
void __attribute__ ((noipa)) \
|
||||
test_##TYPE##_##NAME (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
TYPE *__restrict z, int n) \
|
||||
{ \
|
||||
for (int i = 0; i < n; ++i) \
|
||||
x[i] = y[i] < 8 ? FN (z[i], CONST) : y[i]; \
|
||||
}
|
||||
|
||||
#define TEST_TYPE(T, FN, TYPE) \
|
||||
T (FN, TYPE, zero, 0) \
|
||||
T (FN, TYPE, one, 1) \
|
||||
T (FN, TYPE, two, 2)
|
||||
|
||||
#define TEST_ALL(T) \
|
||||
TEST_TYPE (T, FN (f32), float) \
|
||||
TEST_TYPE (T, FN (f64), double)
|
||||
|
||||
TEST_ALL (DEF_LOOP)
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,31 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#include "cond_fmaxnm_2.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_LOOP(FN, TYPE, NAME, CONST) \
|
||||
{ \
|
||||
TYPE x[N], y[N], z[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
y[i] = i % 13; \
|
||||
z[i] = i * i; \
|
||||
} \
|
||||
test_##TYPE##_##NAME (x, y, z, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = y[i] < 8 ? FN (z[i], CONST) : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_LOOP)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifndef FN
|
||||
#define FN(X) __builtin_fmax##X
|
||||
#endif
|
||||
|
||||
#define DEF_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
void __attribute__ ((noipa)) \
|
||||
test_##TYPE##_##NAME (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
PRED_TYPE *__restrict pred, int n) \
|
||||
{ \
|
||||
for (int i = 0; i < n; ++i) \
|
||||
x[i] = pred[i] != 1 ? FN (y[i], CONST) : 4; \
|
||||
}
|
||||
|
||||
#define TEST_TYPE(T, FN, TYPE, PRED_TYPE) \
|
||||
T (FN, TYPE, PRED_TYPE, zero, 0) \
|
||||
T (FN, TYPE, PRED_TYPE, one, 1) \
|
||||
T (FN, TYPE, PRED_TYPE, two, 2)
|
||||
|
||||
#define TEST_ALL(T) \
|
||||
TEST_TYPE (T, FN (f32), float, int32_t) \
|
||||
TEST_TYPE (T, FN (f64), double, int64_t)
|
||||
|
||||
TEST_ALL (DEF_LOOP)
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64sf_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64df_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,32 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#include "cond_fmaxnm_3.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
PRED_TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
test_##TYPE##_##NAME (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != 1 ? FN (y[i], CONST) : 4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_LOOP)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifndef FN
|
||||
#define FN(X) __builtin_fmax##X
|
||||
#endif
|
||||
|
||||
#define DEF_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
void __attribute__ ((noipa)) \
|
||||
test_##TYPE##_##NAME (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
PRED_TYPE *__restrict pred, int n) \
|
||||
{ \
|
||||
for (int i = 0; i < n; ++i) \
|
||||
x[i] = pred[i] != 1 ? FN (y[i], CONST) : 0; \
|
||||
}
|
||||
|
||||
#define TEST_TYPE(T, FN, TYPE, PRED_TYPE) \
|
||||
T (FN, TYPE, PRED_TYPE, zero, 0) \
|
||||
T (FN, TYPE, PRED_TYPE, one, 1) \
|
||||
T (FN, TYPE, PRED_TYPE, two, 2)
|
||||
|
||||
#define TEST_ALL(T) \
|
||||
TEST_TYPE (T, FN (f32), float, int32_t) \
|
||||
TEST_TYPE (T, FN (f64), double, int64_t)
|
||||
|
||||
TEST_ALL (DEF_LOOP)
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64sf_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64df_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,32 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#include "cond_fmaxnm_4.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_LOOP(FN, TYPE, PRED_TYPE, NAME, CONST) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
PRED_TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
test_##TYPE##_##NAME (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != 1 ? FN (y[i], CONST) : 0; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_LOOP)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include "cond_fmaxnm_1.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fmaxnm_1_run.c"
|
||||
@@ -0,0 +1,9 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include "cond_fmaxnm_2.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fmaxnm_2_run.c"
|
||||
@@ -0,0 +1,9 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include "cond_fmaxnm_3.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fmaxnm_3_run.c"
|
||||
@@ -0,0 +1,9 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include "cond_fmaxnm_4.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {smaxv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {smaxv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fmaxnm_4_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_1.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,5 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_1_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_2.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,5 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_2_run.c"
|
||||
@@ -0,0 +1,12 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_3.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64sf_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64df_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,5 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_3_run.c"
|
||||
@@ -0,0 +1,12 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_4.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64sf_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {movv64df_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,5 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -ffast-math" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_4_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_1.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fminnm_1_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_2.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fminnm_2_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_3.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fminnm_3_run.c"
|
||||
@@ -0,0 +1,10 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#define FN(X) __builtin_fmin##X
|
||||
#include "cond_fmaxnm_4.c"
|
||||
|
||||
/* { dg-final { scan-assembler-times {sminv64sf3_exec} 3 } } */
|
||||
/* { dg-final { scan-assembler-times {sminv64df3_exec} 3 } } */
|
||||
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_..} } } */
|
||||
@@ -0,0 +1,4 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_fminnm_4_run.c"
|
||||
@@ -0,0 +1,57 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
TYPE *__restrict pred, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != -1) ? (x[i] > y[i] ? x[i] : y[i]) : -4; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##NAME##_##TYPE (TYPE *__restrict x, TYPE *__restrict pred, \
|
||||
int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] \
|
||||
= (pred[i] != -1) ? (x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE) : -4; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (0, TYPE, 0); \
|
||||
IMM (86, TYPE, 86); \
|
||||
IMM (109, TYPE, 109); \
|
||||
IMM (141, TYPE, 141); \
|
||||
IMM (92137445376, TYPE, 92137445376); \
|
||||
IMM (-1, TYPE, minus1); \
|
||||
IMM (-110, TYPE, minus110); \
|
||||
IMM (-141, TYPE, minus141); \
|
||||
IMM (-92137445376, TYPE, minus92137445376);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, int8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per test case < 64 bits */
|
||||
/* { dg-final { scan-assembler-times {smaxv64si3_exec} 30 } } */
|
||||
/* { dg-final { scan-assembler-not {smaxv64si3/0} } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_??, 0} } } */
|
||||
|
||||
/* Two per test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i32\tvcc, s[0-9]+, v[0-9]+} 80 } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} } } */
|
||||
/* { dg-final { scan-assembler-not {\ts_cmpk_lg_u32\tvcc_lo, 0} } } */
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_ne_u64\ts\[[0-9]+:[0-9]+\], v\[[0-9]+:[0-9]+\], -1} 10 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 10 } } */
|
||||
@@ -0,0 +1,53 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_smax_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != -1 ? (x[i] > y[i] ? x[i] : y[i]) : -4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varithimm_##NAME##_##TYPE (x, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected \
|
||||
= i % 3 != -1 ? (x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE) : -4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
TYPE *__restrict pred, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != -1) ? (x[i] < y[i] ? x[i] : y[i]) : -4; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##NAME##_##TYPE (TYPE *__restrict x, TYPE *__restrict pred, \
|
||||
int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] \
|
||||
= (pred[i] != -1) ? (x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE) : -4; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (0, TYPE, 0); \
|
||||
IMM (86, TYPE, 86); \
|
||||
IMM (109, TYPE, 109); \
|
||||
IMM (141, TYPE, 141); \
|
||||
IMM (92137445376, TYPE, 92137445376); \
|
||||
IMM (-1, TYPE, minus1); \
|
||||
IMM (-110, TYPE, minus110); \
|
||||
IMM (-141, TYPE, minus141); \
|
||||
IMM (-92137445376, TYPE, minus92137445376);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, int8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per test case < 64 bits */
|
||||
/* { dg-final { scan-assembler-times {sminv64si3_exec} 30 } } */
|
||||
/* { dg-final { scan-assembler-not {sminv64si3/0} } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_??, 0} } } */
|
||||
|
||||
/* Two per test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i32\tvcc, s[0-9]+, v[0-9]+} 80 } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} } } */
|
||||
/* { dg-final { scan-assembler-not {\ts_cmpk_lg_u32\tvcc_lo, 0} } } */
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_ne_u64\ts\[[0-9]+:[0-9]+\], v\[[0-9]+:[0-9]+\], -1} 10 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_lt_i64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 10 } } */
|
||||
@@ -0,0 +1,53 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_smin_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != -1 ? (x[i] < y[i] ? x[i] : y[i]) : -4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varithimm_##NAME##_##TYPE (x, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected \
|
||||
= i % 3 != -1 ? (x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE) : -4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
TYPE *__restrict pred, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != 1) ? (x[i] > y[i] ? x[i] : y[i]) : 4; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##VALUE##_##TYPE (TYPE *__restrict x, TYPE *__restrict pred, \
|
||||
int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != 1) ? (x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE) : 4; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (2, TYPE); \
|
||||
IMM (86, TYPE); \
|
||||
IMM (109, TYPE); \
|
||||
IMM (141, TYPE); \
|
||||
IMM (229, TYPE); \
|
||||
IMM (255, TYPE); \
|
||||
IMM (992137445376, TYPE);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, uint8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* Two per test case < 64 bits with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {umaxv64si3_exec} 20 } } */
|
||||
/* { dg-final { scan-assembler-not {umaxv64si3/0} } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_??, 0} } } */
|
||||
|
||||
/* Two per test case with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i32\tvcc, s[0-9]+, v[0-9]+} 56 } } */
|
||||
/* { dg-final { scan-assembler-not {\ts_cmpk_lg_u32\tvcc_lo, 0} } } */
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_ne_u64\ts\[[0-9]+:[0-9]+\], v\[[0-9]+:[0-9]+\], 1} 8 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_u64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 8 } } */
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_umax_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != 1 ? (x[i] > y[i] ? x[i] : y[i]) : 4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varithimm_##VALUE##_##TYPE (x, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected \
|
||||
= i % 3 != 1 ? (x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE) : 4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, \
|
||||
TYPE *__restrict pred, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != 1) ? (x[i] < y[i] ? x[i] : y[i]) : 4; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##VALUE##_##TYPE (TYPE *__restrict x, TYPE *__restrict pred, \
|
||||
int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = (pred[i] != 1) ? (x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE) : 4; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (2, TYPE); \
|
||||
IMM (86, TYPE); \
|
||||
IMM (109, TYPE); \
|
||||
IMM (141, TYPE); \
|
||||
IMM (229, TYPE); \
|
||||
IMM (255, TYPE); \
|
||||
IMM (992137445376, TYPE);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, uint8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* Two per test case < 64 bits with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {uminv64si3_exec} 20 } } */
|
||||
/* { dg-final { scan-assembler-not {uminv64si3/0} } } */
|
||||
/* { dg-final { scan-assembler-not {\tv_writelane_b32\tv[0-9]+, vcc_??, 0} } } */
|
||||
|
||||
/* Two per test case with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i32\tvcc, s[0-9]+, v[0-9]+} 56 } } */
|
||||
/* { dg-final { scan-assembler-not {\ts_cmpk_lg_u32\tvcc_lo, 0} } } */
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_ne_u64\ts\[[0-9]+:[0-9]+\], v\[[0-9]+:[0-9]+\], 1} 8 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_lt_u64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 8 } } */
|
||||
@@ -0,0 +1,53 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "cond_umin_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = i % 3 != 1 ? (x[i] < y[i] ? x[i] : y[i]) : 4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
TYPE pred[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
pred[i] = i % 3; \
|
||||
} \
|
||||
varithimm_##VALUE##_##TYPE (x, pred, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected \
|
||||
= i % 3 != 1 ? (x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE) : 4; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] > y[i] ? x[i] : y[i]; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##NAME##_##TYPE (TYPE *__restrict x, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (0, TYPE, 0); \
|
||||
IMM (86, TYPE, 86); \
|
||||
IMM (109, TYPE, 109); \
|
||||
IMM (141, TYPE, 141); \
|
||||
IMM (92137445376, TYPE, 92137445376); \
|
||||
IMM (-1, TYPE, minus1); \
|
||||
IMM (-110, TYPE, minus110); \
|
||||
IMM (-141, TYPE, minus141); \
|
||||
IMM (-92137445376, TYPE, minus92137445376);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, int8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {vec_cmpv64didi} 10 } } */
|
||||
|
||||
/* Two per test case: */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_i64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 10 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} 80 } } */
|
||||
@@ -0,0 +1,48 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "smax_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] > y[i] ? x[i] : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
} \
|
||||
varithimm_##NAME##_##TYPE (x, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] < y[i] ? x[i] : y[i]; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##NAME##_##TYPE (TYPE *__restrict x, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (0, TYPE, 0); \
|
||||
IMM (86, TYPE, 86); \
|
||||
IMM (109, TYPE, 109); \
|
||||
IMM (141, TYPE, 141); \
|
||||
IMM (92137445376, TYPE, 92137445376); \
|
||||
IMM (-1, TYPE, minus1); \
|
||||
IMM (-110, TYPE, minus110); \
|
||||
IMM (-141, TYPE, minus141); \
|
||||
IMM (-92137445376, TYPE, minus92137445376);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, int8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, int64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {vec_cmpv64didi} 10 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_lt_i64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 10 } } */
|
||||
|
||||
/* Two per test case:*/
|
||||
/* { dg-final { scan-assembler-times {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} 80 } } */
|
||||
@@ -0,0 +1,48 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "smin_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] < y[i] ? x[i] : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE, NAME) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
} \
|
||||
varithimm_##NAME##_##TYPE (x, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] > y[i] ? x[i] : y[i]; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##VALUE##_##TYPE (TYPE *__restrict x, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (2, TYPE); \
|
||||
IMM (86, TYPE); \
|
||||
IMM (109, TYPE); \
|
||||
IMM (141, TYPE); \
|
||||
IMM (229, TYPE); \
|
||||
IMM (255, TYPE); \
|
||||
IMM (992137445376, TYPE);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, uint8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {vec_cmpv64didi} 8 } } */
|
||||
|
||||
/* Two per test case with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_gt_u64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 8 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} 56 } } */
|
||||
@@ -0,0 +1,48 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "umax_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] > y[i] ? x[i] : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
} \
|
||||
varithimm_##VALUE##_##TYPE (x, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] > (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
/* { dg-do compile } */
|
||||
/* { dg-options "-O2 -ftree-vectorize -dp" } */
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define DO_REGREG_OPS(TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varith_##TYPE##_reg (TYPE *__restrict x, TYPE *__restrict y, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] < y[i] ? x[i] : y[i]; \
|
||||
}
|
||||
|
||||
#define DO_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
void __attribute__ ((noclone)) \
|
||||
varithimm_##VALUE##_##TYPE (TYPE *__restrict x, int count) \
|
||||
{ \
|
||||
for (int i = 0; i < count; ++i) \
|
||||
x[i] = x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
}
|
||||
|
||||
#define DO_ARITH_OPS(REG, IMM, TYPE) \
|
||||
REG (TYPE); \
|
||||
IMM (2, TYPE); \
|
||||
IMM (86, TYPE); \
|
||||
IMM (109, TYPE); \
|
||||
IMM (141, TYPE); \
|
||||
IMM (229, TYPE); \
|
||||
IMM (255, TYPE); \
|
||||
IMM (992137445376, TYPE);
|
||||
|
||||
#define TEST_ALL(REG, IMM) \
|
||||
DO_ARITH_OPS (REG, IMM, uint8_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint16_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint32_t) \
|
||||
DO_ARITH_OPS (REG, IMM, uint64_t)
|
||||
|
||||
TEST_ALL (DO_REGREG_OPS, DO_IMMEDIATE_OPS)
|
||||
|
||||
/* One per 64-bit test case: */
|
||||
/* { dg-final { scan-assembler-times {vec_cmpv64didi} 8 } } */
|
||||
/* { dg-final { scan-assembler-times {\tv_cmp_lt_u64\tvcc, v[[0-9]+:[0-9]+], v[[0-9]+:[0-9]+]} 8 } } */
|
||||
|
||||
/* Two per test case with wide-enough type:*/
|
||||
/* { dg-final { scan-assembler-times {\tv_cmpx_gt_i32\tvcc, s[0-9]+, v[0-9]+} 56 } } */
|
||||
@@ -0,0 +1,48 @@
|
||||
/* { dg-do run } */
|
||||
/* { dg-options "-O2 -ftree-vectorize" } */
|
||||
|
||||
#include "umin_1.c"
|
||||
|
||||
#define N 99
|
||||
|
||||
#define TEST_REGREG_OPS(TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i % 13; \
|
||||
y[i] = i * i; \
|
||||
} \
|
||||
varith_##TYPE##_reg (x, y, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] < y[i] ? x[i] : y[i]; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define TEST_IMMEDIATE_OPS(VALUE, TYPE) \
|
||||
{ \
|
||||
TYPE x[N], y[N]; \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
x[i] = i * i; \
|
||||
} \
|
||||
varithimm_##VALUE##_##TYPE (x, N); \
|
||||
for (int i = 0; i < N; ++i) \
|
||||
{ \
|
||||
TYPE expected = x[i] < (TYPE) VALUE ? x[i] : (TYPE) VALUE; \
|
||||
if (x[i] != expected) \
|
||||
__builtin_abort (); \
|
||||
asm volatile ("" ::: "memory"); \
|
||||
} \
|
||||
}
|
||||
|
||||
int
|
||||
main (void)
|
||||
{
|
||||
TEST_ALL (TEST_REGREG_OPS, TEST_IMMEDIATE_OPS)
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user