aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEric Botcazou <ebotcazou@adacore.com>2015-12-04 14:52:09 +0000
committerEric Botcazou <ebotcazou@adacore.com>2015-12-04 14:52:09 +0000
commit62dd1863abd65ada3d0929db1789c617ff34e1a6 (patch)
tree94204ba776de500b6dc0fc54682d443fd0755f6d
parentc672cad4aff4f9923eab0995cc327a0cb7fc8e2a (diff)
Merge from trunk @231250.scalar-storage-order
git-svn-id: https://gcc.gnu.org/svn/gcc/branches/scalar-storage-order@231274 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r--gcc/ChangeLog672
-rw-r--r--gcc/DATESTAMP2
-rw-r--r--gcc/Makefile.in39
-rw-r--r--gcc/ada/ChangeLog6
-rw-r--r--gcc/ada/s-oscons-tmplt.c6
-rw-r--r--gcc/ada/s-osinte-rtems.ads50
-rw-r--r--gcc/alias.c30
-rw-r--r--gcc/builtins.c7
-rw-r--r--gcc/c-family/ChangeLog40
-rw-r--r--gcc/c-family/c-common.c615
-rw-r--r--gcc/c-family/c-common.h3
-rw-r--r--gcc/c-family/c-ppoutput.c38
-rw-r--r--gcc/c-family/c-pragma.c1
-rw-r--r--gcc/c-family/c-pragma.h2
-rw-r--r--gcc/c/ChangeLog50
-rw-r--r--gcc/c/Make-lang.in2
-rw-r--r--gcc/c/c-decl.c45
-rw-r--r--gcc/c/c-fold.c589
-rw-r--r--gcc/c/c-parser.c43
-rw-r--r--gcc/c/c-tree.h6
-rw-r--r--gcc/c/c-typeck.c73
-rw-r--r--gcc/cfgexpand.c11
-rw-r--r--gcc/cgraphunit.c3
-rw-r--r--gcc/common.opt2
-rw-r--r--gcc/config.in6
-rw-r--r--gcc/config/aarch64/aarch64-builtins.c34
-rw-r--r--gcc/config/aarch64/aarch64-cores.def2
-rw-r--r--gcc/config/aarch64/aarch64-protos.h2
-rw-r--r--gcc/config/aarch64/aarch64-simd.md13
-rw-r--r--gcc/config/aarch64/aarch64.c179
-rw-r--r--gcc/config/aarch64/aarch64.md11
-rw-r--r--gcc/config/aarch64/iterators.md10
-rw-r--r--gcc/config/arm/aarch-cost-tables.h103
-rw-r--r--gcc/config/arm/arm-c.c4
-rw-r--r--gcc/config/arm/arm-cores.def2
-rw-r--r--gcc/config/arm/arm.c69
-rw-r--r--gcc/config/arm/arm.h1
-rw-r--r--gcc/config/arm/arm.opt2
-rw-r--r--gcc/config/i386/i386.c231
-rw-r--r--gcc/config/i386/i386.md70
-rw-r--r--gcc/config/i386/sse.md44
-rw-r--r--gcc/config/mips/mips.c26
-rw-r--r--gcc/config/nvptx/nvptx-protos.h7
-rw-r--r--gcc/config/nvptx/nvptx.c485
-rw-r--r--gcc/config/nvptx/nvptx.h42
-rw-r--r--gcc/config/nvptx/nvptx.md239
-rw-r--r--gcc/config/rs6000/freebsd64.h13
-rw-r--r--gcc/config/rs6000/rs6000.c203
-rw-r--r--gcc/config/rs6000/rs6000.md50
-rw-r--r--gcc/config/s390/constraints.md46
-rw-r--r--gcc/config/s390/predicates.md5
-rw-r--r--gcc/config/s390/s390-builtin-types.def1025
-rw-r--r--gcc/config/s390/s390-builtins.def27
-rw-r--r--gcc/config/s390/s390-c.c24
-rw-r--r--gcc/config/s390/s390.c35
-rw-r--r--gcc/config/s390/s390.md38
-rw-r--r--gcc/config/s390/vecintrin.h16
-rw-r--r--gcc/config/s390/vector.md19
-rw-r--r--gcc/config/s390/vx-builtins.md194
-rwxr-xr-xgcc/configure35
-rw-r--r--gcc/configure.ac6
-rw-r--r--gcc/coretypes.h12
-rw-r--r--gcc/cp/ChangeLog78
-rw-r--r--gcc/cp/Make-lang.in12
-rw-r--r--gcc/cp/call.c11
-rw-r--r--gcc/cp/constraint.cc26
-rw-r--r--gcc/cp/cp-gimplify.c76
-rw-r--r--gcc/cp/cp-tree.h1
-rw-r--r--gcc/cp/mangle.c2
-rw-r--r--gcc/cp/parser.c50
-rw-r--r--gcc/cp/pt.c45
-rw-r--r--gcc/cp/semantics.c19
-rw-r--r--gcc/cp/tree.c3
-rw-r--r--gcc/doc/md.texi365
-rw-r--r--gcc/doc/tm.texi20
-rw-r--r--gcc/doc/tm.texi.in2
-rw-r--r--gcc/dwarf2out.c97
-rw-r--r--gcc/final.c11
-rw-r--r--gcc/fortran/ChangeLog86
-rw-r--r--gcc/fortran/check.c53
-rw-r--r--gcc/fortran/dump-parse-tree.c45
-rw-r--r--gcc/fortran/expr.c13
-rw-r--r--gcc/fortran/gfortran.h11
-rw-r--r--gcc/fortran/gfortran.texi138
-rw-r--r--gcc/fortran/interface.c28
-rw-r--r--gcc/fortran/intrinsic.c7
-rw-r--r--gcc/fortran/intrinsic.h2
-rw-r--r--gcc/fortran/iresolve.c6
-rw-r--r--gcc/fortran/iso-fortran-env.def5
-rw-r--r--gcc/fortran/match.c198
-rw-r--r--gcc/fortran/match.h2
-rw-r--r--gcc/fortran/module.c8
-rw-r--r--gcc/fortran/openmp.c85
-rw-r--r--gcc/fortran/parse.c69
-rw-r--r--gcc/fortran/resolve.c93
-rw-r--r--gcc/fortran/st.c2
-rw-r--r--gcc/fortran/trans-decl.c28
-rw-r--r--gcc/fortran/trans-expr.c10
-rw-r--r--gcc/fortran/trans-intrinsic.c152
-rw-r--r--gcc/fortran/trans-openmp.c37
-rw-r--r--gcc/fortran/trans-stmt.c161
-rw-r--r--gcc/fortran/trans-stmt.h1
-rw-r--r--gcc/fortran/trans-types.c5
-rw-r--r--gcc/fortran/trans.c17
-rw-r--r--gcc/fortran/trans.h7
-rw-r--r--gcc/function.c2
-rw-r--r--gcc/genemit.c46
-rw-r--r--gcc/genmatch.c17
-rw-r--r--gcc/genopinit.c240
-rw-r--r--gcc/gensupport.c158
-rw-r--r--gcc/gensupport.h86
-rw-r--r--gcc/gimple-match-head.c2
-rw-r--r--gcc/gimple-pretty-print.c3
-rw-r--r--gcc/gimple.h2
-rw-r--r--gcc/gimplify.c57
-rw-r--r--gcc/go/gofrontend/MERGE2
-rw-r--r--gcc/go/gofrontend/types.cc46
-rw-r--r--gcc/graphite-dependences.c49
-rw-r--r--gcc/graphite-isl-ast-to-gimple.c33
-rw-r--r--gcc/graphite-poly.c2
-rw-r--r--gcc/graphite-sese-to-poly.c98
-rw-r--r--gcc/graphite.c2
-rw-r--r--gcc/ifcvt.c38
-rw-r--r--gcc/internal-fn.c43
-rw-r--r--gcc/internal-fn.def2
-rw-r--r--gcc/internal-fn.h6
-rw-r--r--gcc/ipa-pure-const.c92
-rw-r--r--gcc/ipa-split.c32
-rw-r--r--gcc/loop-init.c2
-rw-r--r--gcc/loop-iv.c2
-rw-r--r--gcc/lto-streamer-out.c4
-rw-r--r--gcc/lto/ChangeLog4
-rw-r--r--gcc/lto/lto.c4
-rw-r--r--gcc/match.pd10
-rw-r--r--gcc/omp-builtins.def2
-rw-r--r--gcc/omp-low.c118
-rw-r--r--gcc/optabs-query.c30
-rw-r--r--gcc/optabs-query.h6
-rw-r--r--gcc/optabs.c75
-rw-r--r--gcc/optabs.def26
-rw-r--r--gcc/opts-common.c2
-rw-r--r--gcc/passes.c2
-rw-r--r--gcc/predict.c20
-rw-r--r--gcc/predict.h2
-rw-r--r--gcc/regrename.c6
-rw-r--r--gcc/target.def25
-rw-r--r--gcc/targhooks.c10
-rw-r--r--gcc/targhooks.h5
-rw-r--r--gcc/testsuite/ChangeLog318
-rw-r--r--gcc/testsuite/c-c++-common/cpp/pr57580.c9
-rw-r--r--gcc/testsuite/c-c++-common/goacc/host_data-5.c23
-rw-r--r--gcc/testsuite/c-c++-common/goacc/host_data-6.c25
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-2.c27
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-3.c20
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-4.c22
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-5.c19
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-6.c23
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-7.c25
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-8.c22
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-2.c37
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-3.c36
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta.c23
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-alias.c29
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-default-2.c17
-rw-r--r--gcc/testsuite/c-c++-common/goacc/kernels-default.c14
-rw-r--r--gcc/testsuite/c-c++-common/gomp/pr57580.c36
-rw-r--r--gcc/testsuite/c-c++-common/gomp/pr64769.c9
-rw-r--r--gcc/testsuite/c-c++-common/pr68582.c25
-rw-r--r--gcc/testsuite/g++.dg/template/pr67337.C25
-rw-r--r--gcc/testsuite/g++.dg/torture/pr68184.C31
-rw-r--r--gcc/testsuite/g++.dg/torture/pr68470.C36
-rw-r--r--gcc/testsuite/g++.dg/warn/Wnonnull1.C7
-rw-r--r--gcc/testsuite/g++.dg/warn/nonnull3.C19
-rw-r--r--gcc/testsuite/gcc.c-torture/execute/alias-1.c19
-rw-r--r--gcc/testsuite/gcc.c-torture/execute/pr68624.c30
-rw-r--r--gcc/testsuite/gcc.dg/builtin-bswap-6a.c2
-rw-r--r--gcc/testsuite/gcc.dg/gomp/pr46032-2.c (renamed from gcc/testsuite/gcc.dg/pr46032-2.c)0
-rw-r--r--gcc/testsuite/gcc.dg/gomp/pr46032-3.c (renamed from gcc/testsuite/gcc.dg/pr46032-3.c)0
-rw-r--r--gcc/testsuite/gcc.dg/graphite/id-28.c72
-rw-r--r--gcc/testsuite/gcc.dg/optimize-bswapdi-1.c1
-rw-r--r--gcc/testsuite/gcc.dg/optimize-bswapdi-2.c1
-rw-r--r--gcc/testsuite/gcc.dg/optimize-bswapdi-3.c1
-rw-r--r--gcc/testsuite/gcc.dg/optimize-bswapsi-1.c2
-rw-r--r--gcc/testsuite/gcc.dg/optimize-bswapsi-2.c2
-rw-r--r--gcc/testsuite/gcc.dg/pr68162-1.c6
-rw-r--r--gcc/testsuite/gcc.dg/pr68474.c7
-rw-r--r--gcc/testsuite/gcc.dg/pr68513.c125
-rw-r--r--gcc/testsuite/gcc.dg/pr68533.c68
-rw-r--r--gcc/testsuite/gcc.dg/pr68595.c13
-rw-r--r--gcc/testsuite/gcc.dg/sso-9.c27
-rw-r--r--gcc/testsuite/gcc.dg/torture/pr67916.c46
-rw-r--r--gcc/testsuite/gcc.dg/torture/pr68379.c12
-rw-r--r--gcc/testsuite/gcc.dg/torture/pr68570.c35
-rw-r--r--gcc/testsuite/gcc.dg/torture/pr68625.c51
-rw-r--r--gcc/testsuite/gcc.dg/torture/vshuf-4.inc3
-rw-r--r--gcc/testsuite/gcc.dg/torture/vshuf-8.inc4
-rw-r--r--gcc/testsuite/gcc.dg/vect/pr46032.c (renamed from gcc/testsuite/gcc.dg/pr46032.c)2
-rw-r--r--gcc/testsuite/gcc.dg/vect/pr68577.c25
-rw-r--r--gcc/testsuite/gcc.dg/vect/slp-42.c19
-rw-r--r--gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c2
-rw-r--r--gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7.c2
-rw-r--r--gcc/testsuite/gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c4
-rw-r--r--gcc/testsuite/gcc.target/arm/attr-unaligned-load-ice.c19
-rw-r--r--gcc/testsuite/gcc.target/arm/ftest-armv6-thumb.c3
-rw-r--r--gcc/testsuite/gcc.target/arm/ftest-armv6k-thumb.c3
-rw-r--r--gcc/testsuite/gcc.target/arm/ftest-armv6z-thumb.c3
-rw-r--r--gcc/testsuite/gcc.target/i386/avx512vl-vextractf32x4-1.c2
-rw-r--r--gcc/testsuite/gcc.target/i386/avx512vl-vextracti32x4-1.c2
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68432-1.c17
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68432-2.c17
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68432-3.c17
-rw-r--r--gcc/testsuite/gcc.target/i386/pr68647.c18
-rw-r--r--gcc/testsuite/gcc.target/i386/vect-pr67800.c42
-rw-r--r--gcc/testsuite/gcc.target/nvptx/decl.c19
-rw-r--r--gcc/testsuite/gcc.target/nvptx/uninit-decl.c7
-rw-r--r--gcc/testsuite/gcc.target/powerpc/swaps-p8-22.c29
-rw-r--r--gcc/testsuite/gcc.target/s390/bswap-1.c26
-rw-r--r--gcc/testsuite/gcc.target/s390/bswaphi-1.c27
-rw-r--r--gcc/testsuite/gcc.target/s390/vector/vec-vrepi-1.c58
-rw-r--r--gcc/testsuite/gcc.target/s390/zvector/vec-splat-1.c42
-rw-r--r--gcc/testsuite/gcc.target/s390/zvector/vec-splat-2.c42
-rw-r--r--gcc/testsuite/gfortran.dg/coarray/event_1.f9051
-rw-r--r--gcc/testsuite/gfortran.dg/coarray/event_2.f9089
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/array-reduction.f9074
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/assumed.f953
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/coarray.f958
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/coarray_2.f908
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/gang-static.f9514
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/host_data-tree.f951
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/loop-2.f9524
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/loop-6.f958
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/loop-7.f95122
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/reduction-2.f9522
-rw-r--r--gcc/testsuite/gfortran.dg/goacc/reduction.f9523
-rw-r--r--gcc/testsuite/gfortran.dg/graphite/id-26.f03132
-rw-r--r--gcc/testsuite/gfortran.dg/graphite/pr68550-1.f9036
-rw-r--r--gcc/testsuite/gfortran.dg/graphite/pr68550-2.f9014
-rw-r--r--gcc/testsuite/gfortran.dg/graphite/run-id-3.f9012
-rw-r--r--gcc/testsuite/gfortran.dg/pr68379-1.f9035
-rw-r--r--gcc/testsuite/gfortran.dg/pr68379-2.f24
-rw-r--r--gcc/testsuite/gfortran.fortran-torture/compile/pr68639.f9022
-rw-r--r--gcc/testsuite/lib/g++-dg.exp15
-rw-r--r--gcc/testsuite/lib/g++.exp9
-rw-r--r--gcc/testsuite/lib/target-supports.exp4
-rw-r--r--gcc/toplev.c2
-rw-r--r--gcc/tree-call-cdce.c3
-rw-r--r--gcc/tree-cfgcleanup.c25
-rw-r--r--gcc/tree-nested.c2
-rw-r--r--gcc/tree-ssa-math-opts.c79
-rw-r--r--gcc/tree-ssa-structalias.c28
-rw-r--r--gcc/tree-ssa.c8
-rw-r--r--gcc/tree-ssa.h2
-rw-r--r--gcc/tree-streamer-in.c1
-rw-r--r--gcc/tree-streamer-out.c10
-rw-r--r--gcc/tree-vect-data-refs.c17
-rw-r--r--gcc/tree-vect-patterns.c14
-rw-r--r--gcc/tree-vect-slp.c75
-rw-r--r--gcc/tree-vect-stmts.c158
-rw-r--r--gcc/tree.c11
-rw-r--r--gcc/tree.h4
260 files changed, 9098 insertions, 3107 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 4dd84c73e74..7394e28444c 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,675 @@
+2015-12-04 Jakub Jelinek <jakub@redhat.com>
+
+ PR target/68655
+ * config/i386/i386.c (canonicalize_vector_int_perm): New function.
+ (expand_vec_perm_1): Use it and recurse if everything else
+ failed. Use nd.perm instead of perm2.
+ (expand_vec_perm_even_odd_1): If testing_p, use gen_raw_REG
+ instead of gen_lowpart for the target.
+ (ix86_expand_vec_perm_const_1): Use canonicalize_vector_int_perm
+ and recurse if everything else failed.
+
+2015-12-04 Richard Biener <rguenther@suse.de>
+
+ PR middle-end/68636
+ * builtins.c (get_pointer_alignment_1): Take care of byte to
+ bit alignment computation overflow.
+
+2015-12-04 Richard Biener <rguenther@suse.de>
+
+ PR middle-end/67438
+ * match.pd: Guard ~X cmp ~Y -> Y cmp X and the variant with
+ a constant with single_use.
+
+2015-12-04 Bin Cheng <bin.cheng@arm.com>
+ Jiong Wang <jiong.wang@arm.com>
+
+ * config/aarch64/aarch64.c (aarch64_legitimize_address): legitimize
+ address expressions like Ra + Rb + CONST and Ra + Rb<<SCALE + CONST.
+
+2015-12-03 Jan Hubicka <hubicka@ucw.cz>
+
+ * alias.c (alias_set_subset_of, alias_sets_must_conflict_p)
+ Short circuit for !flag_strict_aliasing
+ (get_alias_set): Remove flag_strict_aliasing check.
+ (new_alias_set): Likewise.
+
+2015-12-03 Evandro Menezes <e.menezes@samsung.com>
+
+ * config/aarch64/aarch64-cores.def: Use the Exynos M1 cost model.
+ * config/aarch64/aarch64.c (exynosm1_addrcost_table): New variable.
+ (exynosm1_regmove_cost): Likewise.
+ (exynosm1_vector_cost): Likewise.
+ (exynosm1_tunings): Likewise.
+ * config/arm/aarch-cost-tables.h (exynosm1_extra_costs): Likewise.
+ * config/arm/arm.c (arm_exynos_m1_tune): Likewise.
+
+2015-12-03 Alan Lawrence <alan.lawrence@arm.com>
+ Richard Biener <richard.guenther@gmail.com>
+
+ * cfgexpand.c (pass_expand::execute): Replace call to
+ redirect_edge_var_map_destroy with redirect_edge_var_map_empty.
+ * tree-ssa.c (delete_tree_ssa): Likewise.
+ * function.c (set_cfun): Call redirect_edge_var_map_empty.
+ * passes.c (execute_one_ipa_transform_pass, execute_one_pass): Likewise.
+ * tree-ssa.h (redirect_edge_var_map_destroy): Remove.
+ (redirect_edge_var_map_empty): New.
+ * tree-ssa.c (redirect_edge_var_map_destroy): Remove.
+ (redirect_edge_var_map_empty): New.
+
+2015-12-03 Jeff Law <law@redhat.com>
+
+ PR tree-optimization/68599
+ * loop-init.c (rtl_loop_init): Set LOOPS_HAVE_RECORDED_EXITS
+ in call to loop_optimizer_init.
+ * loop-iv.c (get_simple_loop_desc): Only allow unsafe loop
+ optimization to drop the assumptions/infinite notations if
+ the loop has a single exit.
+
+2015-12-03 Richard Sandiford <richard.sandiford@arm.com>
+
+ * doc/md.texi (vec_load_lanes@var{m}@var{n}): Document that
+ the pattern cannot FAIL.
+ (vec_store_lanes@var{m}@var{n}): Likewise.
+ (maskload@var{m}@var{n}): Likewise.
+ (maskstore@var{m}@var{n}): Likewise. Fix a cut-&-paste error
+ in the name of the pattern.
+ (rsqrt@var{m}2): Document that mode m must be a scalar or vector
+ floating-point mode and that all operands have that mode.
+ (fmin@var{m}3, fmax@var{m}3): Likewise. Document that the
+ pattern cannot FAIL.
+ (sqrt@var{m}2): Document that mode m must be a scalar or vector
+ floating-point mode, that all operands have that mode, and that
+ the patterns cannot FAIL. Remove previous documentation referring
+ to @code{double} and @code{float}.
+ (fmod@var{m}3, remainder@var{m}3, cos@var{m}2, sin@var{m}2)
+ (sincos@var{m}3, log@var{m}2, pow@var{m}3, atan2@var{m}3)
+ (copysign@var{m}3): Likewise.
+ (exp@var{m}2): Likewise. Explicitly state the base.
+ (floor@var{m}2): As for sqrt@var{m}2, but also specify the operands.
+ (btrunc@var{m}2, rint@var{m}2): Likewise.
+ (round@var{m}2): Likewise. Fix incorrect description of rounding
+ effect.
+ (ceil@var{m}2): As for round@var{m}2.
+ (nearbyint@var{m}2): As for floor@var{m}2, but also mention that
+ the instruction must not raise an inexact condition.
+ (scalb@var{m}3): Document previously-undocumented pattern
+ (ldexp@var{m}3, tan@var{m}2, asin@var{m}2, acos@var{m}2)
+ (atan@var{m}2, expm1@var{m}2, exp10@var{m}2, exp2@var{m}2)
+ (log1p@var{m}2, log10@var{m}2, log2@var{m}2, logb@var{m}2)
+ (significand@var{m}2): Likewise.
+ (ffs@var{m}2): Fix the description of the modes, so that operand 1 has
+ mode m and operand 0 is defined more freely. Document that @var{m}
+ can be a scalar or vector integer mode and that the pattern is not
+ allowed to FAIL.
+ (clz@var{m}2, ctz@var{m}2, popcount@var{m}2, parity@var{m}2): Likewise.
+ (clrsb@var{m}2): Likewise, except that the description of the
+ mode was missing in this case.
+
+2015-12-03 Richard Sandiford <richard.sandiford@arm.com>
+
+ * internal-fn.def (RSQRT): New function.
+ * optabs.def (rsqrt_optab): New optab.
+ * doc/md.texi (rsqrtM2): Document.
+ * target.def (builtin_reciprocal): Replace gcall argument with
+ a function decl. Restrict hook to machine functions.
+ * doc/tm.texi: Regenerate.
+ * targhooks.h (default_builtin_reciprocal): Update prototype.
+ * targhooks.c (default_builtin_reciprocal): Likewise.
+ * tree-ssa-math-opts.c: Include internal-fn.h.
+ (internal_fn_reciprocal): New function.
+ (pass_cse_reciprocals::execute): Call it, and build a call to an
+ internal function on success. Only call targetm.builtin_reciprocal
+ for machine functions.
+ * config/aarch64/aarch64-protos.h (aarch64_builtin_rsqrt): Remove
+ second argument.
+ * config/aarch64/aarch64-builtins.c (aarch64_expand_builtin_rsqrt):
+ Rename aarch64_rsqrt_<mode>2 to rsqrt<mode>2.
+ (aarch64_builtin_rsqrt): Remove md_fn argument and only handle
+ machine functions.
+ * config/aarch64/aarch64.c (use_rsqrt_p): New function.
+ (aarch64_builtin_reciprocal): Replace gcall argument with a
+ function decl. Use use_rsqrt_p. Remove optimize_size check.
+ Only handle machine functions. Update call to aarch64_builtin_rsqrt.
+ (aarch64_optab_supported_p): New function.
+ (TARGET_OPTAB_SUPPORTED_P): Define.
+ * config/aarch64/aarch64-simd.md (aarch64_rsqrt_<mode>2): Rename to...
+ (rsqrt<mode>2): ...this.
+ * config/i386/i386.c (use_rsqrt_p): New function.
+ (ix86_builtin_reciprocal): Replace gcall argument with a
+ function decl. Use use_rsqrt_p. Remove optimize_insn_for_size_p
+ check. Only handle machine functions.
+ (ix86_optab_supported_p): Handle rsqrt_optab.
+ * config/rs6000/rs6000.c (TARGET_OPTAB_SUPPORTED_P): Define.
+ (rs6000_builtin_reciprocal): Replace gcall argument with a
+ function decl. Remove optimize_insn_for_size_p check.
+ Only handle machine functions.
+ (rs6000_optab_supported_p): New function.
+
+2015-12-03 Bernd Schmidt <bschmidt@redhat.com>
+
+ PR target/68471
+ PR target/68472
+ * config/i386/i386.c (ix86_mitigate_rop): Don't call
+ compute_bb_for_insn again. Call df_insn_rescan_all.
+ * config/i386/i386.md (set_got_rex64): Override modrm_class.
+
+ * regrename.c (build_def_use): Ignore stack regs if regstack_completed.
+
+2015-12-03 Nathan Sidwell <nathan@acm.org>
+
+ * config/nvptx/nvptx-protos.h (npvptx_section_from_addr_space): Delete.
+ * config/nvptx/nvptx.c (enum nvptx_data_area): New.
+ (SYMBOL_DATA_AREA, SET_SYMBOL_DATA_AREA): New defines.
+ (nvptx_option_override): Set data ares for worker vars.
+ (nvptx_addr_space_from_sym): Delete.
+ (nvptx_encode_section_info): New.
+ (section_for_sym, section_for_decl): New.
+ (nvptx_maybe_convert_symbolic_operand): Get data area from symbol
+ flags,
+ (nvptx_section_from_addr_space): Delete.
+ (nvptx_section_for_decl): Delete.
+ (nvptx_output_aligned, nvptx_declare_object_name,
+ nvptx_assemble_undefined_decl): Use section_for_decl, remove
+ unnecessary checks.
+ (nvptx_print_operand): Add 'D', adjust 'A'.
+ (nvptx_expand_worker_addr): Adjust unspec generation.
+ (TARGET_ENCODE_SECTION_INFO): Override.
+ * config/nvptx/nvptx.h (ADDR_SPACE_GLOBAL, ADDR_SPACE_SHARED,
+ ADDR_SPACE_CONST, ADDR_SPACE_LOCAL, ADDR_SPACE_PARAM): Delete.
+ * config/nvptx/nvptx.md (UNSPEC_FROM_GLOBAL, UNSPEC_FROM_LOCAL,
+ UNSPEC_FROM_PARAM, UNSPEC_FROM_SHARED, UNSPEC_FROM_CONST,
+ UNSPEC_TO_GLOBAL, UNSPEC_TO_LOCAL, UNSPEC_TO_PARAM,
+ UNSPEC_TO_SHARED, UNSPEC_TO_CONST): Delete.
+ (UNSPEC_TO_GENERIC): New.
+ (nvptx_register_or_symbolic_operand): Delete.
+ (cvt_code, cvt_name, cvt_str): Delete.
+ (convaddr_<cvt_name><mode> [P]): Delete.
+ (convaddr_<mode> [P]): New.
+
+2015-12-03 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
+
+ PR rtl-optimization/68624
+ * ifcvt.c (noce_try_cmove_arith): Check clobbers of temp regs in both
+ blocks if they exist and simplify the logic choosing the order to emit
+ them in.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/66051
+ * tree-vect-slp.c (vect_build_slp_tree_1): Remove restriction
+ on load group size. Do not pass in vectorization_factor.
+ (vect_transform_slp_perm_load): Do not require any permute support.
+ (vect_build_slp_tree): Do not pass in vectorization factor.
+ (vect_analyze_slp_instance): Do not compute vectorization
+ factor estimate. Use vector size instead of vectorization factor
+ estimate to split store groups for BB vectorization.
+
+2015-12-03 Ilya Enkovich <enkovich.gnu@gmail.com>
+
+ * cfgexpand.c (expand_gimple_stmt_1): Return statement with
+ DECL as return value is allowed to have NULL bounds.
+
+2015-12-03 Tom de Vries <tom@codesourcery.com>
+
+ * graphite-isl-ast-to-gimple.c (binary_op_to_tree)
+ (gcc_expression_from_isl_expr_op): Guard isl_ast_op_zdiv_r usage with
+ HAVE_ISL_OPTIONS_SET_SCHEDULE_SERIALIZE_SCCS.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/67800
+ PR tree-optimization/68333
+ * tree-vect-patterns.c (vect_recog_dot_prod_pattern): Restore
+ restriction to reduction contexts but allow SLP reductions as well.
+ (vect_recog_sad_pattern): Likewise.
+ (vect_recog_widen_sum_pattern): Likewise.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68639
+ * tree-vect-data-refs.c (dr_group_sort_cmp): Split groups
+ belonging to different loops.
+ (vect_analyze_data_ref_accesses): Likewise.
+
+2015-12-02 Kirill Yukhin <kirill.yukhin@intel.com>
+
+ * config/i386/sse.md (define_insn "vec_extract_hi_<mode>_maskm"):
+ Remove "prefix_extra".
+ (define_insn "vec_extract_hi_<mode>_mask"): New.
+ (define_insn "vec_extract_hi_<mode>"): Remove masking.
+
+2015-12-02 Jan Hubicka <hubicka@ucw.cz>
+
+ * ipa-pure-const.c (ignore_edge_for_pure_const): New function.
+ (propagate_pure_const): Use it; fix comments and optimize loops.
+
+2015-12-02 Jan Hubicka <hubicka@ucw.cz>
+
+ * ipa-pure-const.c (ignore_edge): Rename to ...
+ (ignore_edge_for_nothrow) ... this one; also ignore eges to
+ interposable functions or ones that can not throw.
+ (propagate_nothrow): Fix handling of availability.
+
+2015-12-02 Jan Hubicka <hubicka@ucw.cz>
+
+ PR ipa/68184
+ * cgraphunit.c (cgraph_node::analyze): Set can_throw_external.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * graphite-isl-ast-to-gimple.c (binary_op_to_tree): Handle isl_ast_op_zdiv_r.
+ (gcc_expression_from_isl_expr_op): Same.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * graphite-isl-ast-to-gimple.c (copy_bb_and_scalar_dependences): Check
+ that insertion point is still in the region.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ PR tree-optimization/68550
+ * graphite-isl-ast-to-gimple.c (copy_loop_phi_nodes): Add dump.
+ (copy_bb_and_scalar_dependences): Do not code generate loop peeled
+ statements.
+
+2015-12-02 Ulrich Weigand <Ulrich.Weigand@de.ibm.com>
+
+ * configure.ac: Check assembler support for R_PPC64_ENTRY relocation.
+ * configure: Regenerate.
+ * config.in: Regenerate.
+ * config/rs6000/rs6000.c (rs6000_global_entry_point_needed_p): New
+ function.
+ (rs6000_output_function_prologue): Use it instead of checking
+ cfun->machine->r2_setup_needed. Use internal labels instead of
+ GNU as local label extension. Handle ELFv2 large code model.
+ (rs6000_output_mi_thunk): Do not set cfun->machine->r2_setup_needed.
+ (rs6000_elf_declare_function_name): Handle ELFv2 large code model.
+
+2015-12-02 Jakub Jelinek <jakub@redhat.com>
+
+ PR target/68647
+ * optabs.c (expand_doubleword_popcount, expand_doubleword_parity):
+ New functions.
+ (expand_unop): Use them.
+
+2015-12-02 Marek Polacek <polacek@redhat.com>
+
+ PR c++/68653
+ * tree.c (nonnull_arg_p): Allow OFFSET_TYPE.
+
+2015-12-02 Nathan Sidwell <nathan@acm.org>
+
+ * config/nvptx/nvptx.c (enum nvptx_shuffle_kind): New. Absorb
+ SHUFFLE defines.
+ (nvptx_gen_shuffle, nvptx_print_operand, nvptx_expand_shuffle): Adjust.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * graphite-dependences.c (scop_get_reads): Add extra dumps.
+ (scop_get_must_writes): Same.
+ (scop_get_may_writes): Same.
+ (compute_deps): Same.
+ * graphite-sese-to-poly.c (bounds_are_valid): New.
+ (pdr_add_data_dimensions): Call bounds_are_valid.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * common.opt (flag_loop_optimize_isl): Renamed flag_loop_nest_optimize.
+ * graphite-poly.c (apply_poly_transforms): Same.
+ * graphite.c (gate_graphite_transforms): Same.
+ * toplev.c (process_options): Same.
+
+2015-12-02 Eric Botcazou <ebotcazou@adacore.com>
+
+ * config/mips/mips.c (mips_emit_probe_stack_range): Adjust.
+ (mips_output_probe_stack_range): Rotate the loop and simplify.
+
+2015-12-02 David Sherwood <david.sherwood@arm.com>
+
+ * config/aarch64/aarch64.md: New pattern.
+ * config/aarch64/aarch64-simd.md: Likewise.
+ * config/aarch64/iterators.md: New unspecs, iterators.
+
+2015-12-02 Pierre-Marie de Rodat <derodat@adacore.com>
+
+ * dwarf2out.c (dwar2out_var_location): In addition to notes,
+ process indirect calls whose target is compile-time known.
+ Enhance pattern matching to get the SYMBOL_REF they embed.
+ (gen_subprogram_die): Handle such calls.
+ * final.c (final_scan_insn): For call instructions, invoke the
+ var_location debug hook only after the call has been emitted.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * gimplify.c (enum gimplify_omp_var_data): Add enum value
+ GOVD_MAP_FORCE.
+ (oacc_default_clause): Fix default for scalars in oacc kernels.
+ (gimplify_adjust_omp_clauses_1): Handle GOVD_MAP_FORCE.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * omp-low.c (install_var_field, scan_sharing_clauses): Add and handle
+ parameter base_pointers_restrict.
+ (omp_target_base_pointers_restrict_p): New function.
+ (scan_omp_target): Call scan_sharing_clauses with base_pointers_restrict
+ arg.
+
+2015-12-02 Nathan Sidwell <nathan@acm.org>
+
+ * config/nvptx/nvptx-protos.h (nvptx_output_mov_insn): Declare.
+ (nvptx_underlying_object_mode): Delete.
+ * config/nvptx/nvptx.c (nvptx_underlying_object_mode): Delete.
+ (output_reg): New.
+ (nvptx_declare_function_name): Use output_reg. Remove punning
+ buffer.
+ (nvptx_output_mov_insn): New.
+ (nvptx_print_operand): Separate SUBREG handling, remove 'f' case,
+ Use output_reg. Merge 't' and 'u' handling.
+ * config/nvptx/nvptx.h (NVPTX_PUNNING_BUFFER_REGNUM): Delete.
+ (struct machine_function): Remvoe punning_buffer_size.
+ (REGISTER_NAMES): Remove %punbuffer.
+ * config/nvptx/nvptx.md (UNSPEC_CPLX_LOWPART,
+ UNSPEC_CPLX_HIGHPART): Delete.
+ (*mov<mode>_insn [QHSDIM): Remove unnecessary constraints, use
+ nvptx_output_mov_insn.
+ (*mov<mode>_insn [SDFM): Reorder constraints to match integer
+ moc. Use nvptx_output_mov_insn.
+ (highpartscsf2, set_highpartscsf2, lowpartscsf2,
+ set_lowpartscsf2): Delete.
+ (mov<mode> [SDCM]): Delete.
+
+2015-12-02 Richard Biener <rguenther@suse.de>
+
+ * tree.h (tree_invariant_p): Declare.
+ * tree.c (tree_invariant_p): Export.
+ * genmatch.c (dt_simplify::gen_1): For GENERIC code-gen never
+ create SAVE_EXPRs but reject patterns if we would need to.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * tree-ssa-structalias.c (find_func_aliases_for_builtin_call)
+ (find_func_clobbers, ipa_pta_execute): Handle BUILT_IN_GOACC_PARALLEL.
+
+>>>>>>> .r231221
+2015-12-02 Segher Boessenkool <segher@kernel.crashing.org>
+
+ * config/rs6000/rs6000.md (cstore_si_as_di): New expander.
+ (cstore<mode>4): Use it.
+
+2015-12-02 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68625
+ * tree-cfgcleanup.c (cleanup_tree_cfg_bb): Do not call
+ cleanup_control_flow_bb.
+ (cleanup_tree_cfg_1): First perform cleanup_control_flow_bb
+ on all BBs, then cleanup_tree_cfg_bb and finally iterate
+ over the worklist doing both.
+
+2015-12-02 Richard Sandiford <richard.sandiford@arm.com>
+
+ PR tree-optimization/68432
+ * coretypes.h (optimization_type): New enum.
+ * doc/tm.texi.in (TARGET_OPTAB_SUPPORTED_P): New hook.
+ * doc/tm.texi: Regenerate.
+ * target.def (optab_supported_p): New hook.
+ * targhooks.h (default_optab_supported_p): Declare.
+ * targhooks.c (default_optab_supported_p): New function.
+ * predict.h (function_optimization_type): Declare.
+ (bb_optimization_type): Likewise.
+ * predict.c (function_optimization_type): New function.
+ (bb_optimization_type): Likewise.
+ * optabs-query.h (convert_optab_handler): Define an overload
+ that takes an optimization type.
+ (direct_optab_handler): Likewise.
+ * optabs-query.c (convert_optab_handler): Likewise.
+ (direct_optab_handler): Likewise.
+ * internal-fn.h (direct_internal_fn_supported_p): Take an
+ optimization_type argument.
+ * internal-fn.c (direct_optab_supported_p): Likewise.
+ (multi_vector_optab_supported_p): Likewise.
+ (direct_internal_fn_supported_p): Likewise.
+ * builtins.c (replacement_internal_fn): Update call to
+ direct_internal_fn_supported_p.
+ * gimple-match-head.c (build_call_internal): Likewise.
+ * tree-vect-patterns.c (vect_recog_pow_pattern): Likewise.
+ * tree-vect-stmts.c (vectorizable_internal_function): Likewise.
+ * tree.c (maybe_build_call_expr_loc): Likewise.
+ * config/i386/i386.c (ix86_optab_supported_p): New function.
+ (TARGET_OPTAB_SUPPORTED_P): Define.
+ * config/i386/i386.md (asinxf2): Remove optimize_insn_for_size_p check.
+ (asin<mode>2, acosxf2, acos<mode>2, log1pxf2, log1p<mode>2)
+ (expNcorexf3, expxf2, exp<mode>2, exp10xf2, exp10<mode>2, exp2xf2)
+ (exp2<mode>2, expm1xf2, expm1<mode>2, ldexpxf3, ldexp<mode>3)
+ (scalbxf3, scalb<mode>3, rint<mode>2, round<mode>2)
+ (<rounding_insn>xf2, <rounding_insn><mode>2): Likewise.
+
+2015-12-02 Richard Sandiford <richard.sandiford@arm.com>
+
+ * Makefile.in (GENSUPPORT_H): New macro.
+ (build/gensupport.o, build/read-rtl.o, build/genattr.o)
+ (build/genattr-common.o, build/genattrtab.o, build/genautomata.o)
+ (build/gencodes.o, build/genconditions.o, build/genconfig.o)
+ (build/genconstants.o, build/genextract.o, build/genflags.o)
+ (build/gentarget-def.o): Use it.
+ (build/genemit.o): Likewise. Depend on internal-fn.def.
+ * genopinit.c: Move block comment to optabs.def.
+ (optab_tag, optab_def): Move to gensupport.h
+ (pattern): Likewise, renaming to optab_pattern.
+ (match_pattern): Move to gensupport.c
+ (gen_insn): Use find_optab.
+ (patterns, pattern_cmp): Replace pattern with optab_pattern.
+ (main): Likewise. Use num_optabs.
+ * optabs.def: Add comment that was previously in genopinit.c.
+ * gensupport.h (optab_tag): Moved from genopinit.c
+ (optab_def): Likewise, expanding commentary.
+ (optab_pattern): Likewise, after renaming from pattern.
+ (optabs, num_optabs, find_optab): Declare.
+ * gensupport.c (optabs): Moved from genopinit.c.
+ (num_optabs): New variable.
+ (match_pattern): Moved from genopinit.c.
+ (find_optab): New function, extracted from genopinit.c:gen_insn.
+ * genemit.c (nofail_optabs): New variable.
+ (emit_c_code): New function.
+ (gen_expand): Check whether the instruction is an optab that isn't
+ allowed to fail. Call emit_c_code.
+ (gen_split): Call emit_c_code here too.
+ (main): Initialize nofail_optabs. Don't emit FAIL and DONE here.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/predicates.md (const_mask_operand): New predicate.
+ * config/s390/s390-builtins.def: Set a smaller bitmask for a few builtins.
+ * config/s390/vector.md: Change predicate from immediate_operand
+ to either const_int_operand or const_mask_operand. Add special
+ insn conditions on patterns which have to exclude certain values.
+ * config/s390/vx-builtins.md: Likewise.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/vector.md ("*vec_set<mode>"): Change shift count
+ mode from DI to SI.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/s390-builtin-types.def: New builtin types added.
+ * config/s390/s390-builtins.def: Add s390_vec_splat_* definitions.
+ * config/s390/s390.c (s390_expand_builtin): Always truncate
+ constants to the mode in the pattern.
+ * config/s390/vecintrin.h: Let the vec_splat_* macros point to the
+ respective builtin __builtin_s390_vec_splat_*.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/s390-builtin-types.def: Sort builtin types.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/s390-c.c (s390_get_vstring_flags): Invert the
+ condition for the RT flag.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/constraints.md ("jKK"): New constraint.
+ * config/s390/s390.c (tm-constrs.h): Include for
+ satisfies_constraint_*.
+ (s390_legitimate_constant_p): Allow jKK constants. Use
+ satisfies_constraint_* also for the others.
+ (legitimate_reload_vector_constant_p): Likewise.
+ (print_operand): Allow h output modifier on vectors.
+ * config/s390/vector.md ("mov<mode>"): Add vrepi.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/vector.md ("*vec_splats<mode>"): Fix constraint
+ latter I->K.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * config/s390/s390.md ("bswap<mode>2"): Add support for strv and
+ strvg.
+ ("bswaphi2"): New pattern.
+ New splitter for HI reg-reg bswap.
+
+2015-11-27 Jiri Engelthaler <engycz@gmail.com>
+
+ PR driver/68029
+ * opts-common.c (prune_options): Don't ignore -fdiagnostics-color
+ if it is the first parameter.
+
+2015-12-01 Richard Sandiford <richard.sandiford@arm.com>
+
+ PR tree-optimization/68577
+ * tree-vect-stmts.c (simple_integer_narrowing): New function.
+ (vectorizable_call): Restrict internal function handling
+ to NONE and NARROW cases, using simple_integer_narrowing
+ to test for the latter. Add cost of narrowing operation
+ and insert it where necessary.
+
+2015-12-01 Andreas Tobler <andreast@gcc.gnu.org>
+
+ * config/rs6000/freebsd64.h (ELFv2_ABI_CHECK): Add new macro.
+ (SUBSUBTARGET_OVERRIDE_OPTIONS): Use it to decide whether to set
+ rs6000_current_abi to ABI_AIX or ABI_ELFv2.
+
+2015-12-01 Nathan Sidwell <nathan@acm.org>
+
+ * config/nvptx/nvptx-protos.h (nvptx_output_aligned_decl): Declare.
+ * config/nvptx/nvptx.h (ASM_OUTPUT_ALIGNED_DECL_COMMON,
+ ASM_OUTPUT_ALIGNED_DECL_LOCAL): Forward to nvptx_output_aligned_decl.
+ * config/nvptx/nvptx.c (write_fn_marker, write_var_marker): New.
+ (write_fn_proto, write_fn_proto_from_insn): Call write_fn_marker.
+ (init_output_initializer): Call write_var_marker.
+ (nvptx_output_aligned_decl): New.
+ (nvptx_assemble_undefined_decl, nvptx_file_end): Call write_var_marker.
+
+2015-12-01 Jan Hubicka <hubicka@ucw.cz>
+
+ * c-common.c (parse_optimize_options): Do not silently ignore
+ -fstrict-aliasing changes.
+
+2015-12-01 Jan Hubicka <hubicka@ucw.cz>
+
+ * lto-streamer-out.c (hash_tree): Do not stream TYPE_ALIAS_SET.
+ * tree-streamer-out.c (pack_ts_type_common_value_fields): Do not
+ stream TYPE_ALIAS_SET.
+ * tree-streamer-in.c (unpack_ts_type_common_value_fields): Do not
+ stream TYPE_ALIAS_SET.
+
+2015-12-01 Nathan Sidwell <nathan@acm.org>
+
+ * config/nvptx/nvptx.c (nvptx_function_arg_advance): Don't
+ consider mode.
+
+2015-12-01 Bill Schmidt <wschmidt@linux.vnet.ibm.com>
+
+ * config/rs6000/rs6000.c (const_load_sequence_p): Handle extra
+ indirection for large and small code models.
+ (adjust_vperm): Likewise.
+
+2015-12-01 Julian Brown <julian@codesourcery.com>
+ Cesar Philippidis <cesar@codesourcery.com>
+ James Norris <James_Norris@mentor.com>
+
+ * gimple-pretty-print.c (dump_gimple_omp_target): Add host_data
+ support.
+ * gimple.h (gf_mask): Add GF_OMP_TARGET_KIND_OACC_HOST_DATA.
+ (is_gimple_omp_oacc): Add support for above.
+ * gimplify.c (omp_region_type): Add ORT_ACC_HOST_DATA.
+ (omp_notice_variable): Diagnose undefined implicit uses of
+ use_device variables in offloaded regions.
+ (gimplify_scan_omp_clauses): Add host_data, use_device
+ support. Diagnose undefined mapping of use_device variables in
+ OpenACC clauses.
+ (gimplify_omp_workshare): Add host_data support.
+ (gimplify_expr): Likewise.
+ * omp-builtins.def (BUILT_IN_GOACC_HOST_DATA): New.
+ * omp-low.c (lookup_decl_in_outer_ctx)
+ (maybe_lookup_decl_in_outer_ctx): Add optional argument to skip
+ host_data regions.
+ (scan_sharing_clauses): Support use_device.
+ (check_omp_nesting_restrictions): Support host_data.
+ (expand_omp_target): Support host_data.
+ (lower_omp_target): Skip over outer host_data regions when looking
+ up decls. Support use_device.
+ (make_gimple_omp_edges): Support host_data.
+ * tree-nested.c (convert_nonlocal_omp_clauses): Add use_device
+ clause.
+
+2015-12-01 Marek Polacek <polacek@redhat.com>
+
+ PR middle-end/68582
+ * cgraphunit.c (check_global_declaration): Only depend on TREE_THIS_VOLATILE
+ for VAR_DECLs.
+
+2015-12-01 Richard Sandiford <richard.sandiford@arm.com>
+
+ PR tree-optimization/68474
+ * tree-call-cdce.c (use_internal_fn): Protect call to
+ gen_shrink_wrap_conditions.
+
+2015-12-01 Christian Bruel <christian.bruel@st.com>
+
+ PR target/68617
+ * config/arm/arm.opt (unaligned_access): Save.
+ * config/arm/arm-c.c (__ARM_FEATURE_UNALIGNED): Conditionally define.
+ * config/arm/arm.c (arm_option_override): Move unaligned_access setting
+ (arm_option_override_internal): ... here.
+ * config/arm/arm.h (TARGET_32BIT_P): New macro.
+
+2015-12-01 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68379
+ * tree-vect-stmts.c (vectorizable_load): For BB vectorization
+ always base loads on the first used DR of a group.
+ * tree-vect-data-refs.c (vect_slp_analyze_and_verify_node_alignment):
+ Compute alignment of the first scalar element unconditionally.
+
+2015-12-01 Richard Biener <rguenther@suse.de>
+
+ PR middle-end/68590
+ * genmatch.c (struct capture_info): Add match_use_count.
+ (capture_info::walk_match): Increment match_use_count.
+ (dt_simplify::gen_1): For GENERIC, only wrap multi-use
+ replacements in a save_expr if they occur more often than
+ in the original expression.
+
+2015-12-01 Richard Biener <rguenther@suse.de>
+
+ PR ipa/68470
+ * ipa-split.c (split_function): Handle main part not returning.
+
+2015-12-01 Ilya Enkovich <enkovich.gnu@gmail.com>
+
+ PR middle-end/68595
+ * tree-vect-stmts.c (vect_init_vector): Cast boolean
+ scalars to a proper value before building a vector.
+
2015-12-01 Richard Sandiford <richard.sandiford@arm.com>
* genattrtab.c (check_attr_test): Take an attr_desc instead of
diff --git a/gcc/DATESTAMP b/gcc/DATESTAMP
index 44bd8872f44..afb984d5f67 100644
--- a/gcc/DATESTAMP
+++ b/gcc/DATESTAMP
@@ -1 +1 @@
-20151201
+20151204
diff --git a/gcc/Makefile.in b/gcc/Makefile.in
index bee28797ae7..d2d09f64f5f 100644
--- a/gcc/Makefile.in
+++ b/gcc/Makefile.in
@@ -978,6 +978,7 @@ GCC_PLUGIN_H = gcc-plugin.h highlev-plugin-common.h plugin.def \
PLUGIN_H = plugin.h $(GCC_PLUGIN_H)
PLUGIN_VERSION_H = plugin-version.h configargs.h
CONTEXT_H = context.h
+GENSUPPORT_H = gensupport.h read-md.h optabs.def
#
# Now figure out from those variables how to compile and link.
@@ -2476,7 +2477,7 @@ build/version.o: version.c version.h \
build/errors.o : errors.c $(BCONFIG_H) $(SYSTEM_H) errors.h
build/gensupport.o: gensupport.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h \
$(GTM_H) $(RTL_BASE_H) $(OBSTACK_H) errors.h $(HASHTAB_H) \
- $(READ_MD_H) gensupport.h
+ $(READ_MD_H) $(GENSUPPORT_H)
build/ggc-none.o : ggc-none.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h \
$(GGC_H)
build/min-insn-modes.o : min-insn-modes.c $(BCONFIG_H) $(SYSTEM_H) \
@@ -2487,7 +2488,7 @@ build/read-md.o: read-md.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h \
$(HASHTAB_H) errors.h $(READ_MD_H)
build/read-rtl.o: read-rtl.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h \
$(GTM_H) $(RTL_BASE_H) $(OBSTACK_H) $(HASHTAB_H) $(READ_MD_H) \
- gensupport.h
+ $(GENSUPPORT_H)
build/rtl.o: rtl.c $(BCONFIG_H) coretypes.h $(GTM_H) $(SYSTEM_H) \
$(RTL_H) $(GGC_H) errors.h
build/vec.o : vec.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h $(VEC_H) \
@@ -2509,38 +2510,38 @@ build/gencondmd.o : \
# ...these are the programs themselves.
build/genattr.o : genattr.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/genattr-common.o : genattr-common.c $(RTL_BASE_H) $(BCONFIG_H) \
- $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/genattrtab.o : genattrtab.c $(RTL_BASE_H) $(OBSTACK_H) \
$(BCONFIG_H) $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(GGC_H) \
- $(READ_MD_H) gensupport.h $(FNMATCH_H)
+ $(READ_MD_H) $(GENSUPPORT_H) $(FNMATCH_H)
build/genautomata.o : genautomata.c $(RTL_BASE_H) $(OBSTACK_H) \
$(BCONFIG_H) $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(VEC_H) \
- $(HASHTAB_H) gensupport.h $(FNMATCH_H)
+ $(HASHTAB_H) $(GENSUPPORT_H) $(FNMATCH_H)
build/gencheck.o : gencheck.c all-tree.def $(BCONFIG_H) $(GTM_H) \
$(SYSTEM_H) coretypes.h tree.def c-family/c-common.def \
$(lang_tree_files) gimple.def
build/genchecksum.o : genchecksum.c $(BCONFIG_H) $(SYSTEM_H) $(MD5_H)
build/gencodes.o : gencodes.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h gensupport.h
+ coretypes.h $(GTM_H) errors.h $(GENSUPPORT_H)
build/genconditions.o : genconditions.c $(RTL_BASE_H) $(BCONFIG_H) \
$(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(HASHTAB_H) $(READ_MD_H) \
- gensupport.h
+ $(GENSUPPORT_H)
build/genconfig.o : genconfig.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h gensupport.h
+ coretypes.h $(GTM_H) errors.h $(GENSUPPORT_H)
build/genconstants.o : genconstants.c $(BCONFIG_H) $(SYSTEM_H) \
coretypes.h errors.h $(READ_MD_H)
build/genemit.o : genemit.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H) internal-fn.def
build/genenums.o : genenums.c $(BCONFIG_H) $(SYSTEM_H) \
coretypes.h errors.h $(READ_MD_H)
build/genextract.o : genextract.c $(RTL_BASE_H) $(BCONFIG_H) \
- $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/genflags.o : genflags.c $(RTL_BASE_H) $(OBSTACK_H) $(BCONFIG_H) \
- $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ $(SYSTEM_H) coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/gentarget-def.o : gentarget-def.c $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) $(RTL_BASE_H) errors.h $(READ_MD_H) gensupport.h \
+ coretypes.h $(GTM_H) $(RTL_BASE_H) errors.h $(READ_MD_H) $(GENSUPPORT_H) \
$(HASH_TABLE_H) target-insns.def
build/gengenrtl.o : gengenrtl.c $(BCONFIG_H) $(SYSTEM_H) rtl.def
@@ -2582,20 +2583,20 @@ build/genmddeps.o: genmddeps.c $(BCONFIG_H) $(SYSTEM_H) coretypes.h \
build/genmodes.o : genmodes.c $(BCONFIG_H) $(SYSTEM_H) errors.h \
$(HASHTAB_H) machmode.def $(extra_modes_file)
build/genopinit.o : genopinit.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h gensupport.h optabs.def
+ coretypes.h $(GTM_H) errors.h $(GENSUPPORT_H) optabs.def
build/genoutput.o : genoutput.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/genpeep.o : genpeep.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h gensupport.h toplev.h $(DIAGNOSTIC_CORE_H)
+ coretypes.h $(GTM_H) errors.h $(GENSUPPORT_H) toplev.h $(DIAGNOSTIC_CORE_H)
build/genpreds.o : genpreds.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h $(OBSTACK_H)
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H) $(OBSTACK_H)
build/genrecog.o : genrecog.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h \
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H) \
$(HASH_TABLE_H) inchash.h
build/genhooks.o : genhooks.c $(TARGET_DEF) $(C_TARGET_DEF) \
$(COMMON_TARGET_DEF) $(BCONFIG_H) $(SYSTEM_H) errors.h
build/genmddump.o : genmddump.c $(RTL_BASE_H) $(BCONFIG_H) $(SYSTEM_H) \
- coretypes.h $(GTM_H) errors.h $(READ_MD_H) gensupport.h
+ coretypes.h $(GTM_H) errors.h $(READ_MD_H) $(GENSUPPORT_H)
build/genmatch.o : genmatch.c $(BCONFIG_H) $(SYSTEM_H) \
coretypes.h errors.h $(HASH_TABLE_H) hash-map.h $(GGC_H) is-a.h \
tree.def builtins.def internal-fn.def
diff --git a/gcc/ada/ChangeLog b/gcc/ada/ChangeLog
index 11f387c34b0..84857813202 100644
--- a/gcc/ada/ChangeLog
+++ b/gcc/ada/ChangeLog
@@ -1,3 +1,9 @@
+2015-12-01 Jan Sommer <soja-lists@aries.uberspace.de>
+
+ PR ada/68169
+ * s-oscons-tmplt.c: Generate pthread constants for RTEMS
+ * s-osinte-rtems.ads: Declare pthread structs as opaque types in Ada
+
2015-12-01 Eric Botcazou <ebotcazou@adacore.com>
* gcc-interface/Makefile.in (ADA_EXCLUDE_SRCS): Reorder.
diff --git a/gcc/ada/s-oscons-tmplt.c b/gcc/ada/s-oscons-tmplt.c
index 56da9f8a5cb..d1b522d6701 100644
--- a/gcc/ada/s-oscons-tmplt.c
+++ b/gcc/ada/s-oscons-tmplt.c
@@ -157,7 +157,7 @@ pragma Style_Checks ("M32766");
# include <_types.h>
#endif
-#if defined (__linux__) || defined (__ANDROID__)
+#if defined (__linux__) || defined (__ANDROID__) || defined (__rtems__)
# include <pthread.h>
# include <signal.h>
#endif
@@ -1458,7 +1458,7 @@ CNS(CLOCK_RT_Ada, "")
#endif
#if defined (__APPLE__) || defined (__linux__) || defined (__ANDROID__) \
- || defined (DUMMY)
+ || defined (__rtems__) || defined (DUMMY)
/*
-- Sizes of pthread data types
@@ -1501,7 +1501,7 @@ CND(PTHREAD_RWLOCKATTR_SIZE, "pthread_rwlockattr_t")
CND(PTHREAD_RWLOCK_SIZE, "pthread_rwlock_t")
CND(PTHREAD_ONCE_SIZE, "pthread_once_t")
-#endif /* __APPLE__ || __linux__ || __ANDROID__ */
+#endif /* __APPLE__ || __linux__ || __ANDROID__ || __rtems__ */
/*
diff --git a/gcc/ada/s-osinte-rtems.ads b/gcc/ada/s-osinte-rtems.ads
index 8b9ae1297cd..5a143cc666a 100644
--- a/gcc/ada/s-osinte-rtems.ads
+++ b/gcc/ada/s-osinte-rtems.ads
@@ -51,6 +51,8 @@
-- It is designed to be a bottom-level (leaf) package.
with Interfaces.C;
+with System.OS_Constants;
+
package System.OS_Interface is
pragma Preelaborate;
@@ -60,6 +62,7 @@ package System.OS_Interface is
subtype rtems_id is Interfaces.C.unsigned;
subtype int is Interfaces.C.int;
+ subtype char is Interfaces.C.char;
subtype short is Interfaces.C.short;
subtype long is Interfaces.C.long;
subtype unsigned is Interfaces.C.unsigned;
@@ -68,7 +71,6 @@ package System.OS_Interface is
subtype unsigned_char is Interfaces.C.unsigned_char;
subtype plain_char is Interfaces.C.plain_char;
subtype size_t is Interfaces.C.size_t;
-
-----------
-- Errno --
-----------
@@ -76,11 +78,11 @@ package System.OS_Interface is
function errno return int;
pragma Import (C, errno, "__get_errno");
- EAGAIN : constant := 11;
- EINTR : constant := 4;
- EINVAL : constant := 22;
- ENOMEM : constant := 12;
- ETIMEDOUT : constant := 116;
+ EAGAIN : constant := System.OS_Constants.EAGAIN;
+ EINTR : constant := System.OS_Constants.EINTR;
+ EINVAL : constant := System.OS_Constants.EINVAL;
+ ENOMEM : constant := System.OS_Constants.ENOMEM;
+ ETIMEDOUT : constant := System.OS_Constants.ETIMEDOUT;
-------------
-- Signals --
@@ -448,6 +450,7 @@ package System.OS_Interface is
ss_low_priority : int;
ss_replenish_period : timespec;
ss_initial_budget : timespec;
+ sched_ss_max_repl : int;
end record;
pragma Convention (C, struct_sched_param);
@@ -621,43 +624,34 @@ private
end record;
pragma Convention (C, timespec);
- CLOCK_REALTIME : constant clockid_t := 1;
- CLOCK_MONOTONIC : constant clockid_t := 4;
+ CLOCK_REALTIME : constant clockid_t := System.OS_Constants.CLOCK_REALTIME;
+ CLOCK_MONOTONIC : constant clockid_t := System.OS_Constants.CLOCK_MONOTONIC;
+
+ subtype char_array is Interfaces.C.char_array;
type pthread_attr_t is record
- is_initialized : int;
- stackaddr : System.Address;
- stacksize : int;
- contentionscope : int;
- inheritsched : int;
- schedpolicy : int;
- schedparam : struct_sched_param;
- cputime_clocked_allowed : int;
- detatchstate : int;
+ Data : char_array (1 .. OS_Constants.PTHREAD_ATTR_SIZE);
end record;
pragma Convention (C, pthread_attr_t);
+ for pthread_attr_t'Alignment use Interfaces.C.double'Alignment;
type pthread_condattr_t is record
- flags : int;
- process_shared : int;
+ Data : char_array (1 .. OS_Constants.PTHREAD_CONDATTR_SIZE);
end record;
pragma Convention (C, pthread_condattr_t);
+ for pthread_condattr_t'Alignment use Interfaces.C.double'Alignment;
type pthread_mutexattr_t is record
- is_initialized : int;
- process_shared : int;
- prio_ceiling : int;
- protocol : int;
- mutex_type : int;
- recursive : int;
- end record;
+ Data : char_array (1 .. OS_Constants.PTHREAD_MUTEXATTR_SIZE);
+ end record;
pragma Convention (C, pthread_mutexattr_t);
+ for pthread_mutexattr_t'Alignment use Interfaces.C.double'Alignment;
type pthread_rwlockattr_t is record
- is_initialized : int;
- process_shared : int;
+ Data : char_array (1 .. OS_Constants.PTHREAD_RWLOCKATTR_SIZE);
end record;
pragma Convention (C, pthread_rwlockattr_t);
+ for pthread_rwlockattr_t'Alignment use Interfaces.C.double'Alignment;
type pthread_t is new rtems_id;
diff --git a/gcc/alias.c b/gcc/alias.c
index 9a642dde03e..66aedcef4c9 100644
--- a/gcc/alias.c
+++ b/gcc/alias.c
@@ -405,6 +405,10 @@ alias_set_subset_of (alias_set_type set1, alias_set_type set2)
{
alias_set_entry *ase2;
+ /* Disable TBAA oracle with !flag_strict_aliasing. */
+ if (!flag_strict_aliasing)
+ return true;
+
/* Everything is a subset of the "aliases everything" set. */
if (set2 == 0)
return true;
@@ -537,6 +541,9 @@ alias_sets_conflict_p (alias_set_type set1, alias_set_type set2)
int
alias_sets_must_conflict_p (alias_set_type set1, alias_set_type set2)
{
+ /* Disable TBAA oracle with !flag_strict_aliasing. */
+ if (!flag_strict_aliasing)
+ return 1;
if (set1 == 0 || set2 == 0)
{
++alias_stats.num_alias_zero;
@@ -816,10 +823,12 @@ get_alias_set (tree t)
{
alias_set_type set;
- /* If we're not doing any alias analysis, just assume everything
- aliases everything else. Also return 0 if this or its type is
- an error. */
- if (! flag_strict_aliasing || t == error_mark_node
+ /* We can not give up with -fno-strict-aliasing because we need to build
+ proper type representation for possible functions which are build with
+ -fstirct-aliasing. */
+
+ /* return 0 if this or its type is an error. */
+ if (t == error_mark_node
|| (! TYPE_P (t)
&& (TREE_TYPE (t) == 0 || TREE_TYPE (t) == error_mark_node)))
return 0;
@@ -1085,15 +1094,10 @@ get_alias_set (tree t)
alias_set_type
new_alias_set (void)
{
- if (flag_strict_aliasing)
- {
- if (alias_sets == 0)
- vec_safe_push (alias_sets, (alias_set_entry *) NULL);
- vec_safe_push (alias_sets, (alias_set_entry *) NULL);
- return alias_sets->length () - 1;
- }
- else
- return 0;
+ if (alias_sets == 0)
+ vec_safe_push (alias_sets, (alias_set_entry *) NULL);
+ vec_safe_push (alias_sets, (alias_set_entry *) NULL);
+ return alias_sets->length () - 1;
}
/* Indicate that things in SUBSET can alias things in SUPERSET, but that
diff --git a/gcc/builtins.c b/gcc/builtins.c
index df5c4930997..9d816044c73 100644
--- a/gcc/builtins.c
+++ b/gcc/builtins.c
@@ -458,6 +458,10 @@ get_pointer_alignment_1 (tree exp, unsigned int *alignp,
{
*bitposp = ptr_misalign * BITS_PER_UNIT;
*alignp = ptr_align * BITS_PER_UNIT;
+ /* Make sure to return a sensible alignment when the multiplication
+ by BITS_PER_UNIT overflowed. */
+ if (*alignp == 0)
+ *alignp = 1u << (HOST_BITS_PER_INT - 1);
/* We cannot really tell whether this result is an approximation. */
return true;
}
@@ -1962,7 +1966,8 @@ replacement_internal_fn (gcall *call)
if (ifn != IFN_LAST)
{
tree_pair types = direct_internal_fn_types (ifn, call);
- if (direct_internal_fn_supported_p (ifn, types))
+ optimization_type opt_type = bb_optimization_type (gimple_bb (call));
+ if (direct_internal_fn_supported_p (ifn, types, opt_type))
return ifn;
}
}
diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog
index 6be680a0743..a6a4fc82c03 100644
--- a/gcc/c-family/ChangeLog
+++ b/gcc/c-family/ChangeLog
@@ -1,3 +1,43 @@
+2015-12-03 Jakub Jelinek <jakub@redhat.com>
+
+ PR preprocessor/57580
+ * c-ppoutput.c (print): Change printed field to bool.
+ Move src_file last for smaller padding.
+ (init_pp_output): Set print.printed to false instead of 0.
+ (scan_translation_unit): Fix up formatting. Set print.printed
+ to true after printing something other than newline.
+ (scan_translation_unit_trad): Set print.printed to true instead of 1.
+ (maybe_print_line_1): Set print.printed to false instead of 0.
+ (print_line_1): Likewise.
+ (do_line_change): Set print.printed to true instead of 1.
+ (cb_define, dump_queued_macros, cb_include, cb_def_pragma,
+ dump_macro): Set print.printed to false after printing newline.
+
+2015-12-02 Jason Merrill <jason@redhat.com>
+
+ * c-common.c (fold_for_warn): New.
+ (warn_logical_operator, warn_tautological_cmp)
+ (check_function_arguments_recurse, maybe_warn_bool_compare): Use it.
+
+ * c-common.c (c_disable_warnings, c_enable_warnings, c_fully_fold)
+ (c_fully_fold_internal, decl_constant_value_for_optimization):
+ Move to c/c-fold.c.
+ * c-common.h: Don't declare decl_constant_value_for_optimization.
+
+2015-12-02 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/68162
+ * c-common.h (c_build_qualified_type): Add extra default
+ arguments.
+
+2015-12-01 Julian Brown <julian@codesourcery.com>
+ Cesar Philippidis <cesar@codesourcery.com>
+ James Norris <James_Norris@mentor.com>
+
+ * c-pragma.c (oacc_pragmas): Add PRAGMA_OACC_HOST_DATA.
+ * c-pragma.h (pragma_kind): Add PRAGMA_OACC_HOST_DATA.
+ (pragma_omp_clause): Add PRAGMA_OACC_CLAUSE_USE_DEVICE.
+
2015-11-30 Eric Botcazou <ebotcazou@adacore.com>
* c-ada-spec.c (print_ada_macros): Remove redundant blank line.
diff --git a/gcc/c-family/c-common.c b/gcc/c-family/c-common.c
index e1fb8af2829..a4578f3daa6 100644
--- a/gcc/c-family/c-common.c
+++ b/gcc/c-family/c-common.c
@@ -299,7 +299,6 @@ const struct fname_var_t fname_vars[] =
/* Global visibility options. */
struct visibility_flags visibility_options;
-static tree c_fully_fold_internal (tree expr, bool, bool *, bool *, bool);
static tree check_case_value (location_t, tree);
static bool check_case_bounds (location_t, tree, tree, tree *, tree *,
bool *);
@@ -1095,580 +1094,17 @@ fix_string_type (tree value)
return value;
}
-/* If DISABLE is true, stop issuing warnings. This is used when
- parsing code that we know will not be executed. This function may
- be called multiple times, and works as a stack. */
-
-static void
-c_disable_warnings (bool disable)
-{
- if (disable)
- {
- ++c_inhibit_evaluation_warnings;
- fold_defer_overflow_warnings ();
- }
-}
-
-/* If ENABLE is true, reenable issuing warnings. */
-
-static void
-c_enable_warnings (bool enable)
-{
- if (enable)
- {
- --c_inhibit_evaluation_warnings;
- fold_undefer_and_ignore_overflow_warnings ();
- }
-}
-
-/* Fully fold EXPR, an expression that was not folded (beyond integer
- constant expressions and null pointer constants) when being built
- up. If IN_INIT, this is in a static initializer and certain
- changes are made to the folding done. Clear *MAYBE_CONST if
- MAYBE_CONST is not NULL and EXPR is definitely not a constant
- expression because it contains an evaluated operator (in C99) or an
- operator outside of sizeof returning an integer constant (in C90)
- not permitted in constant expressions, or because it contains an
- evaluated arithmetic overflow. (*MAYBE_CONST should typically be
- set to true by callers before calling this function.) Return the
- folded expression. Function arguments have already been folded
- before calling this function, as have the contents of SAVE_EXPR,
- TARGET_EXPR, BIND_EXPR, VA_ARG_EXPR, OBJ_TYPE_REF and
- C_MAYBE_CONST_EXPR. */
-
-tree
-c_fully_fold (tree expr, bool in_init, bool *maybe_const)
-{
- tree ret;
- tree eptype = NULL_TREE;
- bool dummy = true;
- bool maybe_const_itself = true;
- location_t loc = EXPR_LOCATION (expr);
-
- /* This function is not relevant to C++ because C++ folds while
- parsing, and may need changes to be correct for C++ when C++
- stops folding while parsing. */
- if (c_dialect_cxx ())
- gcc_unreachable ();
-
- if (!maybe_const)
- maybe_const = &dummy;
- if (TREE_CODE (expr) == EXCESS_PRECISION_EXPR)
- {
- eptype = TREE_TYPE (expr);
- expr = TREE_OPERAND (expr, 0);
- }
- ret = c_fully_fold_internal (expr, in_init, maybe_const,
- &maybe_const_itself, false);
- if (eptype)
- ret = fold_convert_loc (loc, eptype, ret);
- *maybe_const &= maybe_const_itself;
- return ret;
-}
-
-/* Internal helper for c_fully_fold. EXPR and IN_INIT are as for
- c_fully_fold. *MAYBE_CONST_OPERANDS is cleared because of operands
- not permitted, while *MAYBE_CONST_ITSELF is cleared because of
- arithmetic overflow (for C90, *MAYBE_CONST_OPERANDS is carried from
- both evaluated and unevaluated subexpressions while
- *MAYBE_CONST_ITSELF is carried from only evaluated
- subexpressions). FOR_INT_CONST indicates if EXPR is an expression
- with integer constant operands, and if any of the operands doesn't
- get folded to an integer constant, don't fold the expression itself. */
+/* Fold X for consideration by one of the warning functions when checking
+ whether an expression has a constant value. */
static tree
-c_fully_fold_internal (tree expr, bool in_init, bool *maybe_const_operands,
- bool *maybe_const_itself, bool for_int_const)
+fold_for_warn (tree x)
{
- tree ret = expr;
- enum tree_code code = TREE_CODE (expr);
- enum tree_code_class kind = TREE_CODE_CLASS (code);
- location_t loc = EXPR_LOCATION (expr);
- tree op0, op1, op2, op3;
- tree orig_op0, orig_op1, orig_op2;
- bool op0_const = true, op1_const = true, op2_const = true;
- bool op0_const_self = true, op1_const_self = true, op2_const_self = true;
- bool nowarning = TREE_NO_WARNING (expr);
- bool unused_p;
- source_range old_range;
-
- /* This function is not relevant to C++ because C++ folds while
- parsing, and may need changes to be correct for C++ when C++
- stops folding while parsing. */
if (c_dialect_cxx ())
- gcc_unreachable ();
-
- /* Constants, declarations, statements, errors, SAVE_EXPRs and
- anything else not counted as an expression cannot usefully be
- folded further at this point. */
- if (!IS_EXPR_CODE_CLASS (kind)
- || kind == tcc_statement
- || code == SAVE_EXPR)
- return expr;
-
- if (IS_EXPR_CODE_CLASS (kind))
- old_range = EXPR_LOCATION_RANGE (expr);
-
- /* Operands of variable-length expressions (function calls) have
- already been folded, as have __builtin_* function calls, and such
- expressions cannot occur in constant expressions. */
- if (kind == tcc_vl_exp)
- {
- *maybe_const_operands = false;
- ret = fold (expr);
- goto out;
- }
-
- if (code == C_MAYBE_CONST_EXPR)
- {
- tree pre = C_MAYBE_CONST_EXPR_PRE (expr);
- tree inner = C_MAYBE_CONST_EXPR_EXPR (expr);
- if (C_MAYBE_CONST_EXPR_NON_CONST (expr))
- *maybe_const_operands = false;
- if (C_MAYBE_CONST_EXPR_INT_OPERANDS (expr))
- {
- *maybe_const_itself = false;
- inner = c_fully_fold_internal (inner, in_init, maybe_const_operands,
- maybe_const_itself, true);
- }
- if (pre && !in_init)
- ret = build2 (COMPOUND_EXPR, TREE_TYPE (expr), pre, inner);
- else
- ret = inner;
- goto out;
- }
-
- /* Assignment, increment, decrement, function call and comma
- operators, and statement expressions, cannot occur in constant
- expressions if evaluated / outside of sizeof. (Function calls
- were handled above, though VA_ARG_EXPR is treated like a function
- call here, and statement expressions are handled through
- C_MAYBE_CONST_EXPR to avoid folding inside them.) */
- switch (code)
- {
- case MODIFY_EXPR:
- case PREDECREMENT_EXPR:
- case PREINCREMENT_EXPR:
- case POSTDECREMENT_EXPR:
- case POSTINCREMENT_EXPR:
- case COMPOUND_EXPR:
- *maybe_const_operands = false;
- break;
-
- case VA_ARG_EXPR:
- case TARGET_EXPR:
- case BIND_EXPR:
- case OBJ_TYPE_REF:
- *maybe_const_operands = false;
- ret = fold (expr);
- goto out;
-
- default:
- break;
- }
-
- /* Fold individual tree codes as appropriate. */
- switch (code)
- {
- case COMPOUND_LITERAL_EXPR:
- /* Any non-constancy will have been marked in a containing
- C_MAYBE_CONST_EXPR; there is no more folding to do here. */
- goto out;
-
- case COMPONENT_REF:
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- op1 = TREE_OPERAND (expr, 1);
- op2 = TREE_OPERAND (expr, 2);
- op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op0);
- if (op0 != orig_op0)
- ret = build3 (COMPONENT_REF, TREE_TYPE (expr), op0, op1, op2);
- if (ret != expr)
- {
- TREE_READONLY (ret) = TREE_READONLY (expr);
- TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
- }
- goto out;
-
- case ARRAY_REF:
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- orig_op1 = op1 = TREE_OPERAND (expr, 1);
- op2 = TREE_OPERAND (expr, 2);
- op3 = TREE_OPERAND (expr, 3);
- op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op0);
- op1 = c_fully_fold_internal (op1, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op1);
- op1 = decl_constant_value_for_optimization (op1);
- if (op0 != orig_op0 || op1 != orig_op1)
- ret = build4 (ARRAY_REF, TREE_TYPE (expr), op0, op1, op2, op3);
- if (ret != expr)
- {
- TREE_READONLY (ret) = TREE_READONLY (expr);
- TREE_SIDE_EFFECTS (ret) = TREE_SIDE_EFFECTS (expr);
- TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
- }
- ret = fold (ret);
- goto out;
-
- case COMPOUND_EXPR:
- case MODIFY_EXPR:
- case PREDECREMENT_EXPR:
- case PREINCREMENT_EXPR:
- case POSTDECREMENT_EXPR:
- case POSTINCREMENT_EXPR:
- case PLUS_EXPR:
- case MINUS_EXPR:
- case MULT_EXPR:
- case POINTER_PLUS_EXPR:
- case TRUNC_DIV_EXPR:
- case CEIL_DIV_EXPR:
- case FLOOR_DIV_EXPR:
- case TRUNC_MOD_EXPR:
- case RDIV_EXPR:
- case EXACT_DIV_EXPR:
- case LSHIFT_EXPR:
- case RSHIFT_EXPR:
- case BIT_IOR_EXPR:
- case BIT_XOR_EXPR:
- case BIT_AND_EXPR:
- case LT_EXPR:
- case LE_EXPR:
- case GT_EXPR:
- case GE_EXPR:
- case EQ_EXPR:
- case NE_EXPR:
- case COMPLEX_EXPR:
- case TRUTH_AND_EXPR:
- case TRUTH_OR_EXPR:
- case TRUTH_XOR_EXPR:
- case UNORDERED_EXPR:
- case ORDERED_EXPR:
- case UNLT_EXPR:
- case UNLE_EXPR:
- case UNGT_EXPR:
- case UNGE_EXPR:
- case UNEQ_EXPR:
- /* Binary operations evaluating both arguments (increment and
- decrement are binary internally in GCC). */
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- orig_op1 = op1 = TREE_OPERAND (expr, 1);
- op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op0);
- if (code != MODIFY_EXPR
- && code != PREDECREMENT_EXPR
- && code != PREINCREMENT_EXPR
- && code != POSTDECREMENT_EXPR
- && code != POSTINCREMENT_EXPR)
- op0 = decl_constant_value_for_optimization (op0);
- /* The RHS of a MODIFY_EXPR was fully folded when building that
- expression for the sake of conversion warnings. */
- if (code != MODIFY_EXPR)
- op1 = c_fully_fold_internal (op1, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op1);
- op1 = decl_constant_value_for_optimization (op1);
-
- if (for_int_const && (TREE_CODE (op0) != INTEGER_CST
- || TREE_CODE (op1) != INTEGER_CST))
- goto out;
-
- if (op0 != orig_op0 || op1 != orig_op1 || in_init)
- ret = in_init
- ? fold_build2_initializer_loc (loc, code, TREE_TYPE (expr), op0, op1)
- : fold_build2_loc (loc, code, TREE_TYPE (expr), op0, op1);
- else
- ret = fold (expr);
- if (TREE_OVERFLOW_P (ret)
- && !TREE_OVERFLOW_P (op0)
- && !TREE_OVERFLOW_P (op1))
- overflow_warning (EXPR_LOC_OR_LOC (expr, input_location), ret);
- if (code == LSHIFT_EXPR
- && TREE_CODE (orig_op0) != INTEGER_CST
- && TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
- && TREE_CODE (op0) == INTEGER_CST
- && c_inhibit_evaluation_warnings == 0
- && tree_int_cst_sgn (op0) < 0)
- warning_at (loc, OPT_Wshift_negative_value,
- "left shift of negative value");
- if ((code == LSHIFT_EXPR || code == RSHIFT_EXPR)
- && TREE_CODE (orig_op1) != INTEGER_CST
- && TREE_CODE (op1) == INTEGER_CST
- && (TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
- || TREE_CODE (TREE_TYPE (orig_op0)) == FIXED_POINT_TYPE)
- && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE
- && c_inhibit_evaluation_warnings == 0)
- {
- if (tree_int_cst_sgn (op1) < 0)
- warning_at (loc, OPT_Wshift_count_negative,
- (code == LSHIFT_EXPR
- ? G_("left shift count is negative")
- : G_("right shift count is negative")));
- else if (compare_tree_int (op1,
- TYPE_PRECISION (TREE_TYPE (orig_op0)))
- >= 0)
- warning_at (loc, OPT_Wshift_count_overflow,
- (code == LSHIFT_EXPR
- ? G_("left shift count >= width of type")
- : G_("right shift count >= width of type")));
- }
- if (code == LSHIFT_EXPR
- /* If either OP0 has been folded to INTEGER_CST... */
- && ((TREE_CODE (orig_op0) != INTEGER_CST
- && TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
- && TREE_CODE (op0) == INTEGER_CST)
- /* ...or if OP1 has been folded to INTEGER_CST... */
- || (TREE_CODE (orig_op1) != INTEGER_CST
- && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE
- && TREE_CODE (op1) == INTEGER_CST))
- && c_inhibit_evaluation_warnings == 0)
- /* ...then maybe we can detect an overflow. */
- maybe_warn_shift_overflow (loc, op0, op1);
- if ((code == TRUNC_DIV_EXPR
- || code == CEIL_DIV_EXPR
- || code == FLOOR_DIV_EXPR
- || code == EXACT_DIV_EXPR
- || code == TRUNC_MOD_EXPR)
- && TREE_CODE (orig_op1) != INTEGER_CST
- && TREE_CODE (op1) == INTEGER_CST
- && (TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
- || TREE_CODE (TREE_TYPE (orig_op0)) == FIXED_POINT_TYPE)
- && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE)
- warn_for_div_by_zero (loc, op1);
- goto out;
-
- case INDIRECT_REF:
- case FIX_TRUNC_EXPR:
- case FLOAT_EXPR:
- CASE_CONVERT:
- case ADDR_SPACE_CONVERT_EXPR:
- case VIEW_CONVERT_EXPR:
- case NON_LVALUE_EXPR:
- case NEGATE_EXPR:
- case BIT_NOT_EXPR:
- case TRUTH_NOT_EXPR:
- case ADDR_EXPR:
- case CONJ_EXPR:
- case REALPART_EXPR:
- case IMAGPART_EXPR:
- /* Unary operations. */
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
- maybe_const_itself, for_int_const);
- STRIP_TYPE_NOPS (op0);
- if (code != ADDR_EXPR && code != REALPART_EXPR && code != IMAGPART_EXPR)
- op0 = decl_constant_value_for_optimization (op0);
-
- if (for_int_const && TREE_CODE (op0) != INTEGER_CST)
- goto out;
-
- /* ??? Cope with user tricks that amount to offsetof. The middle-end is
- not prepared to deal with them if they occur in initializers. */
- if (op0 != orig_op0
- && code == ADDR_EXPR
- && (op1 = get_base_address (op0)) != NULL_TREE
- && INDIRECT_REF_P (op1)
- && TREE_CONSTANT (TREE_OPERAND (op1, 0)))
- ret = fold_convert_loc (loc, TREE_TYPE (expr), fold_offsetof_1 (op0));
- else if (op0 != orig_op0 || in_init)
- ret = in_init
- ? fold_build1_initializer_loc (loc, code, TREE_TYPE (expr), op0)
- : fold_build1_loc (loc, code, TREE_TYPE (expr), op0);
- else
- ret = fold (expr);
- if (code == INDIRECT_REF
- && ret != expr
- && INDIRECT_REF_P (ret))
- {
- TREE_READONLY (ret) = TREE_READONLY (expr);
- TREE_SIDE_EFFECTS (ret) = TREE_SIDE_EFFECTS (expr);
- TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
- }
- switch (code)
- {
- case FIX_TRUNC_EXPR:
- case FLOAT_EXPR:
- CASE_CONVERT:
- /* Don't warn about explicit conversions. We will already
- have warned about suspect implicit conversions. */
- break;
-
- default:
- if (TREE_OVERFLOW_P (ret) && !TREE_OVERFLOW_P (op0))
- overflow_warning (EXPR_LOCATION (expr), ret);
- break;
- }
- goto out;
-
- case TRUTH_ANDIF_EXPR:
- case TRUTH_ORIF_EXPR:
- /* Binary operations not necessarily evaluating both
- arguments. */
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- orig_op1 = op1 = TREE_OPERAND (expr, 1);
- op0 = c_fully_fold_internal (op0, in_init, &op0_const, &op0_const_self,
- for_int_const);
- STRIP_TYPE_NOPS (op0);
-
- unused_p = (op0 == (code == TRUTH_ANDIF_EXPR
- ? truthvalue_false_node
- : truthvalue_true_node));
- c_disable_warnings (unused_p);
- op1 = c_fully_fold_internal (op1, in_init, &op1_const, &op1_const_self,
- for_int_const);
- STRIP_TYPE_NOPS (op1);
- c_enable_warnings (unused_p);
-
- if (for_int_const
- && (TREE_CODE (op0) != INTEGER_CST
- /* Require OP1 be an INTEGER_CST only if it's evaluated. */
- || (!unused_p && TREE_CODE (op1) != INTEGER_CST)))
- goto out;
-
- if (op0 != orig_op0 || op1 != orig_op1 || in_init)
- ret = in_init
- ? fold_build2_initializer_loc (loc, code, TREE_TYPE (expr), op0, op1)
- : fold_build2_loc (loc, code, TREE_TYPE (expr), op0, op1);
- else
- ret = fold (expr);
- *maybe_const_operands &= op0_const;
- *maybe_const_itself &= op0_const_self;
- if (!(flag_isoc99
- && op0_const
- && op0_const_self
- && (code == TRUTH_ANDIF_EXPR
- ? op0 == truthvalue_false_node
- : op0 == truthvalue_true_node)))
- *maybe_const_operands &= op1_const;
- if (!(op0_const
- && op0_const_self
- && (code == TRUTH_ANDIF_EXPR
- ? op0 == truthvalue_false_node
- : op0 == truthvalue_true_node)))
- *maybe_const_itself &= op1_const_self;
- goto out;
-
- case COND_EXPR:
- orig_op0 = op0 = TREE_OPERAND (expr, 0);
- orig_op1 = op1 = TREE_OPERAND (expr, 1);
- orig_op2 = op2 = TREE_OPERAND (expr, 2);
- op0 = c_fully_fold_internal (op0, in_init, &op0_const, &op0_const_self,
- for_int_const);
-
- STRIP_TYPE_NOPS (op0);
- c_disable_warnings (op0 == truthvalue_false_node);
- op1 = c_fully_fold_internal (op1, in_init, &op1_const, &op1_const_self,
- for_int_const);
- STRIP_TYPE_NOPS (op1);
- c_enable_warnings (op0 == truthvalue_false_node);
-
- c_disable_warnings (op0 == truthvalue_true_node);
- op2 = c_fully_fold_internal (op2, in_init, &op2_const, &op2_const_self,
- for_int_const);
- STRIP_TYPE_NOPS (op2);
- c_enable_warnings (op0 == truthvalue_true_node);
-
- if (for_int_const
- && (TREE_CODE (op0) != INTEGER_CST
- /* Only the evaluated operand must be an INTEGER_CST. */
- || (op0 == truthvalue_true_node
- ? TREE_CODE (op1) != INTEGER_CST
- : TREE_CODE (op2) != INTEGER_CST)))
- goto out;
-
- if (op0 != orig_op0 || op1 != orig_op1 || op2 != orig_op2)
- ret = fold_build3_loc (loc, code, TREE_TYPE (expr), op0, op1, op2);
- else
- ret = fold (expr);
- *maybe_const_operands &= op0_const;
- *maybe_const_itself &= op0_const_self;
- if (!(flag_isoc99
- && op0_const
- && op0_const_self
- && op0 == truthvalue_false_node))
- *maybe_const_operands &= op1_const;
- if (!(op0_const
- && op0_const_self
- && op0 == truthvalue_false_node))
- *maybe_const_itself &= op1_const_self;
- if (!(flag_isoc99
- && op0_const
- && op0_const_self
- && op0 == truthvalue_true_node))
- *maybe_const_operands &= op2_const;
- if (!(op0_const
- && op0_const_self
- && op0 == truthvalue_true_node))
- *maybe_const_itself &= op2_const_self;
- goto out;
-
- case EXCESS_PRECISION_EXPR:
- /* Each case where an operand with excess precision may be
- encountered must remove the EXCESS_PRECISION_EXPR around
- inner operands and possibly put one around the whole
- expression or possibly convert to the semantic type (which
- c_fully_fold does); we cannot tell at this stage which is
- appropriate in any particular case. */
- gcc_unreachable ();
-
- default:
- /* Various codes may appear through folding built-in functions
- and their arguments. */
- goto out;
- }
-
- out:
- /* Some folding may introduce NON_LVALUE_EXPRs; all lvalue checks
- have been done by this point, so remove them again. */
- nowarning |= TREE_NO_WARNING (ret);
- STRIP_TYPE_NOPS (ret);
- if (nowarning && !TREE_NO_WARNING (ret))
- {
- if (!CAN_HAVE_LOCATION_P (ret))
- ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
- TREE_NO_WARNING (ret) = 1;
- }
- if (ret != expr)
- {
- protected_set_expr_location (ret, loc);
- if (IS_EXPR_CODE_CLASS (kind))
- set_source_range (ret, old_range.m_start, old_range.m_finish);
- }
- return ret;
-}
-
-/* If not optimizing, EXP is not a VAR_DECL, or EXP has array type,
- return EXP. Otherwise, return either EXP or its known constant
- value (if it has one), but return EXP if EXP has mode BLKmode. ???
- Is the BLKmode test appropriate? */
-
-tree
-decl_constant_value_for_optimization (tree exp)
-{
- tree ret;
-
- /* This function is only used by C, for c_fully_fold and other
- optimization, and may not be correct for C++. */
- if (c_dialect_cxx ())
- gcc_unreachable ();
-
- if (!optimize
- || !VAR_P (exp)
- || TREE_CODE (TREE_TYPE (exp)) == ARRAY_TYPE
- || DECL_MODE (exp) == BLKmode)
- return exp;
-
- ret = decl_constant_value (exp);
- /* Avoid unwanted tree sharing between the initializer and current
- function's body where the tree can be modified e.g. by the
- gimplifier. */
- if (ret != exp && TREE_STATIC (exp))
- ret = unshare_expr (ret);
- return ret;
+ return c_fully_fold (x, /*for_init*/false, /*maybe_constp*/NULL);
+ else
+ /* The C front-end has already folded X appropriately. */
+ return x;
}
/* Print a warning if a constant expression had overflow in folding.
@@ -1784,6 +1220,9 @@ warn_logical_operator (location_t location, enum tree_code code, tree type,
programmer. That is, an expression such as op && MASK
where op should not be any boolean expression, nor a
constant, and mask seems to be a non-boolean integer constant. */
+ if (TREE_CODE (op_right) == CONST_DECL)
+ /* An enumerator counts as a constant. */
+ op_right = DECL_INITIAL (op_right);
if (!truth_value_p (code_left)
&& INTEGRAL_TYPE_P (TREE_TYPE (op_left))
&& !CONSTANT_CLASS_P (op_left)
@@ -1804,7 +1243,8 @@ warn_logical_operator (location_t location, enum tree_code code, tree type,
/* We do not warn for constants because they are typical of macro
expansions that test for features. */
- if (CONSTANT_CLASS_P (op_left) || CONSTANT_CLASS_P (op_right))
+ if (CONSTANT_CLASS_P (fold_for_warn (op_left))
+ || CONSTANT_CLASS_P (fold_for_warn (op_right)))
return;
/* This warning only makes sense with logical operands. */
@@ -1924,7 +1364,8 @@ warn_tautological_cmp (location_t loc, enum tree_code code, tree lhs, tree rhs)
/* We do not warn for constants because they are typical of macro
expansions that test for features, sizeof, and similar. */
- if (CONSTANT_CLASS_P (fold (lhs)) || CONSTANT_CLASS_P (fold (rhs)))
+ if (CONSTANT_CLASS_P (fold_for_warn (lhs))
+ || CONSTANT_CLASS_P (fold_for_warn (rhs)))
return;
/* Don't warn for e.g.
@@ -9992,7 +9433,6 @@ parse_optimize_options (tree args, bool attr_p)
bool ret = true;
unsigned opt_argc;
unsigned i;
- int saved_flag_strict_aliasing;
const char **opt_argv;
struct cl_decoded_option *decoded_options;
unsigned int decoded_options_count;
@@ -10085,8 +9525,6 @@ parse_optimize_options (tree args, bool attr_p)
for (i = 1; i < opt_argc; i++)
opt_argv[i] = (*optimize_args)[i];
- saved_flag_strict_aliasing = flag_strict_aliasing;
-
/* Now parse the options. */
decode_cmdline_options_to_array_default_mask (opt_argc, opt_argv,
&decoded_options,
@@ -10097,9 +9535,6 @@ parse_optimize_options (tree args, bool attr_p)
targetm.override_options_after_change();
- /* Don't allow changing -fstrict-aliasing. */
- flag_strict_aliasing = saved_flag_strict_aliasing;
-
optimize_args->truncate (0);
return ret;
}
@@ -10288,11 +9723,14 @@ check_function_arguments_recurse (void (*callback)
if (TREE_CODE (param) == COND_EXPR)
{
+ tree cond = fold_for_warn (TREE_OPERAND (param, 0));
/* Check both halves of the conditional expression. */
- check_function_arguments_recurse (callback, ctx,
- TREE_OPERAND (param, 1), param_num);
- check_function_arguments_recurse (callback, ctx,
- TREE_OPERAND (param, 2), param_num);
+ if (!integer_zerop (cond))
+ check_function_arguments_recurse (callback, ctx,
+ TREE_OPERAND (param, 1), param_num);
+ if (!integer_nonzerop (cond))
+ check_function_arguments_recurse (callback, ctx,
+ TREE_OPERAND (param, 2), param_num);
return;
}
@@ -12571,9 +12009,14 @@ maybe_warn_bool_compare (location_t loc, enum tree_code code, tree op0,
if (TREE_CODE_CLASS (code) != tcc_comparison)
return;
- tree cst = (TREE_CODE (op0) == INTEGER_CST)
- ? op0 : (TREE_CODE (op1) == INTEGER_CST) ? op1 : NULL_TREE;
- if (!cst)
+ tree f, cst;
+ if (f = fold_for_warn (op0),
+ TREE_CODE (f) == INTEGER_CST)
+ cst = op0 = f;
+ else if (f = fold_for_warn (op1),
+ TREE_CODE (f) == INTEGER_CST)
+ cst = op1 = f;
+ else
return;
if (!integer_zerop (cst) && !integer_onep (cst))
diff --git a/gcc/c-family/c-common.h b/gcc/c-family/c-common.h
index bad8d05e620..ef64e6b1b42 100644
--- a/gcc/c-family/c-common.h
+++ b/gcc/c-family/c-common.h
@@ -809,7 +809,6 @@ extern enum conversion_safety unsafe_conversion_p (location_t, tree, tree,
bool);
extern bool decl_with_nonnull_addr_p (const_tree);
extern tree c_fully_fold (tree, bool, bool *);
-extern tree decl_constant_value_for_optimization (tree);
extern tree c_wrap_maybe_const (tree, bool);
extern tree c_save_expr (tree);
extern tree c_common_truthvalue_conversion (location_t, tree);
@@ -866,7 +865,7 @@ extern tree pointer_int_sum (location_t, enum tree_code, tree, tree,
bool = true);
/* Add qualifiers to a type, in the fashion for C. */
-extern tree c_build_qualified_type (tree, int);
+extern tree c_build_qualified_type (tree, int, tree = NULL_TREE, size_t = 0);
/* Build tree nodes and builtin functions common to both C and C++ language
frontends. */
diff --git a/gcc/c-family/c-ppoutput.c b/gcc/c-family/c-ppoutput.c
index 9fe4aa9df0e..6aa7c1a079e 100644
--- a/gcc/c-family/c-ppoutput.c
+++ b/gcc/c-family/c-ppoutput.c
@@ -31,11 +31,11 @@ static struct
const cpp_token *prev; /* Previous token. */
const cpp_token *source; /* Source token for spacing. */
int src_line; /* Line number currently being written. */
- unsigned char printed; /* Nonzero if something output at line. */
+ bool printed; /* True if something output at line. */
bool first_time; /* pp_file_change hasn't been called yet. */
- const char *src_file; /* Current source file. */
bool prev_was_system_token; /* True if the previous token was a
system token.*/
+ const char *src_file; /* Current source file. */
} print;
/* Defined and undefined macros being queued for output with -dU at
@@ -153,7 +153,7 @@ init_pp_output (FILE *out_stream)
/* Initialize the print structure. */
print.src_line = 1;
- print.printed = 0;
+ print.printed = false;
print.prev = 0;
print.outf = out_stream;
print.first_time = 1;
@@ -206,12 +206,16 @@ scan_translation_unit (cpp_reader *pfile)
{
line_marker_emitted = do_line_change (pfile, token, loc, false);
putc (' ', print.outf);
+ print.printed = true;
}
else if (print.source->flags & PREV_WHITE
|| (print.prev
&& cpp_avoid_paste (pfile, print.prev, token))
|| (print.prev == NULL && token->type == CPP_HASH))
- putc (' ', print.outf);
+ {
+ putc (' ', print.outf);
+ print.printed = true;
+ }
}
else if (token->flags & PREV_WHITE)
{
@@ -222,6 +226,7 @@ scan_translation_unit (cpp_reader *pfile)
&& !in_pragma)
line_marker_emitted = do_line_change (pfile, token, loc, false);
putc (' ', print.outf);
+ print.printed = true;
}
avoid_paste = false;
@@ -239,7 +244,7 @@ scan_translation_unit (cpp_reader *pfile)
fprintf (print.outf, "%s %s", space, name);
else
fprintf (print.outf, "%s", name);
- print.printed = 1;
+ print.printed = true;
in_pragma = true;
}
else if (token->type == CPP_PRAGMA_EOL)
@@ -250,23 +255,23 @@ scan_translation_unit (cpp_reader *pfile)
else
{
if (cpp_get_options (parse_in)->debug)
- linemap_dump_location (line_table, token->src_loc,
- print.outf);
+ linemap_dump_location (line_table, token->src_loc, print.outf);
if (do_line_adjustments
&& !in_pragma
&& !line_marker_emitted
- && print.prev_was_system_token != !!in_system_header_at(loc)
+ && print.prev_was_system_token != !!in_system_header_at (loc)
&& !is_location_from_builtin_token (loc))
/* The system-ness of this token is different from the one
of the previous token. Let's emit a line change to
mark the new system-ness before we emit the token. */
{
do_line_change (pfile, token, loc, false);
- print.prev_was_system_token = !!in_system_header_at(loc);
+ print.prev_was_system_token = !!in_system_header_at (loc);
}
cpp_output_token (token, print.outf);
line_marker_emitted = false;
+ print.printed = true;
}
/* CPP_COMMENT tokens and raw-string literal tokens can
@@ -316,7 +321,7 @@ scan_translation_unit_trad (cpp_reader *pfile)
size_t len = pfile->out.cur - pfile->out.base;
maybe_print_line (pfile->out.first_line);
fwrite (pfile->out.base, 1, len, print.outf);
- print.printed = 1;
+ print.printed = true;
if (!CPP_OPTION (pfile, discard_comments))
account_for_newlines (pfile->out.base, len);
}
@@ -339,7 +344,7 @@ maybe_print_line_1 (source_location src_loc, FILE *stream)
{
putc ('\n', stream);
print.src_line++;
- print.printed = 0;
+ print.printed = false;
}
if (!flag_no_line_commands
@@ -385,7 +390,7 @@ print_line_1 (source_location src_loc, const char *special_flags, FILE *stream)
/* End any previous line of text. */
if (print.printed)
putc ('\n', stream);
- print.printed = 0;
+ print.printed = false;
if (!flag_no_line_commands)
{
@@ -460,7 +465,7 @@ do_line_change (cpp_reader *pfile, const cpp_token *token,
if (!CPP_OPTION (pfile, traditional))
{
int spaces = LOCATION_COLUMN (src_loc) - 2;
- print.printed = 1;
+ print.printed = true;
while (-- spaces >= 0)
putc (' ', print.outf);
@@ -503,6 +508,7 @@ cb_define (cpp_reader *pfile, source_location line, cpp_hashnode *node)
fputs ((const char *) NODE_NAME (node), print.outf);
putc ('\n', print.outf);
+ print.printed = false;
linemap_resolve_location (line_table, line,
LRK_MACRO_DEFINITION_LOCATION,
&map);
@@ -554,7 +560,7 @@ dump_queued_macros (cpp_reader *pfile ATTRIBUTE_UNUSED)
{
putc ('\n', print.outf);
print.src_line++;
- print.printed = 0;
+ print.printed = false;
}
for (q = define_queue; q;)
@@ -563,6 +569,7 @@ dump_queued_macros (cpp_reader *pfile ATTRIBUTE_UNUSED)
fputs ("#define ", print.outf);
fputs (q->macro, print.outf);
putc ('\n', print.outf);
+ print.printed = false;
print.src_line++;
oq = q;
q = q->next;
@@ -606,6 +613,7 @@ cb_include (cpp_reader *pfile ATTRIBUTE_UNUSED, source_location line,
}
putc ('\n', print.outf);
+ print.printed = false;
print.src_line++;
}
@@ -671,6 +679,7 @@ cb_def_pragma (cpp_reader *pfile, source_location line)
maybe_print_line (line);
fputs ("#pragma ", print.outf);
cpp_output_line (pfile, print.outf);
+ print.printed = false;
print.src_line++;
}
@@ -684,6 +693,7 @@ dump_macro (cpp_reader *pfile, cpp_hashnode *node, void *v ATTRIBUTE_UNUSED)
fputs ((const char *) cpp_macro_definition (pfile, node),
print.outf);
putc ('\n', print.outf);
+ print.printed = false;
print.src_line++;
}
diff --git a/gcc/c-family/c-pragma.c b/gcc/c-family/c-pragma.c
index 12c3e75ef18..56cf6976fc9 100644
--- a/gcc/c-family/c-pragma.c
+++ b/gcc/c-family/c-pragma.c
@@ -1251,6 +1251,7 @@ static const struct omp_pragma_def oacc_pragmas[] = {
{ "declare", PRAGMA_OACC_DECLARE },
{ "enter", PRAGMA_OACC_ENTER_DATA },
{ "exit", PRAGMA_OACC_EXIT_DATA },
+ { "host_data", PRAGMA_OACC_HOST_DATA },
{ "kernels", PRAGMA_OACC_KERNELS },
{ "loop", PRAGMA_OACC_LOOP },
{ "parallel", PRAGMA_OACC_PARALLEL },
diff --git a/gcc/c-family/c-pragma.h b/gcc/c-family/c-pragma.h
index 999ac6794d3..dd246b938a1 100644
--- a/gcc/c-family/c-pragma.h
+++ b/gcc/c-family/c-pragma.h
@@ -33,6 +33,7 @@ enum pragma_kind {
PRAGMA_OACC_DECLARE,
PRAGMA_OACC_ENTER_DATA,
PRAGMA_OACC_EXIT_DATA,
+ PRAGMA_OACC_HOST_DATA,
PRAGMA_OACC_KERNELS,
PRAGMA_OACC_LOOP,
PRAGMA_OACC_PARALLEL,
@@ -167,6 +168,7 @@ enum pragma_omp_clause {
PRAGMA_OACC_CLAUSE_SELF,
PRAGMA_OACC_CLAUSE_SEQ,
PRAGMA_OACC_CLAUSE_TILE,
+ PRAGMA_OACC_CLAUSE_USE_DEVICE,
PRAGMA_OACC_CLAUSE_VECTOR,
PRAGMA_OACC_CLAUSE_VECTOR_LENGTH,
PRAGMA_OACC_CLAUSE_WAIT,
diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog
index 0655aef6c19..468ef9398be 100644
--- a/gcc/c/ChangeLog
+++ b/gcc/c/ChangeLog
@@ -1,3 +1,53 @@
+2015-12-04 Eric Botcazou <ebotcazou@adacore.com>
+
+ * c-tree.h (c_build_va_arg): Adjust prototype.
+ * c-parser.c (c_parser_postfix_expression): Adjust call to above.
+ * c-typeck.c (c_build_va_arg): Rename LOC parameter to LOC2, add LOC1
+ parameter, adjust throughout and issue an error if EXPR is a component
+ with reverse storage order.
+
+2015-12-02 Jason Merrill <jason@redhat.com>
+
+ * c-fold.c (c_disable_warnings, c_enable_warnings, c_fully_fold)
+ (c_fully_fold_internal, decl_constant_value_for_optimization):
+ Move from c-common.c.
+ * c-tree.h: Declare decl_constant_value_for_optimization.
+ * Make-lang.in (C_AND_OBJC_OBJS): Add c-fold.o.
+
+2015-12-02 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/68162
+ * c-decl.c (grokdeclarator): Set first_non_attr_kind before
+ following link from declarator to next declarator. Track original
+ qualified type and pass it to c_build_qualified_type.
+ * c-typeck.c (c_build_qualified_type): Add arguments
+ orig_qual_type and orig_qual_indirect.
+
+2015-12-02 Thomas Schwinge <thomas@codesourcery.com>
+
+ * c-parser.c (c_parser_omp_clause_name)
+ (c_parser_oacc_all_clauses): Alphabetical sorting.
+
+2015-12-02 Jakub Jelinek <jakub@redhat.com>
+
+ PR c/68533
+ * c-decl.c (get_parm_info): Use b->locus instead of input_location
+ for diagnostics.
+
+2015-12-01 Julian Brown <julian@codesourcery.com>
+ Cesar Philippidis <cesar@codesourcery.com>
+ James Norris <James_Norris@mentor.com>
+
+ * c-parser.c (c_parser_omp_clause_name): Add use_device support.
+ (c_parser_oacc_clause_use_device): New function.
+ (c_parser_oacc_all_clauses): Add use_device support.
+ (OACC_HOST_DATA_CLAUSE_MASK): New macro.
+ (c_parser_oacc_host_data): New function.
+ (c_parser_omp_construct): Add host_data support.
+ * c-tree.h (c_finish_oacc_host_data): Add prototype.
+ * c-typeck.c (c_finish_oacc_host_data): New function.
+ (c_finish_omp_clauses): Add use_device support.
+
2015-11-29 Jan Hubicka <hubicka@ucw.cz>
PR c/67106
diff --git a/gcc/c/Make-lang.in b/gcc/c/Make-lang.in
index 85365fd0116..b1d0e91b0ad 100644
--- a/gcc/c/Make-lang.in
+++ b/gcc/c/Make-lang.in
@@ -51,7 +51,7 @@ CFLAGS-c/gccspec.o += $(DRIVER_DEFINES)
# Language-specific object files for C and Objective C.
C_AND_OBJC_OBJS = attribs.o c/c-errors.o c/c-decl.o c/c-typeck.o \
c/c-convert.o c/c-aux-info.o c/c-objc-common.o c/c-parser.o \
- c/c-array-notation.o $(C_COMMON_OBJS) $(C_TARGET_OBJS)
+ c/c-array-notation.o c/c-fold.o $(C_COMMON_OBJS) $(C_TARGET_OBJS)
# Language-specific object files for C.
C_OBJS = c/c-lang.o c-family/stub-objc.o $(C_AND_OBJC_OBJS)
diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c
index 31de0a51e56..9ad821925a0 100644
--- a/gcc/c/c-decl.c
+++ b/gcc/c/c-decl.c
@@ -5351,6 +5351,8 @@ grokdeclarator (const struct c_declarator *declarator,
tree returned_attrs = NULL_TREE;
bool bitfield = width != NULL;
tree element_type;
+ tree orig_qual_type = NULL;
+ size_t orig_qual_indirect = 0;
struct c_arg_info *arg_info = 0;
addr_space_t as1, as2, address_space;
location_t loc = UNKNOWN_LOCATION;
@@ -5389,9 +5391,9 @@ grokdeclarator (const struct c_declarator *declarator,
case cdk_function:
case cdk_pointer:
funcdef_syntax = (decl->kind == cdk_function);
- decl = decl->declarator;
if (first_non_attr_kind == cdk_attrs)
first_non_attr_kind = decl->kind;
+ decl = decl->declarator;
break;
case cdk_attrs:
@@ -5513,12 +5515,17 @@ grokdeclarator (const struct c_declarator *declarator,
if ((TREE_CODE (type) == ARRAY_TYPE
|| first_non_attr_kind == cdk_array)
&& TYPE_QUALS (element_type))
- type = TYPE_MAIN_VARIANT (type);
+ {
+ orig_qual_type = type;
+ type = TYPE_MAIN_VARIANT (type);
+ }
type_quals = ((constp ? TYPE_QUAL_CONST : 0)
| (restrictp ? TYPE_QUAL_RESTRICT : 0)
| (volatilep ? TYPE_QUAL_VOLATILE : 0)
| (atomicp ? TYPE_QUAL_ATOMIC : 0)
| ENCODE_QUAL_ADDR_SPACE (address_space));
+ if (type_quals != TYPE_QUALS (element_type))
+ orig_qual_type = NULL_TREE;
/* Applying the _Atomic qualifier to an array type (through the use
of typedefs or typeof) must be detected here. If the qualifier
@@ -6013,6 +6020,7 @@ grokdeclarator (const struct c_declarator *declarator,
array_ptr_attrs = NULL_TREE;
array_parm_static = 0;
}
+ orig_qual_indirect++;
break;
}
case cdk_function:
@@ -6022,6 +6030,7 @@ grokdeclarator (const struct c_declarator *declarator,
attributes. */
bool really_funcdef = false;
tree arg_types;
+ orig_qual_type = NULL_TREE;
if (funcdef_flag)
{
const struct c_declarator *t = declarator->declarator;
@@ -6122,7 +6131,9 @@ grokdeclarator (const struct c_declarator *declarator,
pedwarn (loc, OPT_Wpedantic,
"ISO C forbids qualified function types");
if (type_quals)
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
+ orig_qual_type = NULL_TREE;
size_varies = false;
/* When the pointed-to type involves components of variable size,
@@ -6304,7 +6315,8 @@ grokdeclarator (const struct c_declarator *declarator,
pedwarn (loc, OPT_Wpedantic,
"ISO C forbids qualified function types");
if (type_quals)
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
decl = build_decl (declarator->id_loc,
TYPE_DECL, declarator->u.id, type);
if (declspecs->explicit_signed_p)
@@ -6357,7 +6369,8 @@ grokdeclarator (const struct c_declarator *declarator,
pedwarn (loc, OPT_Wpedantic,
"ISO C forbids const or volatile function types");
if (type_quals)
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
return type;
}
@@ -6405,7 +6418,8 @@ grokdeclarator (const struct c_declarator *declarator,
/* Transfer const-ness of array into that of type pointed to. */
type = TREE_TYPE (type);
if (type_quals)
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
type = c_build_pointer_type (type);
type_quals = array_ptr_quals;
if (type_quals)
@@ -6496,7 +6510,8 @@ grokdeclarator (const struct c_declarator *declarator,
TYPE_DOMAIN (type) = build_range_type (sizetype, size_zero_node,
NULL_TREE);
}
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
decl = build_decl (declarator->id_loc,
FIELD_DECL, declarator->u.id, type);
DECL_NONADDRESSABLE_P (decl) = bitfield;
@@ -6608,7 +6623,8 @@ grokdeclarator (const struct c_declarator *declarator,
/* An uninitialized decl with `extern' is a reference. */
int extern_ref = !initialized && storage_class == csc_extern;
- type = c_build_qualified_type (type, type_quals);
+ type = c_build_qualified_type (type, type_quals, orig_qual_type,
+ orig_qual_indirect);
/* C99 6.2.2p7: It is invalid (compile-time undefined
behavior) to create an 'extern' declaration for a
@@ -6913,11 +6929,11 @@ get_parm_info (bool ellipsis, tree expr)
{
if (TYPE_QUALS (TREE_TYPE (b->decl)) != TYPE_UNQUALIFIED
|| C_DECL_REGISTER (b->decl))
- error ("%<void%> as only parameter may not be qualified");
+ error_at (b->locus, "%<void%> as only parameter may not be qualified");
/* There cannot be an ellipsis. */
if (ellipsis)
- error ("%<void%> must be the only parameter");
+ error_at (b->locus, "%<void%> must be the only parameter");
arg_info->types = void_list_node;
return arg_info;
@@ -6946,13 +6962,14 @@ get_parm_info (bool ellipsis, tree expr)
/* Check for forward decls that never got their actual decl. */
if (TREE_ASM_WRITTEN (decl))
- error ("parameter %q+D has just a forward declaration", decl);
+ error_at (b->locus,
+ "parameter %q+D has just a forward declaration", decl);
/* Check for (..., void, ...) and issue an error. */
else if (VOID_TYPE_P (type) && !DECL_NAME (decl))
{
if (!gave_void_only_once_err)
{
- error ("%<void%> must be the only parameter");
+ error_at (b->locus, "%<void%> must be the only parameter");
gave_void_only_once_err = true;
}
}
@@ -6991,13 +7008,13 @@ get_parm_info (bool ellipsis, tree expr)
{
if (b->id)
/* The %s will be one of 'struct', 'union', or 'enum'. */
- warning_at (input_location, 0,
+ warning_at (b->locus, 0,
"%<%s %E%> declared inside parameter list"
" will not be visible outside of this definition or"
" declaration", keyword, b->id);
else
/* The %s will be one of 'struct', 'union', or 'enum'. */
- warning_at (input_location, 0,
+ warning_at (b->locus, 0,
"anonymous %s declared inside parameter list"
" will not be visible outside of this definition or"
" declaration", keyword);
diff --git a/gcc/c/c-fold.c b/gcc/c/c-fold.c
new file mode 100644
index 00000000000..c554e179d55
--- /dev/null
+++ b/gcc/c/c-fold.c
@@ -0,0 +1,589 @@
+/* Support for fully folding sub-trees of an expression for C compiler.
+ Copyright (C) 1992-2015 Free Software Foundation, Inc.
+
+This file is part of GCC.
+
+GCC is free software; you can redistribute it and/or modify it under
+the terms of the GNU General Public License as published by the Free
+Software Foundation; either version 3, or (at your option) any later
+version.
+
+GCC is distributed in the hope that it will be useful, but WITHOUT ANY
+WARRANTY; without even the implied warranty of MERCHANTABILITY or
+FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+for more details.
+
+You should have received a copy of the GNU General Public License
+along with GCC; see the file COPYING3. If not see
+<http://www.gnu.org/licenses/>. */
+
+#include "config.h"
+#include "system.h"
+#include "coretypes.h"
+#include "target.h"
+#include "function.h"
+#include "bitmap.h"
+#include "c-tree.h"
+#include "intl.h"
+#include "gimplify.h"
+
+static tree c_fully_fold_internal (tree expr, bool, bool *, bool *, bool);
+
+/* If DISABLE is true, stop issuing warnings. This is used when
+ parsing code that we know will not be executed. This function may
+ be called multiple times, and works as a stack. */
+
+static void
+c_disable_warnings (bool disable)
+{
+ if (disable)
+ {
+ ++c_inhibit_evaluation_warnings;
+ fold_defer_overflow_warnings ();
+ }
+}
+
+/* If ENABLE is true, reenable issuing warnings. */
+
+static void
+c_enable_warnings (bool enable)
+{
+ if (enable)
+ {
+ --c_inhibit_evaluation_warnings;
+ fold_undefer_and_ignore_overflow_warnings ();
+ }
+}
+
+/* Fully fold EXPR, an expression that was not folded (beyond integer
+ constant expressions and null pointer constants) when being built
+ up. If IN_INIT, this is in a static initializer and certain
+ changes are made to the folding done. Clear *MAYBE_CONST if
+ MAYBE_CONST is not NULL and EXPR is definitely not a constant
+ expression because it contains an evaluated operator (in C99) or an
+ operator outside of sizeof returning an integer constant (in C90)
+ not permitted in constant expressions, or because it contains an
+ evaluated arithmetic overflow. (*MAYBE_CONST should typically be
+ set to true by callers before calling this function.) Return the
+ folded expression. Function arguments have already been folded
+ before calling this function, as have the contents of SAVE_EXPR,
+ TARGET_EXPR, BIND_EXPR, VA_ARG_EXPR, OBJ_TYPE_REF and
+ C_MAYBE_CONST_EXPR. */
+
+tree
+c_fully_fold (tree expr, bool in_init, bool *maybe_const)
+{
+ tree ret;
+ tree eptype = NULL_TREE;
+ bool dummy = true;
+ bool maybe_const_itself = true;
+ location_t loc = EXPR_LOCATION (expr);
+
+ if (!maybe_const)
+ maybe_const = &dummy;
+ if (TREE_CODE (expr) == EXCESS_PRECISION_EXPR)
+ {
+ eptype = TREE_TYPE (expr);
+ expr = TREE_OPERAND (expr, 0);
+ }
+ ret = c_fully_fold_internal (expr, in_init, maybe_const,
+ &maybe_const_itself, false);
+ if (eptype)
+ ret = fold_convert_loc (loc, eptype, ret);
+ *maybe_const &= maybe_const_itself;
+ return ret;
+}
+
+/* Internal helper for c_fully_fold. EXPR and IN_INIT are as for
+ c_fully_fold. *MAYBE_CONST_OPERANDS is cleared because of operands
+ not permitted, while *MAYBE_CONST_ITSELF is cleared because of
+ arithmetic overflow (for C90, *MAYBE_CONST_OPERANDS is carried from
+ both evaluated and unevaluated subexpressions while
+ *MAYBE_CONST_ITSELF is carried from only evaluated
+ subexpressions). FOR_INT_CONST indicates if EXPR is an expression
+ with integer constant operands, and if any of the operands doesn't
+ get folded to an integer constant, don't fold the expression itself. */
+
+static tree
+c_fully_fold_internal (tree expr, bool in_init, bool *maybe_const_operands,
+ bool *maybe_const_itself, bool for_int_const)
+{
+ tree ret = expr;
+ enum tree_code code = TREE_CODE (expr);
+ enum tree_code_class kind = TREE_CODE_CLASS (code);
+ location_t loc = EXPR_LOCATION (expr);
+ tree op0, op1, op2, op3;
+ tree orig_op0, orig_op1, orig_op2;
+ bool op0_const = true, op1_const = true, op2_const = true;
+ bool op0_const_self = true, op1_const_self = true, op2_const_self = true;
+ bool nowarning = TREE_NO_WARNING (expr);
+ bool unused_p;
+ source_range old_range;
+
+ /* Constants, declarations, statements, errors, SAVE_EXPRs and
+ anything else not counted as an expression cannot usefully be
+ folded further at this point. */
+ if (!IS_EXPR_CODE_CLASS (kind)
+ || kind == tcc_statement
+ || code == SAVE_EXPR)
+ return expr;
+
+ if (IS_EXPR_CODE_CLASS (kind))
+ old_range = EXPR_LOCATION_RANGE (expr);
+
+ /* Operands of variable-length expressions (function calls) have
+ already been folded, as have __builtin_* function calls, and such
+ expressions cannot occur in constant expressions. */
+ if (kind == tcc_vl_exp)
+ {
+ *maybe_const_operands = false;
+ ret = fold (expr);
+ goto out;
+ }
+
+ if (code == C_MAYBE_CONST_EXPR)
+ {
+ tree pre = C_MAYBE_CONST_EXPR_PRE (expr);
+ tree inner = C_MAYBE_CONST_EXPR_EXPR (expr);
+ if (C_MAYBE_CONST_EXPR_NON_CONST (expr))
+ *maybe_const_operands = false;
+ if (C_MAYBE_CONST_EXPR_INT_OPERANDS (expr))
+ {
+ *maybe_const_itself = false;
+ inner = c_fully_fold_internal (inner, in_init, maybe_const_operands,
+ maybe_const_itself, true);
+ }
+ if (pre && !in_init)
+ ret = build2 (COMPOUND_EXPR, TREE_TYPE (expr), pre, inner);
+ else
+ ret = inner;
+ goto out;
+ }
+
+ /* Assignment, increment, decrement, function call and comma
+ operators, and statement expressions, cannot occur in constant
+ expressions if evaluated / outside of sizeof. (Function calls
+ were handled above, though VA_ARG_EXPR is treated like a function
+ call here, and statement expressions are handled through
+ C_MAYBE_CONST_EXPR to avoid folding inside them.) */
+ switch (code)
+ {
+ case MODIFY_EXPR:
+ case PREDECREMENT_EXPR:
+ case PREINCREMENT_EXPR:
+ case POSTDECREMENT_EXPR:
+ case POSTINCREMENT_EXPR:
+ case COMPOUND_EXPR:
+ *maybe_const_operands = false;
+ break;
+
+ case VA_ARG_EXPR:
+ case TARGET_EXPR:
+ case BIND_EXPR:
+ case OBJ_TYPE_REF:
+ *maybe_const_operands = false;
+ ret = fold (expr);
+ goto out;
+
+ default:
+ break;
+ }
+
+ /* Fold individual tree codes as appropriate. */
+ switch (code)
+ {
+ case COMPOUND_LITERAL_EXPR:
+ /* Any non-constancy will have been marked in a containing
+ C_MAYBE_CONST_EXPR; there is no more folding to do here. */
+ goto out;
+
+ case COMPONENT_REF:
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ op1 = TREE_OPERAND (expr, 1);
+ op2 = TREE_OPERAND (expr, 2);
+ op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op0);
+ if (op0 != orig_op0)
+ ret = build3 (COMPONENT_REF, TREE_TYPE (expr), op0, op1, op2);
+ if (ret != expr)
+ {
+ TREE_READONLY (ret) = TREE_READONLY (expr);
+ TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
+ }
+ goto out;
+
+ case ARRAY_REF:
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ orig_op1 = op1 = TREE_OPERAND (expr, 1);
+ op2 = TREE_OPERAND (expr, 2);
+ op3 = TREE_OPERAND (expr, 3);
+ op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op0);
+ op1 = c_fully_fold_internal (op1, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op1);
+ op1 = decl_constant_value_for_optimization (op1);
+ if (op0 != orig_op0 || op1 != orig_op1)
+ ret = build4 (ARRAY_REF, TREE_TYPE (expr), op0, op1, op2, op3);
+ if (ret != expr)
+ {
+ TREE_READONLY (ret) = TREE_READONLY (expr);
+ TREE_SIDE_EFFECTS (ret) = TREE_SIDE_EFFECTS (expr);
+ TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
+ }
+ ret = fold (ret);
+ goto out;
+
+ case COMPOUND_EXPR:
+ case MODIFY_EXPR:
+ case PREDECREMENT_EXPR:
+ case PREINCREMENT_EXPR:
+ case POSTDECREMENT_EXPR:
+ case POSTINCREMENT_EXPR:
+ case PLUS_EXPR:
+ case MINUS_EXPR:
+ case MULT_EXPR:
+ case POINTER_PLUS_EXPR:
+ case TRUNC_DIV_EXPR:
+ case CEIL_DIV_EXPR:
+ case FLOOR_DIV_EXPR:
+ case TRUNC_MOD_EXPR:
+ case RDIV_EXPR:
+ case EXACT_DIV_EXPR:
+ case LSHIFT_EXPR:
+ case RSHIFT_EXPR:
+ case BIT_IOR_EXPR:
+ case BIT_XOR_EXPR:
+ case BIT_AND_EXPR:
+ case LT_EXPR:
+ case LE_EXPR:
+ case GT_EXPR:
+ case GE_EXPR:
+ case EQ_EXPR:
+ case NE_EXPR:
+ case COMPLEX_EXPR:
+ case TRUTH_AND_EXPR:
+ case TRUTH_OR_EXPR:
+ case TRUTH_XOR_EXPR:
+ case UNORDERED_EXPR:
+ case ORDERED_EXPR:
+ case UNLT_EXPR:
+ case UNLE_EXPR:
+ case UNGT_EXPR:
+ case UNGE_EXPR:
+ case UNEQ_EXPR:
+ /* Binary operations evaluating both arguments (increment and
+ decrement are binary internally in GCC). */
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ orig_op1 = op1 = TREE_OPERAND (expr, 1);
+ op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op0);
+ if (code != MODIFY_EXPR
+ && code != PREDECREMENT_EXPR
+ && code != PREINCREMENT_EXPR
+ && code != POSTDECREMENT_EXPR
+ && code != POSTINCREMENT_EXPR)
+ op0 = decl_constant_value_for_optimization (op0);
+ /* The RHS of a MODIFY_EXPR was fully folded when building that
+ expression for the sake of conversion warnings. */
+ if (code != MODIFY_EXPR)
+ op1 = c_fully_fold_internal (op1, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op1);
+ op1 = decl_constant_value_for_optimization (op1);
+
+ if (for_int_const && (TREE_CODE (op0) != INTEGER_CST
+ || TREE_CODE (op1) != INTEGER_CST))
+ goto out;
+
+ if (op0 != orig_op0 || op1 != orig_op1 || in_init)
+ ret = in_init
+ ? fold_build2_initializer_loc (loc, code, TREE_TYPE (expr), op0, op1)
+ : fold_build2_loc (loc, code, TREE_TYPE (expr), op0, op1);
+ else
+ ret = fold (expr);
+ if (TREE_OVERFLOW_P (ret)
+ && !TREE_OVERFLOW_P (op0)
+ && !TREE_OVERFLOW_P (op1))
+ overflow_warning (EXPR_LOC_OR_LOC (expr, input_location), ret);
+ if (code == LSHIFT_EXPR
+ && TREE_CODE (orig_op0) != INTEGER_CST
+ && TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
+ && TREE_CODE (op0) == INTEGER_CST
+ && c_inhibit_evaluation_warnings == 0
+ && tree_int_cst_sgn (op0) < 0)
+ warning_at (loc, OPT_Wshift_negative_value,
+ "left shift of negative value");
+ if ((code == LSHIFT_EXPR || code == RSHIFT_EXPR)
+ && TREE_CODE (orig_op1) != INTEGER_CST
+ && TREE_CODE (op1) == INTEGER_CST
+ && (TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
+ || TREE_CODE (TREE_TYPE (orig_op0)) == FIXED_POINT_TYPE)
+ && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE
+ && c_inhibit_evaluation_warnings == 0)
+ {
+ if (tree_int_cst_sgn (op1) < 0)
+ warning_at (loc, OPT_Wshift_count_negative,
+ (code == LSHIFT_EXPR
+ ? G_("left shift count is negative")
+ : G_("right shift count is negative")));
+ else if (compare_tree_int (op1,
+ TYPE_PRECISION (TREE_TYPE (orig_op0)))
+ >= 0)
+ warning_at (loc, OPT_Wshift_count_overflow,
+ (code == LSHIFT_EXPR
+ ? G_("left shift count >= width of type")
+ : G_("right shift count >= width of type")));
+ }
+ if (code == LSHIFT_EXPR
+ /* If either OP0 has been folded to INTEGER_CST... */
+ && ((TREE_CODE (orig_op0) != INTEGER_CST
+ && TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
+ && TREE_CODE (op0) == INTEGER_CST)
+ /* ...or if OP1 has been folded to INTEGER_CST... */
+ || (TREE_CODE (orig_op1) != INTEGER_CST
+ && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE
+ && TREE_CODE (op1) == INTEGER_CST))
+ && c_inhibit_evaluation_warnings == 0)
+ /* ...then maybe we can detect an overflow. */
+ maybe_warn_shift_overflow (loc, op0, op1);
+ if ((code == TRUNC_DIV_EXPR
+ || code == CEIL_DIV_EXPR
+ || code == FLOOR_DIV_EXPR
+ || code == EXACT_DIV_EXPR
+ || code == TRUNC_MOD_EXPR)
+ && TREE_CODE (orig_op1) != INTEGER_CST
+ && TREE_CODE (op1) == INTEGER_CST
+ && (TREE_CODE (TREE_TYPE (orig_op0)) == INTEGER_TYPE
+ || TREE_CODE (TREE_TYPE (orig_op0)) == FIXED_POINT_TYPE)
+ && TREE_CODE (TREE_TYPE (orig_op1)) == INTEGER_TYPE)
+ warn_for_div_by_zero (loc, op1);
+ goto out;
+
+ case INDIRECT_REF:
+ case FIX_TRUNC_EXPR:
+ case FLOAT_EXPR:
+ CASE_CONVERT:
+ case ADDR_SPACE_CONVERT_EXPR:
+ case VIEW_CONVERT_EXPR:
+ case NON_LVALUE_EXPR:
+ case NEGATE_EXPR:
+ case BIT_NOT_EXPR:
+ case TRUTH_NOT_EXPR:
+ case ADDR_EXPR:
+ case CONJ_EXPR:
+ case REALPART_EXPR:
+ case IMAGPART_EXPR:
+ /* Unary operations. */
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ op0 = c_fully_fold_internal (op0, in_init, maybe_const_operands,
+ maybe_const_itself, for_int_const);
+ STRIP_TYPE_NOPS (op0);
+ if (code != ADDR_EXPR && code != REALPART_EXPR && code != IMAGPART_EXPR)
+ op0 = decl_constant_value_for_optimization (op0);
+
+ if (for_int_const && TREE_CODE (op0) != INTEGER_CST)
+ goto out;
+
+ /* ??? Cope with user tricks that amount to offsetof. The middle-end is
+ not prepared to deal with them if they occur in initializers. */
+ if (op0 != orig_op0
+ && code == ADDR_EXPR
+ && (op1 = get_base_address (op0)) != NULL_TREE
+ && INDIRECT_REF_P (op1)
+ && TREE_CONSTANT (TREE_OPERAND (op1, 0)))
+ ret = fold_convert_loc (loc, TREE_TYPE (expr), fold_offsetof_1 (op0));
+ else if (op0 != orig_op0 || in_init)
+ ret = in_init
+ ? fold_build1_initializer_loc (loc, code, TREE_TYPE (expr), op0)
+ : fold_build1_loc (loc, code, TREE_TYPE (expr), op0);
+ else
+ ret = fold (expr);
+ if (code == INDIRECT_REF
+ && ret != expr
+ && INDIRECT_REF_P (ret))
+ {
+ TREE_READONLY (ret) = TREE_READONLY (expr);
+ TREE_SIDE_EFFECTS (ret) = TREE_SIDE_EFFECTS (expr);
+ TREE_THIS_VOLATILE (ret) = TREE_THIS_VOLATILE (expr);
+ }
+ switch (code)
+ {
+ case FIX_TRUNC_EXPR:
+ case FLOAT_EXPR:
+ CASE_CONVERT:
+ /* Don't warn about explicit conversions. We will already
+ have warned about suspect implicit conversions. */
+ break;
+
+ default:
+ if (TREE_OVERFLOW_P (ret) && !TREE_OVERFLOW_P (op0))
+ overflow_warning (EXPR_LOCATION (expr), ret);
+ break;
+ }
+ goto out;
+
+ case TRUTH_ANDIF_EXPR:
+ case TRUTH_ORIF_EXPR:
+ /* Binary operations not necessarily evaluating both
+ arguments. */
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ orig_op1 = op1 = TREE_OPERAND (expr, 1);
+ op0 = c_fully_fold_internal (op0, in_init, &op0_const, &op0_const_self,
+ for_int_const);
+ STRIP_TYPE_NOPS (op0);
+
+ unused_p = (op0 == (code == TRUTH_ANDIF_EXPR
+ ? truthvalue_false_node
+ : truthvalue_true_node));
+ c_disable_warnings (unused_p);
+ op1 = c_fully_fold_internal (op1, in_init, &op1_const, &op1_const_self,
+ for_int_const);
+ STRIP_TYPE_NOPS (op1);
+ c_enable_warnings (unused_p);
+
+ if (for_int_const
+ && (TREE_CODE (op0) != INTEGER_CST
+ /* Require OP1 be an INTEGER_CST only if it's evaluated. */
+ || (!unused_p && TREE_CODE (op1) != INTEGER_CST)))
+ goto out;
+
+ if (op0 != orig_op0 || op1 != orig_op1 || in_init)
+ ret = in_init
+ ? fold_build2_initializer_loc (loc, code, TREE_TYPE (expr), op0, op1)
+ : fold_build2_loc (loc, code, TREE_TYPE (expr), op0, op1);
+ else
+ ret = fold (expr);
+ *maybe_const_operands &= op0_const;
+ *maybe_const_itself &= op0_const_self;
+ if (!(flag_isoc99
+ && op0_const
+ && op0_const_self
+ && (code == TRUTH_ANDIF_EXPR
+ ? op0 == truthvalue_false_node
+ : op0 == truthvalue_true_node)))
+ *maybe_const_operands &= op1_const;
+ if (!(op0_const
+ && op0_const_self
+ && (code == TRUTH_ANDIF_EXPR
+ ? op0 == truthvalue_false_node
+ : op0 == truthvalue_true_node)))
+ *maybe_const_itself &= op1_const_self;
+ goto out;
+
+ case COND_EXPR:
+ orig_op0 = op0 = TREE_OPERAND (expr, 0);
+ orig_op1 = op1 = TREE_OPERAND (expr, 1);
+ orig_op2 = op2 = TREE_OPERAND (expr, 2);
+ op0 = c_fully_fold_internal (op0, in_init, &op0_const, &op0_const_self,
+ for_int_const);
+
+ STRIP_TYPE_NOPS (op0);
+ c_disable_warnings (op0 == truthvalue_false_node);
+ op1 = c_fully_fold_internal (op1, in_init, &op1_const, &op1_const_self,
+ for_int_const);
+ STRIP_TYPE_NOPS (op1);
+ c_enable_warnings (op0 == truthvalue_false_node);
+
+ c_disable_warnings (op0 == truthvalue_true_node);
+ op2 = c_fully_fold_internal (op2, in_init, &op2_const, &op2_const_self,
+ for_int_const);
+ STRIP_TYPE_NOPS (op2);
+ c_enable_warnings (op0 == truthvalue_true_node);
+
+ if (for_int_const
+ && (TREE_CODE (op0) != INTEGER_CST
+ /* Only the evaluated operand must be an INTEGER_CST. */
+ || (op0 == truthvalue_true_node
+ ? TREE_CODE (op1) != INTEGER_CST
+ : TREE_CODE (op2) != INTEGER_CST)))
+ goto out;
+
+ if (op0 != orig_op0 || op1 != orig_op1 || op2 != orig_op2)
+ ret = fold_build3_loc (loc, code, TREE_TYPE (expr), op0, op1, op2);
+ else
+ ret = fold (expr);
+ *maybe_const_operands &= op0_const;
+ *maybe_const_itself &= op0_const_self;
+ if (!(flag_isoc99
+ && op0_const
+ && op0_const_self
+ && op0 == truthvalue_false_node))
+ *maybe_const_operands &= op1_const;
+ if (!(op0_const
+ && op0_const_self
+ && op0 == truthvalue_false_node))
+ *maybe_const_itself &= op1_const_self;
+ if (!(flag_isoc99
+ && op0_const
+ && op0_const_self
+ && op0 == truthvalue_true_node))
+ *maybe_const_operands &= op2_const;
+ if (!(op0_const
+ && op0_const_self
+ && op0 == truthvalue_true_node))
+ *maybe_const_itself &= op2_const_self;
+ goto out;
+
+ case EXCESS_PRECISION_EXPR:
+ /* Each case where an operand with excess precision may be
+ encountered must remove the EXCESS_PRECISION_EXPR around
+ inner operands and possibly put one around the whole
+ expression or possibly convert to the semantic type (which
+ c_fully_fold does); we cannot tell at this stage which is
+ appropriate in any particular case. */
+ gcc_unreachable ();
+
+ default:
+ /* Various codes may appear through folding built-in functions
+ and their arguments. */
+ goto out;
+ }
+
+ out:
+ /* Some folding may introduce NON_LVALUE_EXPRs; all lvalue checks
+ have been done by this point, so remove them again. */
+ nowarning |= TREE_NO_WARNING (ret);
+ STRIP_TYPE_NOPS (ret);
+ if (nowarning && !TREE_NO_WARNING (ret))
+ {
+ if (!CAN_HAVE_LOCATION_P (ret))
+ ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
+ TREE_NO_WARNING (ret) = 1;
+ }
+ if (ret != expr)
+ {
+ protected_set_expr_location (ret, loc);
+ if (IS_EXPR_CODE_CLASS (kind))
+ set_source_range (ret, old_range.m_start, old_range.m_finish);
+ }
+ return ret;
+}
+
+/* If not optimizing, EXP is not a VAR_DECL, or EXP has array type,
+ return EXP. Otherwise, return either EXP or its known constant
+ value (if it has one), but return EXP if EXP has mode BLKmode. ???
+ Is the BLKmode test appropriate? */
+
+tree
+decl_constant_value_for_optimization (tree exp)
+{
+ tree ret;
+
+ if (!optimize
+ || !VAR_P (exp)
+ || TREE_CODE (TREE_TYPE (exp)) == ARRAY_TYPE
+ || DECL_MODE (exp) == BLKmode)
+ return exp;
+
+ ret = decl_constant_value (exp);
+ /* Avoid unwanted tree sharing between the initializer and current
+ function's body where the tree can be modified e.g. by the
+ gimplifier. */
+ if (ret != exp && TREE_STATIC (exp))
+ ret = unshare_expr (ret);
+ return ret;
+}
diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c
index 0259f66aeb4..c7d15f9fc38 100644
--- a/gcc/c/c-parser.c
+++ b/gcc/c/c-parser.c
@@ -7485,7 +7485,7 @@ c_parser_postfix_expression (c_parser *parser)
else
{
tree type_expr = NULL_TREE;
- expr.value = c_build_va_arg (loc, e1.value,
+ expr.value = c_build_va_arg (start_loc, e1.value, loc,
groktypename (t1, &type_expr, NULL));
if (type_expr)
{
@@ -10277,6 +10277,8 @@ c_parser_omp_clause_name (c_parser *parser)
result = PRAGMA_OMP_CLAUSE_UNIFORM;
else if (!strcmp ("untied", p))
result = PRAGMA_OMP_CLAUSE_UNTIED;
+ else if (!strcmp ("use_device", p))
+ result = PRAGMA_OACC_CLAUSE_USE_DEVICE;
else if (!strcmp ("use_device_ptr", p))
result = PRAGMA_OMP_CLAUSE_USE_DEVICE_PTR;
break;
@@ -11631,6 +11633,15 @@ c_parser_oacc_clause_tile (c_parser *parser, tree list)
return c;
}
+/* OpenACC 2.0:
+ use_device ( variable-list ) */
+
+static tree
+c_parser_oacc_clause_use_device (c_parser *parser, tree list)
+{
+ return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_USE_DEVICE, list);
+}
+
/* OpenACC:
wait ( int-expr-list ) */
@@ -12949,6 +12960,10 @@ c_parser_oacc_all_clauses (c_parser *parser, omp_clause_mask mask,
clauses = c_parser_oacc_clause_tile (parser, clauses);
c_name = "tile";
break;
+ case PRAGMA_OACC_CLAUSE_USE_DEVICE:
+ clauses = c_parser_oacc_clause_use_device (parser, clauses);
+ c_name = "use_device";
+ break;
case PRAGMA_OACC_CLAUSE_VECTOR:
c_name = "vector";
clauses = c_parser_oacc_shape_clause (parser, OMP_CLAUSE_VECTOR,
@@ -13590,6 +13605,29 @@ c_parser_oacc_enter_exit_data (c_parser *parser, bool enter)
/* OpenACC 2.0:
+ # pragma acc host_data oacc-data-clause[optseq] new-line
+ structured-block
+*/
+
+#define OACC_HOST_DATA_CLAUSE_MASK \
+ ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_USE_DEVICE) )
+
+static tree
+c_parser_oacc_host_data (location_t loc, c_parser *parser)
+{
+ tree stmt, clauses, block;
+
+ clauses = c_parser_oacc_all_clauses (parser, OACC_HOST_DATA_CLAUSE_MASK,
+ "#pragma acc host_data");
+
+ block = c_begin_omp_parallel ();
+ add_stmt (c_parser_omp_structured_block (parser));
+ stmt = c_finish_oacc_host_data (loc, clauses, block);
+ return stmt;
+}
+
+
+/* OpenACC 2.0:
# pragma acc loop oacc-loop-clause[optseq] new-line
structured-block
@@ -16897,6 +16935,9 @@ c_parser_omp_construct (c_parser *parser)
case PRAGMA_OACC_DATA:
stmt = c_parser_oacc_data (loc, parser);
break;
+ case PRAGMA_OACC_HOST_DATA:
+ stmt = c_parser_oacc_host_data (loc, parser);
+ break;
case PRAGMA_OACC_KERNELS:
case PRAGMA_OACC_PARALLEL:
strcpy (p_name, "#pragma acc");
diff --git a/gcc/c/c-tree.h b/gcc/c/c-tree.h
index 6bc216af889..00e72b115ca 100644
--- a/gcc/c/c-tree.h
+++ b/gcc/c/c-tree.h
@@ -653,6 +653,7 @@ extern tree c_finish_goto_ptr (location_t, tree);
extern tree c_expr_to_decl (tree, bool *, bool *);
extern tree c_finish_omp_construct (location_t, enum tree_code, tree, tree);
extern tree c_finish_oacc_data (location_t, tree, tree);
+extern tree c_finish_oacc_host_data (location_t, tree, tree);
extern tree c_begin_omp_parallel (void);
extern tree c_finish_omp_parallel (location_t, tree, tree);
extern tree c_begin_omp_task (void);
@@ -660,7 +661,7 @@ extern tree c_finish_omp_task (location_t, tree, tree);
extern void c_finish_omp_cancel (location_t, tree);
extern void c_finish_omp_cancellation_point (location_t, tree);
extern tree c_finish_omp_clauses (tree, bool, bool = false);
-extern tree c_build_va_arg (location_t, tree, tree);
+extern tree c_build_va_arg (location_t, tree, location_t, tree);
extern tree c_finish_transaction (location_t, tree, int);
extern bool c_tree_equal (tree, tree);
extern tree c_build_function_call_vec (location_t, vec<location_t>, tree,
@@ -727,4 +728,7 @@ extern void
set_c_expr_source_range (c_expr *expr,
source_range src_range);
+/* In c-fold.c */
+extern tree decl_constant_value_for_optimization (tree);
+
#endif /* ! GCC_C_TREE_H */
diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c
index 741c75cb169..b691072caa9 100644
--- a/gcc/c/c-typeck.c
+++ b/gcc/c/c-typeck.c
@@ -11631,6 +11631,25 @@ c_finish_oacc_data (location_t loc, tree clauses, tree block)
return add_stmt (stmt);
}
+/* Generate OACC_HOST_DATA, with CLAUSES and BLOCK as its compound
+ statement. LOC is the location of the OACC_HOST_DATA. */
+
+tree
+c_finish_oacc_host_data (location_t loc, tree clauses, tree block)
+{
+ tree stmt;
+
+ block = c_end_compound_stmt (loc, block, true);
+
+ stmt = make_node (OACC_HOST_DATA);
+ TREE_TYPE (stmt) = void_type_node;
+ OACC_HOST_DATA_CLAUSES (stmt) = clauses;
+ OACC_HOST_DATA_BODY (stmt) = block;
+ SET_EXPR_LOCATION (stmt, loc);
+
+ return add_stmt (stmt);
+}
+
/* Like c_begin_compound_stmt, except force the retention of the BLOCK. */
tree
@@ -13074,6 +13093,7 @@ c_finish_omp_clauses (tree clauses, bool is_omp, bool declare_simd)
bitmap_set_bit (&map_head, DECL_UID (t));
goto check_dup_generic;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_IS_DEVICE_PTR:
case OMP_CLAUSE_USE_DEVICE_PTR:
t = OMP_CLAUSE_DECL (c);
@@ -13317,10 +13337,15 @@ c_finish_transaction (location_t loc, tree block, int flags)
}
/* Make a variant type in the proper way for C/C++, propagating qualifiers
- down to the element type of an array. */
+ down to the element type of an array. If ORIG_QUAL_TYPE is not
+ NULL, then it should be used as the qualified type
+ ORIG_QUAL_INDIRECT levels down in array type derivation (to
+ preserve information about the typedef name from which an array
+ type was derived). */
tree
-c_build_qualified_type (tree type, int type_quals)
+c_build_qualified_type (tree type, int type_quals, tree orig_qual_type,
+ size_t orig_qual_indirect)
{
if (type == error_mark_node)
return type;
@@ -13329,18 +13354,22 @@ c_build_qualified_type (tree type, int type_quals)
{
tree t;
tree element_type = c_build_qualified_type (TREE_TYPE (type),
- type_quals);
+ type_quals, orig_qual_type,
+ orig_qual_indirect - 1);
/* See if we already have an identically qualified type. */
- for (t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
- {
- if (TYPE_QUALS (strip_array_types (t)) == type_quals
- && TYPE_NAME (t) == TYPE_NAME (type)
- && TYPE_CONTEXT (t) == TYPE_CONTEXT (type)
- && attribute_list_equal (TYPE_ATTRIBUTES (t),
- TYPE_ATTRIBUTES (type)))
- break;
- }
+ if (orig_qual_type && orig_qual_indirect == 0)
+ t = orig_qual_type;
+ else
+ for (t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
+ {
+ if (TYPE_QUALS (strip_array_types (t)) == type_quals
+ && TYPE_NAME (t) == TYPE_NAME (type)
+ && TYPE_CONTEXT (t) == TYPE_CONTEXT (type)
+ && attribute_list_equal (TYPE_ATTRIBUTES (t),
+ TYPE_ATTRIBUTES (type)))
+ break;
+ }
if (!t)
{
tree domain = TYPE_DOMAIN (type);
@@ -13384,7 +13413,9 @@ c_build_qualified_type (tree type, int type_quals)
type_quals &= ~TYPE_QUAL_RESTRICT;
}
- tree var_type = build_qualified_type (type, type_quals);
+ tree var_type = (orig_qual_type && orig_qual_indirect == 0
+ ? orig_qual_type
+ : build_qualified_type (type, type_quals));
/* A variant type does not inherit the list of incomplete vars from the
type main variant. */
if (RECORD_OR_UNION_TYPE_P (var_type))
@@ -13395,20 +13426,28 @@ c_build_qualified_type (tree type, int type_quals)
/* Build a VA_ARG_EXPR for the C parser. */
tree
-c_build_va_arg (location_t loc, tree expr, tree type)
+c_build_va_arg (location_t loc1, tree expr, location_t loc2, tree type)
{
if (error_operand_p (type))
return error_mark_node;
+ /* VA_ARG_EXPR cannot be used for a scalar va_list with reverse storage
+ order because it takes the address of the expression. */
+ else if (handled_component_p (expr)
+ && reverse_storage_order_for_component_p (expr))
+ {
+ error_at (loc1, "cannot use %<va_arg%> with reverse storage order");
+ return error_mark_node;
+ }
else if (!COMPLETE_TYPE_P (type))
{
- error_at (loc, "second argument to %<va_arg%> is of incomplete "
+ error_at (loc2, "second argument to %<va_arg%> is of incomplete "
"type %qT", type);
return error_mark_node;
}
else if (warn_cxx_compat && TREE_CODE (type) == ENUMERAL_TYPE)
- warning_at (loc, OPT_Wc___compat,
+ warning_at (loc2, OPT_Wc___compat,
"C++ requires promoted type, not enum type, in %<va_arg%>");
- return build_va_arg (loc, expr, type);
+ return build_va_arg (loc2, expr, type);
}
/* Return truthvalue of whether T1 is the same tree structure as T2.
diff --git a/gcc/cfgexpand.c b/gcc/cfgexpand.c
index 1990e107db6..0cf417270e9 100644
--- a/gcc/cfgexpand.c
+++ b/gcc/cfgexpand.c
@@ -3534,6 +3534,12 @@ expand_gimple_stmt_1 (gimple *stmt)
{
tree result = DECL_RESULT (current_function_decl);
+ /* Mark we have return statement with missing bounds. */
+ if (!bnd
+ && chkp_function_instrumented_p (cfun->decl)
+ && !DECL_P (op0))
+ bnd = error_mark_node;
+
/* If we are not returning the current function's RESULT_DECL,
build an assignment to it. */
if (op0 != result)
@@ -3550,9 +3556,6 @@ expand_gimple_stmt_1 (gimple *stmt)
op0 = build2 (MODIFY_EXPR, TREE_TYPE (result),
result, op0);
}
- /* Mark we have return statement with missing bounds. */
- if (!bnd && chkp_function_instrumented_p (cfun->decl))
- bnd = error_mark_node;
}
if (!op0)
@@ -6291,7 +6294,7 @@ pass_expand::execute (function *fun)
expand_phi_nodes (&SA);
/* Release any stale SSA redirection data. */
- redirect_edge_var_map_destroy ();
+ redirect_edge_var_map_empty ();
/* Register rtl specific functions for cfg. */
rtl_register_cfg_hooks ();
diff --git a/gcc/cgraphunit.c b/gcc/cgraphunit.c
index f73d9a78e03..4ab64147e88 100644
--- a/gcc/cgraphunit.c
+++ b/gcc/cgraphunit.c
@@ -575,6 +575,7 @@ cgraph_node::analyze (void)
cgraph_node *t = cgraph_node::get (thunk.alias);
create_edge (t, NULL, 0, CGRAPH_FREQ_BASE);
+ callees->can_throw_external = !TREE_NOTHROW (t->decl);
/* Target code in expand_thunk may need the thunk's target
to be analyzed, so recurse here. */
if (!t->analyzed)
@@ -956,7 +957,7 @@ check_global_declaration (symtab_node *snode)
&& ! DECL_ABSTRACT_ORIGIN (decl)
&& ! TREE_PUBLIC (decl)
/* A volatile variable might be used in some non-obvious way. */
- && ! TREE_THIS_VOLATILE (decl)
+ && (! VAR_P (decl) || ! TREE_THIS_VOLATILE (decl))
/* Global register variables must be declared to reserve them. */
&& ! (TREE_CODE (decl) == VAR_DECL && DECL_REGISTER (decl))
/* Global ctors and dtors are called by the runtime. */
diff --git a/gcc/common.opt b/gcc/common.opt
index e1617c41bd8..e593631b5f2 100644
--- a/gcc/common.opt
+++ b/gcc/common.opt
@@ -1379,7 +1379,7 @@ Common Ignore
Does nothing. Preserved for backward compatibility.
floop-nest-optimize
-Common Report Var(flag_loop_optimize_isl) Optimization
+Common Report Var(flag_loop_nest_optimize) Optimization
Enable the ISL based loop nest optimizer.
fstrict-volatile-bitfields
diff --git a/gcc/config.in b/gcc/config.in
index bb0d22053e9..a1762bec436 100644
--- a/gcc/config.in
+++ b/gcc/config.in
@@ -327,6 +327,12 @@
#endif
+/* Define if your assembler supports the R_PPC64_ENTRY relocation. */
+#ifndef USED_FOR_TARGET
+#undef HAVE_AS_ENTRY_MARKERS
+#endif
+
+
/* Define if your assembler supports explicit relocations. */
#ifndef USED_FOR_TARGET
#undef HAVE_AS_EXPLICIT_RELOCS
diff --git a/gcc/config/aarch64/aarch64-builtins.c b/gcc/config/aarch64/aarch64-builtins.c
index 45011f61d9b..b268a6aaf7c 100644
--- a/gcc/config/aarch64/aarch64-builtins.c
+++ b/gcc/config/aarch64/aarch64-builtins.c
@@ -1176,19 +1176,19 @@ aarch64_expand_builtin_rsqrt (int fcode, tree exp, rtx target)
switch (fcode)
{
case AARCH64_BUILTIN_RSQRT_DF:
- gen = gen_aarch64_rsqrt_df2;
+ gen = gen_rsqrtdf2;
break;
case AARCH64_BUILTIN_RSQRT_SF:
- gen = gen_aarch64_rsqrt_sf2;
+ gen = gen_rsqrtsf2;
break;
case AARCH64_BUILTIN_RSQRT_V2DF:
- gen = gen_aarch64_rsqrt_v2df2;
+ gen = gen_rsqrtv2df2;
break;
case AARCH64_BUILTIN_RSQRT_V2SF:
- gen = gen_aarch64_rsqrt_v2sf2;
+ gen = gen_rsqrtv2sf2;
break;
case AARCH64_BUILTIN_RSQRT_V4SF:
- gen = gen_aarch64_rsqrt_v4sf2;
+ gen = gen_rsqrtv4sf2;
break;
default: gcc_unreachable ();
}
@@ -1405,24 +1405,14 @@ aarch64_builtin_vectorized_function (unsigned int fn, tree type_out,
/* Return builtin for reciprocal square root. */
tree
-aarch64_builtin_rsqrt (unsigned int fn, bool md_fn)
+aarch64_builtin_rsqrt (unsigned int fn)
{
- if (md_fn)
- {
- if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv2df)
- return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V2DF];
- if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv2sf)
- return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V2SF];
- if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv4sf)
- return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V4SF];
- }
- else
- {
- if (fn == BUILT_IN_SQRT)
- return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_DF];
- if (fn == BUILT_IN_SQRTF)
- return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_SF];
- }
+ if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv2df)
+ return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V2DF];
+ if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv2sf)
+ return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V2SF];
+ if (fn == AARCH64_SIMD_BUILTIN_UNOP_sqrtv4sf)
+ return aarch64_builtin_decls[AARCH64_BUILTIN_RSQRT_V4SF];
return NULL_TREE;
}
diff --git a/gcc/config/aarch64/aarch64-cores.def b/gcc/config/aarch64/aarch64-cores.def
index f8fab28d912..076574ec429 100644
--- a/gcc/config/aarch64/aarch64-cores.def
+++ b/gcc/config/aarch64/aarch64-cores.def
@@ -44,7 +44,7 @@ AARCH64_CORE("cortex-a35", cortexa35, cortexa53, 8A, AARCH64_FL_FOR_ARCH8 | AA
AARCH64_CORE("cortex-a53", cortexa53, cortexa53, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC, cortexa53, "0x41", "0xd03")
AARCH64_CORE("cortex-a57", cortexa57, cortexa57, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC, cortexa57, "0x41", "0xd07")
AARCH64_CORE("cortex-a72", cortexa72, cortexa57, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC, cortexa72, "0x41", "0xd08")
-AARCH64_CORE("exynos-m1", exynosm1, cortexa57, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC | AARCH64_FL_CRYPTO, cortexa72, "0x53", "0x001")
+AARCH64_CORE("exynos-m1", exynosm1, cortexa57, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC | AARCH64_FL_CRYPTO, exynosm1, "0x53", "0x001")
AARCH64_CORE("qdf24xx", qdf24xx, cortexa57, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC | AARCH64_FL_CRYPTO, cortexa57, "0x51", "0x800")
AARCH64_CORE("thunderx", thunderx, thunderx, 8A, AARCH64_FL_FOR_ARCH8 | AARCH64_FL_CRC | AARCH64_FL_CRYPTO, thunderx, "0x43", "0x0a1")
AARCH64_CORE("xgene1", xgene1, xgene1, 8A, AARCH64_FL_FOR_ARCH8, xgene1, "0x50", "0x000")
diff --git a/gcc/config/aarch64/aarch64-protos.h b/gcc/config/aarch64/aarch64-protos.h
index e0a050ce5bc..e6bfe06bc15 100644
--- a/gcc/config/aarch64/aarch64-protos.h
+++ b/gcc/config/aarch64/aarch64-protos.h
@@ -407,7 +407,7 @@ rtx aarch64_expand_builtin (tree exp,
int ignore ATTRIBUTE_UNUSED);
tree aarch64_builtin_decl (unsigned, bool ATTRIBUTE_UNUSED);
-tree aarch64_builtin_rsqrt (unsigned int, bool);
+tree aarch64_builtin_rsqrt (unsigned int);
tree aarch64_builtin_vectorized_function (unsigned int, tree, tree);
diff --git a/gcc/config/aarch64/aarch64-simd.md b/gcc/config/aarch64/aarch64-simd.md
index 7910484baf0..030a1013caa 100644
--- a/gcc/config/aarch64/aarch64-simd.md
+++ b/gcc/config/aarch64/aarch64-simd.md
@@ -399,7 +399,7 @@
"frsqrts\\t%<v>0<Vmtype>, %<v>1<Vmtype>, %<v>2<Vmtype>"
[(set_attr "type" "neon_fp_rsqrts_<Vetype><q>")])
-(define_expand "aarch64_rsqrt_<mode>2"
+(define_expand "rsqrt<mode>2"
[(set (match_operand:VALLF 0 "register_operand" "=w")
(unspec:VALLF [(match_operand:VALLF 1 "register_operand" "w")]
UNSPEC_RSQRT))]
@@ -1962,6 +1962,17 @@
[(set_attr "type" "neon_fp_minmax_<Vetype><q>")]
)
+;; Auto-vectorized forms for the IEEE-754 fmax()/fmin() functions
+(define_insn "<fmaxmin><mode>3"
+ [(set (match_operand:VDQF 0 "register_operand" "=w")
+ (unspec:VDQF [(match_operand:VDQF 1 "register_operand" "w")
+ (match_operand:VDQF 2 "register_operand" "w")]
+ FMAXMIN))]
+ "TARGET_SIMD"
+ "<fmaxmin_op>\\t%0.<Vtype>, %1.<Vtype>, %2.<Vtype>"
+ [(set_attr "type" "neon_fp_minmax_<Vetype><q>")]
+)
+
;; 'across lanes' add.
(define_expand "reduc_plus_scal_<mode>"
diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c
index 88dbe158c73..191ad6debb8 100644
--- a/gcc/config/aarch64/aarch64.c
+++ b/gcc/config/aarch64/aarch64.c
@@ -216,6 +216,22 @@ static const struct cpu_addrcost_table cortexa57_addrcost_table =
0, /* imm_offset */
};
+static const struct cpu_addrcost_table exynosm1_addrcost_table =
+{
+ {
+ 0, /* hi */
+ 0, /* si */
+ 0, /* di */
+ 2, /* ti */
+ },
+ 0, /* pre_modify */
+ 0, /* post_modify */
+ 1, /* register_offset */
+ 1, /* register_sextend */
+ 2, /* register_zextend */
+ 0, /* imm_offset */
+};
+
static const struct cpu_addrcost_table xgene1_addrcost_table =
{
{
@@ -262,6 +278,16 @@ static const struct cpu_regmove_cost cortexa53_regmove_cost =
2 /* FP2FP */
};
+static const struct cpu_regmove_cost exynosm1_regmove_cost =
+{
+ 1, /* GP2GP */
+ /* Avoid the use of slow int<->fp moves for spilling by setting
+ their cost higher than memmov_cost (actual, 4 and 9). */
+ 9, /* GP2FP */
+ 9, /* FP2GP */
+ 1 /* FP2FP */
+};
+
static const struct cpu_regmove_cost thunderx_regmove_cost =
{
2, /* GP2GP */
@@ -314,6 +340,22 @@ static const struct cpu_vector_cost cortexa57_vector_cost =
1 /* cond_not_taken_branch_cost */
};
+static const struct cpu_vector_cost exynosm1_vector_cost =
+{
+ 1, /* scalar_stmt_cost */
+ 5, /* scalar_load_cost */
+ 1, /* scalar_store_cost */
+ 3, /* vec_stmt_cost */
+ 3, /* vec_to_scalar_cost */
+ 3, /* scalar_to_vec_cost */
+ 5, /* vec_align_load_cost */
+ 5, /* vec_unalign_load_cost */
+ 1, /* vec_unalign_store_cost */
+ 1, /* vec_store_cost */
+ 1, /* cond_taken_branch_cost */
+ 1 /* cond_not_taken_branch_cost */
+};
+
/* Generic costs for vector insn classes. */
static const struct cpu_vector_cost xgene1_vector_cost =
{
@@ -470,6 +512,30 @@ static const struct tune_params cortexa72_tunings =
(AARCH64_EXTRA_TUNE_NONE) /* tune_flags. */
};
+static const struct tune_params exynosm1_tunings =
+{
+ &exynosm1_extra_costs,
+ &exynosm1_addrcost_table,
+ &exynosm1_regmove_cost,
+ &exynosm1_vector_cost,
+ &generic_branch_cost,
+ 4, /* memmov_cost */
+ 3, /* issue_rate */
+ (AARCH64_FUSE_NOTHING), /* fusible_ops */
+ 4, /* function_align. */
+ 4, /* jump_align. */
+ 4, /* loop_align. */
+ 2, /* int_reassoc_width. */
+ 4, /* fp_reassoc_width. */
+ 1, /* vec_reassoc_width. */
+ 2, /* min_div_recip_mul_sf. */
+ 2, /* min_div_recip_mul_df. */
+ 48, /* max_case_values. */
+ 64, /* cache_line_size. */
+ tune_params::AUTOPREFETCHER_OFF, /* autoprefetcher_model. */
+ (AARCH64_EXTRA_TUNE_NONE) /* tune_flags. */
+};
+
static const struct tune_params thunderx_tunings =
{
&thunderx_extra_costs,
@@ -4757,13 +4823,75 @@ aarch64_legitimize_address (rtx x, rtx /* orig_x */, machine_mode mode)
We try to pick as large a range for the offset as possible to
maximize the chance of a CSE. However, for aligned addresses
we limit the range to 4k so that structures with different sized
- elements are likely to use the same base. */
+ elements are likely to use the same base. We need to be careful
+ not to split a CONST for some forms of address expression, otherwise
+ it will generate sub-optimal code. */
if (GET_CODE (x) == PLUS && CONST_INT_P (XEXP (x, 1)))
{
HOST_WIDE_INT offset = INTVAL (XEXP (x, 1));
HOST_WIDE_INT base_offset;
+ if (GET_CODE (XEXP (x, 0)) == PLUS)
+ {
+ rtx op0 = XEXP (XEXP (x, 0), 0);
+ rtx op1 = XEXP (XEXP (x, 0), 1);
+
+ /* Address expressions of the form Ra + Rb + CONST.
+
+ If CONST is within the range supported by the addressing
+ mode "reg+offset", do not split CONST and use the
+ sequence
+ Rt = Ra + Rb;
+ addr = Rt + CONST. */
+ if (REG_P (op0) && REG_P (op1))
+ {
+ machine_mode addr_mode = GET_MODE (x);
+ rtx base = gen_reg_rtx (addr_mode);
+ rtx addr = plus_constant (addr_mode, base, offset);
+
+ if (aarch64_legitimate_address_hook_p (mode, addr, false))
+ {
+ emit_insn (gen_adddi3 (base, op0, op1));
+ return addr;
+ }
+ }
+ /* Address expressions of the form Ra + Rb<<SCALE + CONST.
+
+ If Reg + Rb<<SCALE is a valid address expression, do not
+ split CONST and use the sequence
+ Rc = CONST;
+ Rt = Ra + Rc;
+ addr = Rt + Rb<<SCALE.
+
+ Here we split CONST out of memory referece because:
+ a) We depend on GIMPLE optimizers to pick up common sub
+ expression involving the scaling operation.
+ b) The index Rb is likely a loop iv, it's better to split
+ the CONST so that computation of new base Rt is a loop
+ invariant and can be moved out of loop. This is more
+ important when the original base Ra is sfp related. */
+ else if (REG_P (op0) || REG_P (op1))
+ {
+ machine_mode addr_mode = GET_MODE (x);
+ rtx base = gen_reg_rtx (addr_mode);
+
+ /* Switch to make sure that register is in op0. */
+ if (REG_P (op1))
+ std::swap (op0, op1);
+
+ rtx addr = gen_rtx_PLUS (addr_mode, op1, base);
+
+ if (aarch64_legitimate_address_hook_p (mode, addr, false))
+ {
+ base = force_operand (plus_constant (addr_mode,
+ op0, offset),
+ NULL_RTX);
+ return gen_rtx_PLUS (addr_mode, op1, base);
+ }
+ }
+ }
+
/* Does it look like we'll need a load/store-pair operation? */
if (GET_MODE_SIZE (mode) > 16
|| mode == TImode)
@@ -7099,26 +7227,27 @@ aarch64_memory_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
return aarch64_tune_params.memmov_cost;
}
+/* Return true if it is safe and beneficial to use the rsqrt optabs to
+ optimize 1.0/sqrt. */
+
+static bool
+use_rsqrt_p (void)
+{
+ return (!flag_trapping_math
+ && flag_unsafe_math_optimizations
+ && (aarch64_tune_params.extra_tuning_flags
+ & AARCH64_EXTRA_TUNE_RECIP_SQRT));
+}
+
/* Function to decide when to use
reciprocal square root builtins. */
static tree
-aarch64_builtin_reciprocal (gcall *call)
+aarch64_builtin_reciprocal (tree fndecl)
{
- if (flag_trapping_math
- || !flag_unsafe_math_optimizations
- || optimize_size
- || ! (aarch64_tune_params.extra_tuning_flags
- & AARCH64_EXTRA_TUNE_RECIP_SQRT))
- return NULL_TREE;
-
- if (gimple_call_internal_p (call))
+ if (!use_rsqrt_p ())
return NULL_TREE;
-
- tree fndecl = gimple_call_fndecl (call);
- enum built_in_function fn = DECL_FUNCTION_CODE (fndecl);
- bool md_fn = DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD;
- return aarch64_builtin_rsqrt (fn, md_fn);
+ return aarch64_builtin_rsqrt (DECL_FUNCTION_CODE (fndecl));
}
typedef rtx (*rsqrte_type) (rtx, rtx);
@@ -13546,6 +13675,23 @@ aarch64_promoted_type (const_tree t)
return float_type_node;
return NULL_TREE;
}
+
+/* Implement the TARGET_OPTAB_SUPPORTED_P hook. */
+
+static bool
+aarch64_optab_supported_p (int op, machine_mode, machine_mode,
+ optimization_type opt_type)
+{
+ switch (op)
+ {
+ case rsqrt_optab:
+ return opt_type == OPTIMIZE_FOR_SPEED && use_rsqrt_p ();
+
+ default:
+ return true;
+ }
+}
+
#undef TARGET_ADDRESS_COST
#define TARGET_ADDRESS_COST aarch64_address_cost
@@ -13866,6 +14012,9 @@ aarch64_promoted_type (const_tree t)
#undef TARGET_PRINT_OPERAND_ADDRESS
#define TARGET_PRINT_OPERAND_ADDRESS aarch64_print_operand_address
+#undef TARGET_OPTAB_SUPPORTED_P
+#define TARGET_OPTAB_SUPPORTED_P aarch64_optab_supported_p
+
struct gcc_target targetm = TARGET_INITIALIZER;
#include "gt-aarch64.h"
diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md
index 64a40ae3175..765df6a305e 100644
--- a/gcc/config/aarch64/aarch64.md
+++ b/gcc/config/aarch64/aarch64.md
@@ -4569,6 +4569,17 @@
[(set_attr "type" "f_minmax<s>")]
)
+;; Scalar forms for the IEEE-754 fmax()/fmin() functions
+(define_insn "<fmaxmin><mode>3"
+ [(set (match_operand:GPF 0 "register_operand" "=w")
+ (unspec:GPF [(match_operand:GPF 1 "register_operand" "w")
+ (match_operand:GPF 2 "register_operand" "w")]
+ FMAXMIN))]
+ "TARGET_FLOAT"
+ "<fmaxmin_op>\\t%<s>0, %<s>1, %<s>2"
+ [(set_attr "type" "f_minmax<s>")]
+)
+
;; For copysign (x, y), we want to generate:
;;
;; LDR d2, #(1 << 63)
diff --git a/gcc/config/aarch64/iterators.md b/gcc/config/aarch64/iterators.md
index 9343c9cd1c8..8bdd2648f89 100644
--- a/gcc/config/aarch64/iterators.md
+++ b/gcc/config/aarch64/iterators.md
@@ -306,6 +306,8 @@
UNSPEC_VEC_SHR ; Used in aarch64-simd.md.
UNSPEC_SQRDMLAH ; Used in aarch64-simd.md.
UNSPEC_SQRDMLSH ; Used in aarch64-simd.md.
+ UNSPEC_FMAXNM ; Used in aarch64-simd.md.
+ UNSPEC_FMINNM ; Used in aarch64-simd.md.
])
;; ------------------------------------------------------------------
@@ -948,6 +950,8 @@
(define_int_iterator FMAXMIN_UNS [UNSPEC_FMAX UNSPEC_FMIN])
+(define_int_iterator FMAXMIN [UNSPEC_FMAXNM UNSPEC_FMINNM])
+
(define_int_iterator VQDMULH [UNSPEC_SQDMULH UNSPEC_SQRDMULH])
(define_int_iterator USSUQADD [UNSPEC_SUQADD UNSPEC_USQADD])
@@ -1040,6 +1044,12 @@
(UNSPEC_FMINNMV "fminnm")
(UNSPEC_FMINV "fmin")])
+(define_int_attr fmaxmin [(UNSPEC_FMAXNM "fmax")
+ (UNSPEC_FMINNM "fmin")])
+
+(define_int_attr fmaxmin_op [(UNSPEC_FMAXNM "fmaxnm")
+ (UNSPEC_FMINNM "fminnm")])
+
(define_int_attr sur [(UNSPEC_SHADD "s") (UNSPEC_UHADD "u")
(UNSPEC_SRHADD "sr") (UNSPEC_URHADD "ur")
(UNSPEC_SHSUB "s") (UNSPEC_UHSUB "u")
diff --git a/gcc/config/arm/aarch-cost-tables.h b/gcc/config/arm/aarch-cost-tables.h
index 66e09a8b5db..850bde060b0 100644
--- a/gcc/config/arm/aarch-cost-tables.h
+++ b/gcc/config/arm/aarch-cost-tables.h
@@ -331,6 +331,109 @@ const struct cpu_cost_table cortexa57_extra_costs =
}
};
+const struct cpu_cost_table exynosm1_extra_costs =
+{
+ /* ALU */
+ {
+ 0, /* arith. */
+ 0, /* logical. */
+ 0, /* shift. */
+ COSTS_N_INSNS (0), /* shift_reg. */
+ 0, /* arith_shift. */
+ COSTS_N_INSNS (1), /* arith_shift_reg. */
+ 0, /* log_shift. */
+ COSTS_N_INSNS (1), /* log_shift_reg. */
+ 0, /* extend. */
+ COSTS_N_INSNS (1), /* extend_arith. */
+ 0, /* bfi. */
+ 0, /* bfx. */
+ 0, /* clz. */
+ 0, /* rev. */
+ 0, /* non_exec. */
+ true /* non_exec_costs_exec. */
+ },
+ {
+ /* MULT SImode */
+ {
+ COSTS_N_INSNS (2), /* simple. */
+ COSTS_N_INSNS (3), /* flag_setting. */
+ COSTS_N_INSNS (4), /* extend. */
+ COSTS_N_INSNS (2), /* add. */
+ COSTS_N_INSNS (4), /* extend_add. */
+ COSTS_N_INSNS (19) /* idiv. */
+ },
+ /* MULT DImode */
+ {
+ COSTS_N_INSNS (3), /* simple. */
+ 0, /* flag_setting (N/A). */
+ COSTS_N_INSNS (4), /* extend. */
+ COSTS_N_INSNS (3), /* add. */
+ COSTS_N_INSNS (4), /* extend_add. */
+ COSTS_N_INSNS (35) /* idiv. */
+ }
+ },
+ /* LD/ST */
+ {
+ COSTS_N_INSNS (3), /* load. */
+ COSTS_N_INSNS (4), /* load_sign_extend. */
+ COSTS_N_INSNS (3), /* ldrd. */
+ COSTS_N_INSNS (2), /* ldm_1st. */
+ 1, /* ldm_regs_per_insn_1st. */
+ 2, /* ldm_regs_per_insn_subsequent. */
+ COSTS_N_INSNS (4), /* loadf. */
+ COSTS_N_INSNS (4), /* loadd. */
+ COSTS_N_INSNS (4), /* load_unaligned. */
+ 0, /* store. */
+ 0, /* strd. */
+ 0, /* stm_1st. */
+ 1, /* stm_regs_per_insn_1st. */
+ 2, /* stm_regs_per_insn_subsequent. */
+ 0, /* storef. */
+ 0, /* stored. */
+ 0, /* store_unaligned. */
+ COSTS_N_INSNS (1), /* loadv. */
+ COSTS_N_INSNS (1) /* storev. */
+ },
+ {
+ /* FP SFmode */
+ {
+ COSTS_N_INSNS (21), /* div. */
+ COSTS_N_INSNS (3), /* mult. */
+ COSTS_N_INSNS (4), /* mult_addsub. */
+ COSTS_N_INSNS (4), /* fma. */
+ COSTS_N_INSNS (2), /* addsub. */
+ COSTS_N_INSNS (0), /* fpconst. */
+ COSTS_N_INSNS (0), /* neg. */
+ COSTS_N_INSNS (3), /* compare. */
+ COSTS_N_INSNS (2), /* widen. */
+ COSTS_N_INSNS (2), /* narrow. */
+ COSTS_N_INSNS (12), /* toint. */
+ COSTS_N_INSNS (7), /* fromint. */
+ COSTS_N_INSNS (2) /* roundint. */
+ },
+ /* FP DFmode */
+ {
+ COSTS_N_INSNS (34), /* div. */
+ COSTS_N_INSNS (3), /* mult. */
+ COSTS_N_INSNS (4), /* mult_addsub. */
+ COSTS_N_INSNS (4), /* fma. */
+ COSTS_N_INSNS (2), /* addsub. */
+ COSTS_N_INSNS (0), /* fpconst. */
+ COSTS_N_INSNS (0), /* neg. */
+ COSTS_N_INSNS (3), /* compare. */
+ COSTS_N_INSNS (2), /* widen. */
+ COSTS_N_INSNS (2), /* narrow. */
+ COSTS_N_INSNS (12), /* toint. */
+ COSTS_N_INSNS (7), /* fromint. */
+ COSTS_N_INSNS (2) /* roundint. */
+ }
+ },
+ /* Vector */
+ {
+ COSTS_N_INSNS (0) /* alu. */
+ }
+};
+
const struct cpu_cost_table xgene1_extra_costs =
{
/* ALU */
diff --git a/gcc/config/arm/arm-c.c b/gcc/config/arm/arm-c.c
index c336a167086..7dee28ec52d 100644
--- a/gcc/config/arm/arm-c.c
+++ b/gcc/config/arm/arm-c.c
@@ -66,8 +66,8 @@ arm_cpu_builtins (struct cpp_reader* pfile)
def_or_undef_macro (pfile, "__ARM_FEATURE_SAT", TARGET_ARM_SAT);
def_or_undef_macro (pfile, "__ARM_FEATURE_CRYPTO", TARGET_CRYPTO);
- if (unaligned_access)
- builtin_define ("__ARM_FEATURE_UNALIGNED");
+ def_or_undef_macro (pfile, "__ARM_FEATURE_UNALIGNED", unaligned_access);
+
if (TARGET_CRC32)
builtin_define ("__ARM_FEATURE_CRC32");
diff --git a/gcc/config/arm/arm-cores.def b/gcc/config/arm/arm-cores.def
index d09707b6ed0..642c840bed7 100644
--- a/gcc/config/arm/arm-cores.def
+++ b/gcc/config/arm/arm-cores.def
@@ -169,7 +169,7 @@ ARM_CORE("cortex-a35", cortexa35, cortexa53, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED
ARM_CORE("cortex-a53", cortexa53, cortexa53, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), cortex_a53)
ARM_CORE("cortex-a57", cortexa57, cortexa57, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), cortex_a57)
ARM_CORE("cortex-a72", cortexa72, cortexa57, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), cortex_a57)
-ARM_CORE("exynos-m1", exynosm1, cortexa57, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), cortex_a57)
+ARM_CORE("exynos-m1", exynosm1, exynosm1, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), exynosm1)
ARM_CORE("qdf24xx", qdf24xx, cortexa57, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_CRC32 | FL_FOR_ARCH8A), cortex_a57)
ARM_CORE("xgene1", xgene1, xgene1, 8A, ARM_FSET_MAKE_CPU1 (FL_LDSCHED | FL_FOR_ARCH8A), xgene1)
diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c
index e0cdc209734..42bf27223ef 100644
--- a/gcc/config/arm/arm.c
+++ b/gcc/config/arm/arm.c
@@ -2006,6 +2006,29 @@ const struct tune_params arm_cortex_a57_tune =
tune_params::SCHED_AUTOPREF_FULL
};
+const struct tune_params arm_exynosm1_tune =
+{
+ arm_9e_rtx_costs,
+ &exynosm1_extra_costs,
+ NULL, /* Sched adj cost. */
+ arm_default_branch_cost,
+ &arm_default_vec_cost,
+ 1, /* Constant limit. */
+ 2, /* Max cond insns. */
+ 8, /* Memset max inline. */
+ 3, /* Issue rate. */
+ ARM_PREFETCH_NOT_BENEFICIAL,
+ tune_params::PREF_CONST_POOL_FALSE,
+ tune_params::PREF_LDRD_TRUE,
+ tune_params::LOG_OP_NON_SHORT_CIRCUIT_FALSE, /* Thumb. */
+ tune_params::LOG_OP_NON_SHORT_CIRCUIT_FALSE, /* ARM. */
+ tune_params::DISPARAGE_FLAGS_ALL,
+ tune_params::PREF_NEON_64_FALSE,
+ tune_params::PREF_NEON_STRINGOPS_TRUE,
+ tune_params::FUSE_NOTHING,
+ tune_params::SCHED_AUTOPREF_OFF
+};
+
const struct tune_params arm_xgene1_tune =
{
arm_9e_rtx_costs,
@@ -2876,6 +2899,28 @@ arm_option_override_internal (struct gcc_options *opts,
if (!TARGET_THUMB2_P (opts->x_target_flags))
opts->x_arm_restrict_it = 0;
+ /* Enable -munaligned-access by default for
+ - all ARMv6 architecture-based processors when compiling for a 32-bit ISA
+ i.e. Thumb2 and ARM state only.
+ - ARMv7-A, ARMv7-R, and ARMv7-M architecture-based processors.
+ - ARMv8 architecture-base processors.
+
+ Disable -munaligned-access by default for
+ - all pre-ARMv6 architecture-based processors
+ - ARMv6-M architecture-based processors. */
+
+ if (! opts_set->x_unaligned_access)
+ {
+ opts->x_unaligned_access = (TARGET_32BIT_P (opts->x_target_flags)
+ && arm_arch6 && (arm_arch_notm || arm_arch7));
+ }
+ else if (opts->x_unaligned_access == 1
+ && !(arm_arch6 && (arm_arch_notm || arm_arch7)))
+ {
+ warning (0, "target CPU does not support unaligned accesses");
+ opts->x_unaligned_access = 0;
+ }
+
/* Don't warn since it's on by default in -O2. */
if (TARGET_THUMB1_P (opts->x_target_flags))
opts->x_flag_schedule_insns = 0;
@@ -3281,30 +3326,6 @@ arm_option_override (void)
fix_cm3_ldrd = 0;
}
- /* Enable -munaligned-access by default for
- - all ARMv6 architecture-based processors when compiling for a 32-bit ISA
- i.e. Thumb2 and ARM state only.
- - ARMv7-A, ARMv7-R, and ARMv7-M architecture-based processors.
- - ARMv8 architecture-base processors.
-
- Disable -munaligned-access by default for
- - all pre-ARMv6 architecture-based processors
- - ARMv6-M architecture-based processors. */
-
- if (unaligned_access == 2)
- {
- if (TARGET_32BIT && arm_arch6 && (arm_arch_notm || arm_arch7))
- unaligned_access = 1;
- else
- unaligned_access = 0;
- }
- else if (unaligned_access == 1
- && !(arm_arch6 && (arm_arch_notm || arm_arch7)))
- {
- warning (0, "target CPU does not support unaligned accesses");
- unaligned_access = 0;
- }
-
/* Hot/Cold partitioning is not currently supported, since we can't
handle literal pool placement in that case. */
if (flag_reorder_blocks_and_partition)
diff --git a/gcc/config/arm/arm.h b/gcc/config/arm/arm.h
index 6ed8ad3823e..fd999dd0941 100644
--- a/gcc/config/arm/arm.h
+++ b/gcc/config/arm/arm.h
@@ -131,6 +131,7 @@ extern void (*arm_lang_output_object_attributes_hook)(void);
#define TARGET_ARM_P(flags) (!TARGET_THUMB_P (flags))
#define TARGET_THUMB1_P(flags) (TARGET_THUMB_P (flags) && !arm_arch_thumb2)
#define TARGET_THUMB2_P(flags) (TARGET_THUMB_P (flags) && arm_arch_thumb2)
+#define TARGET_32BIT_P(flags) (TARGET_ARM_P (flags) || TARGET_THUMB2_P (flags))
/* Run-time Target Specification. */
#define TARGET_SOFT_FLOAT (arm_float_abi == ARM_FLOAT_ABI_SOFT)
diff --git a/gcc/config/arm/arm.opt b/gcc/config/arm/arm.opt
index 6f2db8f3a0d..1e438a9c092 100644
--- a/gcc/config/arm/arm.opt
+++ b/gcc/config/arm/arm.opt
@@ -267,7 +267,7 @@ Avoid overlapping destination and address registers on LDRD instructions
that may trigger Cortex-M3 errata.
munaligned-access
-Target Report Var(unaligned_access) Init(2)
+Target Report Var(unaligned_access) Init(2) Save
Enable unaligned word and halfword accesses to packed data.
mneon-for-64bits
diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
index 23a42734007..4247af353ac 100644
--- a/gcc/config/i386/i386.c
+++ b/gcc/config/i386/i386.c
@@ -42676,66 +42676,36 @@ ix86_vectorize_builtin_scatter (const_tree vectype,
return ix86_builtins[code];
}
+/* Return true if it is safe to use the rsqrt optabs to optimize
+ 1.0/sqrt. */
+
+static bool
+use_rsqrt_p ()
+{
+ return (TARGET_SSE_MATH
+ && flag_finite_math_only
+ && !flag_trapping_math
+ && flag_unsafe_math_optimizations);
+}
+
/* Returns a code for a target-specific builtin that implements
reciprocal of the function, or NULL_TREE if not available. */
static tree
-ix86_builtin_reciprocal (gcall *call)
+ix86_builtin_reciprocal (tree fndecl)
{
- if (! (TARGET_SSE_MATH && !optimize_insn_for_size_p ()
- && flag_finite_math_only && !flag_trapping_math
- && flag_unsafe_math_optimizations))
- return NULL_TREE;
-
- if (gimple_call_internal_p (call))
- switch (gimple_call_internal_fn (call))
- {
- tree type;
- case IFN_SQRT:
- type = TREE_TYPE (gimple_call_lhs (call));
- switch (TYPE_MODE (type))
- {
- /* Vectorized version of sqrt to rsqrt conversion. */
- case V4SFmode:
- return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR);
-
- case V8SFmode:
- return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR256);
-
- default:
- return NULL_TREE;
- }
-
- default:
- return NULL_TREE;
- }
-
- tree fndecl = gimple_call_fndecl (call);
- if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
- /* Machine dependent builtins. */
- switch (DECL_FUNCTION_CODE (fndecl))
- {
- /* Vectorized version of sqrt to rsqrt conversion. */
- case IX86_BUILTIN_SQRTPS_NR:
- return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR);
-
- case IX86_BUILTIN_SQRTPS_NR256:
- return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR256);
+ switch (DECL_FUNCTION_CODE (fndecl))
+ {
+ /* Vectorized version of sqrt to rsqrt conversion. */
+ case IX86_BUILTIN_SQRTPS_NR:
+ return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR);
- default:
- return NULL_TREE;
- }
- else
- /* Normal builtins. */
- switch (DECL_FUNCTION_CODE (fndecl))
- {
- /* Sqrt to rsqrt conversion. */
- case BUILT_IN_SQRTF:
- return ix86_get_builtin (IX86_BUILTIN_RSQRTF);
+ case IX86_BUILTIN_SQRTPS_NR256:
+ return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR256);
- default:
- return NULL_TREE;
- }
+ default:
+ return NULL_TREE;
+ }
}
/* Helper for avx_vpermilps256_operand et al. This is also used by
@@ -45267,8 +45237,9 @@ ix86_mitigate_rop (void)
COPY_HARD_REG_SET (inout_risky, input_risky);
IOR_HARD_REG_SET (inout_risky, output_risky);
- compute_bb_for_insn ();
df_note_add_problem ();
+ /* Fix up what stack-regs did. */
+ df_insn_rescan_all ();
df_analyze ();
regrename_init (true);
@@ -49365,6 +49336,57 @@ expand_vec_perm_pshufb (struct expand_vec_perm_d *d)
return true;
}
+/* For V*[QHS]Imode permutations, check if the same permutation
+ can't be performed in a 2x, 4x or 8x wider inner mode. */
+
+static bool
+canonicalize_vector_int_perm (const struct expand_vec_perm_d *d,
+ struct expand_vec_perm_d *nd)
+{
+ int i;
+ enum machine_mode mode = VOIDmode;
+
+ switch (d->vmode)
+ {
+ case V16QImode: mode = V8HImode; break;
+ case V32QImode: mode = V16HImode; break;
+ case V64QImode: mode = V32HImode; break;
+ case V8HImode: mode = V4SImode; break;
+ case V16HImode: mode = V8SImode; break;
+ case V32HImode: mode = V16SImode; break;
+ case V4SImode: mode = V2DImode; break;
+ case V8SImode: mode = V4DImode; break;
+ case V16SImode: mode = V8DImode; break;
+ default: return false;
+ }
+ for (i = 0; i < d->nelt; i += 2)
+ if ((d->perm[i] & 1) || d->perm[i + 1] != d->perm[i] + 1)
+ return false;
+ nd->vmode = mode;
+ nd->nelt = d->nelt / 2;
+ for (i = 0; i < nd->nelt; i++)
+ nd->perm[i] = d->perm[2 * i] / 2;
+ if (GET_MODE_INNER (mode) != DImode)
+ canonicalize_vector_int_perm (nd, nd);
+ if (nd != d)
+ {
+ nd->one_operand_p = d->one_operand_p;
+ nd->testing_p = d->testing_p;
+ if (d->op0 == d->op1)
+ nd->op0 = nd->op1 = gen_lowpart (nd->vmode, d->op0);
+ else
+ {
+ nd->op0 = gen_lowpart (nd->vmode, d->op0);
+ nd->op1 = gen_lowpart (nd->vmode, d->op1);
+ }
+ if (d->testing_p)
+ nd->target = gen_raw_REG (nd->vmode, LAST_VIRTUAL_REGISTER + 1);
+ else
+ nd->target = gen_reg_rtx (nd->vmode);
+ }
+ return true;
+}
+
/* A subroutine of ix86_expand_vec_perm_builtin_1. Try to instantiate D
in a single instruction. */
@@ -49372,7 +49394,7 @@ static bool
expand_vec_perm_1 (struct expand_vec_perm_d *d)
{
unsigned i, nelt = d->nelt;
- unsigned char perm2[MAX_VECT_LEN];
+ struct expand_vec_perm_d nd;
/* Check plain VEC_SELECT first, because AVX has instructions that could
match both SEL and SEL+CONCAT, but the plain SEL will allow a memory
@@ -49385,10 +49407,10 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
for (i = 0; i < nelt; i++)
{
- perm2[i] = d->perm[i] & mask;
- if (perm2[i] != i)
+ nd.perm[i] = d->perm[i] & mask;
+ if (nd.perm[i] != i)
identity_perm = false;
- if (perm2[i])
+ if (nd.perm[i])
broadcast_perm = false;
}
@@ -49457,7 +49479,7 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
}
}
- if (expand_vselect (d->target, d->op0, perm2, nelt, d->testing_p))
+ if (expand_vselect (d->target, d->op0, nd.perm, nelt, d->testing_p))
return true;
/* There are plenty of patterns in sse.md that are written for
@@ -49468,10 +49490,10 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
every other permutation operand. */
for (i = 0; i < nelt; i += 2)
{
- perm2[i] = d->perm[i] & mask;
- perm2[i + 1] = (d->perm[i + 1] & mask) + nelt;
+ nd.perm[i] = d->perm[i] & mask;
+ nd.perm[i + 1] = (d->perm[i + 1] & mask) + nelt;
}
- if (expand_vselect_vconcat (d->target, d->op0, d->op0, perm2, nelt,
+ if (expand_vselect_vconcat (d->target, d->op0, d->op0, nd.perm, nelt,
d->testing_p))
return true;
@@ -49480,13 +49502,13 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
{
for (i = 0; i < nelt; i += 4)
{
- perm2[i + 0] = d->perm[i + 0] & mask;
- perm2[i + 1] = d->perm[i + 1] & mask;
- perm2[i + 2] = (d->perm[i + 2] & mask) + nelt;
- perm2[i + 3] = (d->perm[i + 3] & mask) + nelt;
+ nd.perm[i + 0] = d->perm[i + 0] & mask;
+ nd.perm[i + 1] = d->perm[i + 1] & mask;
+ nd.perm[i + 2] = (d->perm[i + 2] & mask) + nelt;
+ nd.perm[i + 3] = (d->perm[i + 3] & mask) + nelt;
}
- if (expand_vselect_vconcat (d->target, d->op0, d->op0, perm2, nelt,
+ if (expand_vselect_vconcat (d->target, d->op0, d->op0, nd.perm, nelt,
d->testing_p))
return true;
}
@@ -49507,10 +49529,10 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
e -= nelt;
else
e += nelt;
- perm2[i] = e;
+ nd.perm[i] = e;
}
- if (expand_vselect_vconcat (d->target, d->op1, d->op0, perm2, nelt,
+ if (expand_vselect_vconcat (d->target, d->op1, d->op0, nd.perm, nelt,
d->testing_p))
return true;
}
@@ -49536,6 +49558,14 @@ expand_vec_perm_1 (struct expand_vec_perm_d *d)
if (ix86_expand_vec_perm_vpermi2 (NULL_RTX, NULL_RTX, NULL_RTX, NULL_RTX, d))
return true;
+ /* See if we can get the same permutation in different vector integer
+ mode. */
+ if (canonicalize_vector_int_perm (d, &nd) && expand_vec_perm_1 (&nd))
+ {
+ if (!d->testing_p)
+ emit_move_insn (d->target, gen_lowpart (d->vmode, nd.target));
+ return true;
+ }
return false;
}
@@ -50968,7 +50998,7 @@ expand_vec_perm_even_odd_1 (struct expand_vec_perm_d *d, unsigned odd)
struct expand_vec_perm_d d_copy = *d;
d_copy.vmode = V4DFmode;
if (d->testing_p)
- d_copy.target = gen_lowpart (V4DFmode, d->target);
+ d_copy.target = gen_raw_REG (V4DFmode, LAST_VIRTUAL_REGISTER + 1);
else
d_copy.target = gen_reg_rtx (V4DFmode);
d_copy.op0 = gen_lowpart (V4DFmode, d->op0);
@@ -51007,7 +51037,7 @@ expand_vec_perm_even_odd_1 (struct expand_vec_perm_d *d, unsigned odd)
struct expand_vec_perm_d d_copy = *d;
d_copy.vmode = V8SFmode;
if (d->testing_p)
- d_copy.target = gen_lowpart (V8SFmode, d->target);
+ d_copy.target = gen_raw_REG (V8SFmode, LAST_VIRTUAL_REGISTER + 1);
else
d_copy.target = gen_reg_rtx (V8SFmode);
d_copy.op0 = gen_lowpart (V8SFmode, d->op0);
@@ -51451,6 +51481,16 @@ ix86_expand_vec_perm_const_1 (struct expand_vec_perm_d *d)
if (expand_vec_perm_vpshufb4_vpermq2 (d))
return true;
+ /* See if we can get the same permutation in different vector integer
+ mode. */
+ struct expand_vec_perm_d nd;
+ if (canonicalize_vector_int_perm (d, &nd) && expand_vec_perm_1 (&nd))
+ {
+ if (!d->testing_p)
+ emit_move_insn (d->target, gen_lowpart (d->vmode, nd.target));
+ return true;
+ }
+
return false;
}
@@ -54100,6 +54140,52 @@ ix86_operands_ok_for_move_multiple (rtx *operands, bool load,
return true;
}
+/* Implement the TARGET_OPTAB_SUPPORTED_P hook. */
+
+static bool
+ix86_optab_supported_p (int op, machine_mode mode1, machine_mode,
+ optimization_type opt_type)
+{
+ switch (op)
+ {
+ case asin_optab:
+ case acos_optab:
+ case log1p_optab:
+ case exp_optab:
+ case exp10_optab:
+ case exp2_optab:
+ case expm1_optab:
+ case ldexp_optab:
+ case scalb_optab:
+ case round_optab:
+ return opt_type == OPTIMIZE_FOR_SPEED;
+
+ case rint_optab:
+ if (SSE_FLOAT_MODE_P (mode1)
+ && TARGET_SSE_MATH
+ && !flag_trapping_math
+ && !TARGET_ROUND)
+ return opt_type == OPTIMIZE_FOR_SPEED;
+ return true;
+
+ case floor_optab:
+ case ceil_optab:
+ case btrunc_optab:
+ if (SSE_FLOAT_MODE_P (mode1)
+ && TARGET_SSE_MATH
+ && !flag_trapping_math
+ && TARGET_ROUND)
+ return true;
+ return opt_type == OPTIMIZE_FOR_SPEED;
+
+ case rsqrt_optab:
+ return opt_type == OPTIMIZE_FOR_SPEED && use_rsqrt_p ();
+
+ default:
+ return true;
+ }
+}
+
/* Address space support.
This is not "far pointers" in the 16-bit sense, but an easy way
@@ -54645,6 +54731,9 @@ ix86_addr_space_zero_address_valid (addr_space_t as)
#undef TARGET_ABSOLUTE_BIGGEST_ALIGNMENT
#define TARGET_ABSOLUTE_BIGGEST_ALIGNMENT 512
+#undef TARGET_OPTAB_SUPPORTED_P
+#define TARGET_OPTAB_SUPPORTED_P ix86_optab_supported_p
+
struct gcc_target targetm = TARGET_INITIALIZER;
#include "gt-i386.h"
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index cbb9ffd86af..f2b20412137 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -12421,6 +12421,7 @@
"lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
[(set_attr "type" "lea")
(set_attr "length_address" "4")
+ (set_attr "modrm_class" "unknown")
(set_attr "mode" "DI")])
(define_insn "set_rip_rex64"
@@ -14726,9 +14727,6 @@
{
int i;
- if (optimize_insn_for_size_p ())
- FAIL;
-
for (i = 2; i < 6; i++)
operands[i] = gen_reg_rtx (XFmode);
@@ -14746,9 +14744,6 @@
rtx op0 = gen_reg_rtx (XFmode);
rtx op1 = gen_reg_rtx (XFmode);
- if (optimize_insn_for_size_p ())
- FAIL;
-
emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
emit_insn (gen_asinxf2 (op0, op1));
emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
@@ -14770,9 +14765,6 @@
{
int i;
- if (optimize_insn_for_size_p ())
- FAIL;
-
for (i = 2; i < 6; i++)
operands[i] = gen_reg_rtx (XFmode);
@@ -14790,9 +14782,6 @@
rtx op0 = gen_reg_rtx (XFmode);
rtx op1 = gen_reg_rtx (XFmode);
- if (optimize_insn_for_size_p ())
- FAIL;
-
emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
emit_insn (gen_acosxf2 (op0, op1));
emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
@@ -14953,9 +14942,6 @@
"TARGET_USE_FANCY_MATH_387
&& flag_unsafe_math_optimizations"
{
- if (optimize_insn_for_size_p ())
- FAIL;
-
ix86_emit_i387_log1p (operands[0], operands[1]);
DONE;
})
@@ -14970,9 +14956,6 @@
{
rtx op0;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
@@ -15121,9 +15104,6 @@
{
int i;
- if (optimize_insn_for_size_p ())
- FAIL;
-
for (i = 3; i < 10; i++)
operands[i] = gen_reg_rtx (XFmode);
@@ -15138,9 +15118,6 @@
{
rtx op2;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op2 = gen_reg_rtx (XFmode);
emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
@@ -15158,9 +15135,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
@@ -15178,9 +15152,6 @@
{
rtx op2;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op2 = gen_reg_rtx (XFmode);
emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
@@ -15198,9 +15169,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
@@ -15218,9 +15186,6 @@
{
rtx op2;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op2 = gen_reg_rtx (XFmode);
emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
@@ -15238,9 +15203,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
@@ -15278,9 +15240,6 @@
{
int i;
- if (optimize_insn_for_size_p ())
- FAIL;
-
for (i = 2; i < 13; i++)
operands[i] = gen_reg_rtx (XFmode);
@@ -15300,9 +15259,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
@@ -15320,8 +15276,6 @@
&& flag_unsafe_math_optimizations"
{
rtx tmp1, tmp2;
- if (optimize_insn_for_size_p ())
- FAIL;
tmp1 = gen_reg_rtx (XFmode);
tmp2 = gen_reg_rtx (XFmode);
@@ -15343,9 +15297,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
@@ -15366,9 +15317,6 @@
"TARGET_USE_FANCY_MATH_387
&& flag_unsafe_math_optimizations"
{
- if (optimize_insn_for_size_p ())
- FAIL;
-
operands[3] = gen_reg_rtx (XFmode);
})
@@ -15383,9 +15331,6 @@
{
rtx op0, op1, op2;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
op2 = gen_reg_rtx (XFmode);
@@ -15463,8 +15408,6 @@
if (TARGET_ROUND)
emit_insn (gen_sse4_1_round<mode>2
(operands[0], operands[1], GEN_INT (ROUND_MXCSR)));
- else if (optimize_insn_for_size_p ())
- FAIL;
else
ix86_expand_rint (operands[0], operands[1]);
}
@@ -15491,9 +15434,6 @@
|| (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
&& !flag_trapping_math && !flag_rounding_math)"
{
- if (optimize_insn_for_size_p ())
- FAIL;
-
if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
&& !flag_trapping_math && !flag_rounding_math)
{
@@ -15747,8 +15687,7 @@
FRNDINT_ROUNDING))
(clobber (reg:CC FLAGS_REG))])]
"TARGET_USE_FANCY_MATH_387
- && flag_unsafe_math_optimizations
- && !optimize_insn_for_size_p ()")
+ && flag_unsafe_math_optimizations")
(define_expand "<rounding_insn><mode>2"
[(parallel [(set (match_operand:MODEF 0 "register_operand")
@@ -15768,8 +15707,6 @@
if (TARGET_ROUND)
emit_insn (gen_sse4_1_round<mode>2
(operands[0], operands[1], GEN_INT (ROUND_<ROUNDING>)));
- else if (optimize_insn_for_size_p ())
- FAIL;
else if (TARGET_64BIT || (<MODE>mode != DFmode))
{
if (ROUND_<ROUNDING> == ROUND_FLOOR)
@@ -15797,9 +15734,6 @@
{
rtx op0, op1;
- if (optimize_insn_for_size_p ())
- FAIL;
-
op0 = gen_reg_rtx (XFmode);
op1 = gen_reg_rtx (XFmode);
emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
diff --git a/gcc/config/i386/sse.md b/gcc/config/i386/sse.md
index e7b517aeb6c..680d813472d 100644
--- a/gcc/config/i386/sse.md
+++ b/gcc/config/i386/sse.md
@@ -7534,32 +7534,40 @@
&& rtx_equal_p (operands[2], operands[0])"
"vextract<shuffletype>32x4\t{$0x1, %1, %0%{%3%}|%0%{%3%}, %1, 0x1}"
[(set_attr "type" "sselog1")
- (set_attr "prefix_extra" "1")
(set_attr "length_immediate" "1")
(set_attr "prefix" "evex")
(set_attr "mode" "<sseinsnmode>")])
-(define_insn "vec_extract_hi_<mode><mask_name>"
- [(set (match_operand:<ssehalfvecmode> 0 "<store_mask_predicate>" "=<store_mask_constraint>")
+(define_insn "vec_extract_hi_<mode>_mask"
+ [(set (match_operand:<ssehalfvecmode> 0 "register_operand" "=v")
+ (vec_merge:<ssehalfvecmode>
+ (vec_select:<ssehalfvecmode>
+ (match_operand:VI4F_256 1 "register_operand" "v")
+ (parallel [(const_int 4) (const_int 5)
+ (const_int 6) (const_int 7)]))
+ (match_operand:<ssehalfvecmode> 2 "vector_move_operand" "0C")
+ (match_operand:<avx512fmaskmode> 3 "register_operand" "Yk")))]
+ "TARGET_AVX512VL"
+ "vextract<shuffletype>32x4\t{$0x1, %1, %0%{%3%}%N2|%0%{%3%}%N2, %1, 0x1}"
+ [(set_attr "type" "sselog1")
+ (set_attr "length_immediate" "1")
+ (set_attr "prefix" "evex")
+ (set_attr "mode" "<sseinsnmode>")])
+
+(define_insn "vec_extract_hi_<mode>"
+ [(set (match_operand:<ssehalfvecmode> 0 "nonimmediate_operand" "=xm, vm")
(vec_select:<ssehalfvecmode>
- (match_operand:VI4F_256 1 "register_operand" "v")
+ (match_operand:VI4F_256 1 "register_operand" "x, v")
(parallel [(const_int 4) (const_int 5)
(const_int 6) (const_int 7)])))]
- "TARGET_AVX && <mask_avx512vl_condition>"
-{
- if (TARGET_AVX512VL)
- return "vextract<shuffletype>32x4\t{$0x1, %1, %0<mask_operand2>|%0<mask_operand2>, %1, 0x1}";
- else
- return "vextract<i128>\t{$0x1, %1, %0|%0, %1, 0x1}";
-}
- [(set_attr "type" "sselog1")
- (set_attr "prefix_extra" "1")
+ "TARGET_AVX"
+ "@
+ vextract<i128>\t{$0x1, %1, %0|%0, %1, 0x1}
+ vextract<shuffletype>32x4\t{$0x1, %1, %0|%0, %1, 0x1}"
+ [(set_attr "isa" "*, avx512vl")
+ (set_attr "prefix" "vex, evex")
+ (set_attr "type" "sselog1")
(set_attr "length_immediate" "1")
- (set (attr "prefix")
- (if_then_else
- (match_test "TARGET_AVX512VL")
- (const_string "evex")
- (const_string "vex")))
(set_attr "mode" "<sseinsnmode>")])
(define_insn_and_split "vec_extract_lo_v32hi"
diff --git a/gcc/config/mips/mips.c b/gcc/config/mips/mips.c
index eeb80eb1abb..6145944fbf7 100644
--- a/gcc/config/mips/mips.c
+++ b/gcc/config/mips/mips.c
@@ -11364,11 +11364,12 @@ mips_emit_probe_stack_range (HOST_WIDE_INT first, HOST_WIDE_INT size)
/* Step 3: the loop
- while (TEST_ADDR != LAST_ADDR)
+ do
{
TEST_ADDR = TEST_ADDR + PROBE_INTERVAL
probe at TEST_ADDR
}
+ while (TEST_ADDR != LAST_ADDR)
probes at FIRST + N * PROBE_INTERVAL for values of N from 1
until it is equal to ROUNDED_SIZE. */
@@ -11394,38 +11395,31 @@ const char *
mips_output_probe_stack_range (rtx reg1, rtx reg2)
{
static int labelno = 0;
- char loop_lab[32], end_lab[32], tmp[64];
+ char loop_lab[32], tmp[64];
rtx xops[2];
- ASM_GENERATE_INTERNAL_LABEL (loop_lab, "LPSRL", labelno);
- ASM_GENERATE_INTERNAL_LABEL (end_lab, "LPSRE", labelno++);
+ ASM_GENERATE_INTERNAL_LABEL (loop_lab, "LPSRL", labelno++);
+ /* Loop. */
ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, loop_lab);
- /* Jump to END_LAB if TEST_ADDR == LAST_ADDR. */
- xops[0] = reg1;
- xops[1] = reg2;
- strcpy (tmp, "%(%<beq\t%0,%1,");
- output_asm_insn (strcat (tmp, &end_lab[1]), xops);
-
/* TEST_ADDR = TEST_ADDR + PROBE_INTERVAL. */
+ xops[0] = reg1;
xops[1] = GEN_INT (-PROBE_INTERVAL);
if (TARGET_64BIT && TARGET_LONG64)
output_asm_insn ("daddiu\t%0,%0,%1", xops);
else
output_asm_insn ("addiu\t%0,%0,%1", xops);
- /* Probe at TEST_ADDR and branch. */
- fprintf (asm_out_file, "\tb\t");
- assemble_name_raw (asm_out_file, loop_lab);
- fputc ('\n', asm_out_file);
+ /* Probe at TEST_ADDR, test if TEST_ADDR == LAST_ADDR and branch. */
+ xops[1] = reg2;
+ strcpy (tmp, "%(%<bne\t%0,%1,");
+ output_asm_insn (strcat (tmp, &loop_lab[1]), xops);
if (TARGET_64BIT)
output_asm_insn ("sd\t$0,0(%0)%)", xops);
else
output_asm_insn ("sw\t$0,0(%0)%)", xops);
- ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, end_lab);
-
return "";
}
diff --git a/gcc/config/nvptx/nvptx-protos.h b/gcc/config/nvptx/nvptx-protos.h
index 9fda531bed3..7e0c296e3f0 100644
--- a/gcc/config/nvptx/nvptx-protos.h
+++ b/gcc/config/nvptx/nvptx-protos.h
@@ -24,11 +24,13 @@
extern void nvptx_declare_function_name (FILE *, const char *, const_tree decl);
extern void nvptx_declare_object_name (FILE *file, const char *name,
const_tree decl);
+extern void nvptx_output_aligned_decl (FILE *file, const char *name,
+ const_tree decl,
+ HOST_WIDE_INT size, unsigned align);
extern void nvptx_function_end (FILE *);
extern void nvptx_output_skip (FILE *, unsigned HOST_WIDE_INT);
extern void nvptx_output_ascii (FILE *, const char *, unsigned HOST_WIDE_INT);
extern void nvptx_register_pragmas (void);
-extern const char *nvptx_section_for_decl (const_tree);
#ifdef RTX_CODE
extern void nvptx_expand_oacc_fork (unsigned);
@@ -36,10 +38,9 @@ extern void nvptx_expand_oacc_join (unsigned);
extern void nvptx_expand_call (rtx, rtx);
extern rtx nvptx_expand_compare (rtx);
extern const char *nvptx_ptx_type_from_mode (machine_mode, bool);
+extern const char *nvptx_output_mov_insn (rtx, rtx);
extern const char *nvptx_output_call_insn (rtx_insn *, rtx, rtx);
extern const char *nvptx_output_return (void);
-extern machine_mode nvptx_underlying_object_mode (rtx);
-extern const char *nvptx_section_from_addr_space (addr_space_t);
extern bool nvptx_hard_regno_mode_ok (int, machine_mode);
extern rtx nvptx_maybe_convert_symbolic_operand (rtx);
#endif
diff --git a/gcc/config/nvptx/nvptx.c b/gcc/config/nvptx/nvptx.c
index 899c8566df2..a036f30f51e 100644
--- a/gcc/config/nvptx/nvptx.c
+++ b/gcc/config/nvptx/nvptx.c
@@ -70,10 +70,34 @@
/* This file should be included last. */
#include "target-def.h"
-#define SHUFFLE_UP 0
-#define SHUFFLE_DOWN 1
-#define SHUFFLE_BFLY 2
-#define SHUFFLE_IDX 3
+/* The kind of shuffe instruction. */
+enum nvptx_shuffle_kind
+{
+ SHUFFLE_UP,
+ SHUFFLE_DOWN,
+ SHUFFLE_BFLY,
+ SHUFFLE_IDX,
+ SHUFFLE_MAX
+};
+
+/* The various PTX memory areas an object might reside in. */
+enum nvptx_data_area
+{
+ DATA_AREA_GENERIC,
+ DATA_AREA_GLOBAL,
+ DATA_AREA_SHARED,
+ DATA_AREA_LOCAL,
+ DATA_AREA_CONST,
+ DATA_AREA_PARAM,
+ DATA_AREA_MAX
+};
+
+/* We record the data area in the target symbol flags. */
+#define SYMBOL_DATA_AREA(SYM) \
+ (nvptx_data_area)((SYMBOL_REF_FLAGS (SYM) >> SYMBOL_FLAG_MACH_DEP_SHIFT) \
+ & 7)
+#define SET_SYMBOL_DATA_AREA(SYM,AREA) \
+ (SYMBOL_REF_FLAGS (SYM) |= (AREA) << SYMBOL_FLAG_MACH_DEP_SHIFT)
/* Record the function decls we've written, and the libfuncs and function
decls corresponding to them. */
@@ -149,29 +173,14 @@ nvptx_option_override (void)
= hash_table<declared_libfunc_hasher>::create_ggc (17);
worker_bcast_sym = gen_rtx_SYMBOL_REF (Pmode, worker_bcast_name);
+ SET_SYMBOL_DATA_AREA (worker_bcast_sym, DATA_AREA_SHARED);
worker_bcast_align = GET_MODE_ALIGNMENT (SImode) / BITS_PER_UNIT;
worker_red_sym = gen_rtx_SYMBOL_REF (Pmode, worker_red_name);
+ SET_SYMBOL_DATA_AREA (worker_red_sym, DATA_AREA_SHARED);
worker_red_align = GET_MODE_ALIGNMENT (SImode) / BITS_PER_UNIT;
}
-/* Return the mode to be used when declaring a ptx object for OBJ.
- For objects with subparts such as complex modes this is the mode
- of the subpart. */
-
-machine_mode
-nvptx_underlying_object_mode (rtx obj)
-{
- if (GET_CODE (obj) == SUBREG)
- obj = SUBREG_REG (obj);
- machine_mode mode = GET_MODE (obj);
- if (mode == TImode)
- return DImode;
- if (COMPLEX_MODE_P (mode))
- return GET_MODE_INNER (mode);
- return mode;
-}
-
/* Return a ptx type for MODE. If PROMOTE, then use .u32 for QImode to
deal with ptx ideosyncracies. */
@@ -206,22 +215,49 @@ nvptx_ptx_type_from_mode (machine_mode mode, bool promote)
}
}
-/* Determine the address space to use for SYMBOL_REF SYM. */
+/* Encode the PTX data area that DECL (which might not actually be a
+ _DECL) should reside in. */
-static addr_space_t
-nvptx_addr_space_from_sym (rtx sym)
+static void
+nvptx_encode_section_info (tree decl, rtx rtl, int first)
{
- tree decl = SYMBOL_REF_DECL (sym);
- if (decl == NULL_TREE || TREE_CODE (decl) == FUNCTION_DECL)
- return ADDR_SPACE_GENERIC;
+ default_encode_section_info (decl, rtl, first);
+ if (first && MEM_P (rtl))
+ {
+ nvptx_data_area area = DATA_AREA_GENERIC;
- bool is_const = (CONSTANT_CLASS_P (decl)
- || TREE_CODE (decl) == CONST_DECL
- || TREE_READONLY (decl));
- if (is_const)
- return ADDR_SPACE_CONST;
+ if (TREE_CONSTANT (decl))
+ area = DATA_AREA_CONST;
+ else if (TREE_CODE (decl) == VAR_DECL)
+ /* TODO: This would be a good place to check for a .shared or
+ other section name. */
+ area = TREE_READONLY (decl) ? DATA_AREA_CONST : DATA_AREA_GLOBAL;
- return ADDR_SPACE_GLOBAL;
+ SET_SYMBOL_DATA_AREA (XEXP (rtl, 0), area);
+ }
+}
+
+/* Return the PTX name of the data area in which SYM should be
+ placed. The symbol must have already been processed by
+ nvptx_encode_seciton_info, or equivalent. */
+
+static const char *
+section_for_sym (rtx sym)
+{
+ nvptx_data_area area = SYMBOL_DATA_AREA (sym);
+ /* Same order as nvptx_data_area enum. */
+ static char const *const areas[] =
+ {"", ".global", ".shared", ".local", ".const", ".param"};
+
+ return areas[area];
+}
+
+/* Similarly for a decl. */
+
+static const char *
+section_for_decl (const_tree decl)
+{
+ return section_for_sym (XEXP (DECL_RTL (CONST_CAST (tree, decl)), 0));
}
/* Check NAME for special function names and redirect them by returning a
@@ -257,6 +293,37 @@ maybe_split_mode (machine_mode mode)
return VOIDmode;
}
+/* Output a register, subreg, or register pair (with optional
+ enclosing braces). */
+
+static void
+output_reg (FILE *file, unsigned regno, machine_mode inner_mode,
+ int subreg_offset = -1)
+{
+ if (inner_mode == VOIDmode)
+ {
+ if (HARD_REGISTER_NUM_P (regno))
+ fprintf (file, "%s", reg_names[regno]);
+ else
+ fprintf (file, "%%r%d", regno);
+ }
+ else if (subreg_offset >= 0)
+ {
+ output_reg (file, regno, VOIDmode);
+ fprintf (file, "$%d", subreg_offset);
+ }
+ else
+ {
+ if (subreg_offset == -1)
+ fprintf (file, "{");
+ output_reg (file, regno, inner_mode, GET_MODE_SIZE (inner_mode));
+ fprintf (file, ",");
+ output_reg (file, regno, inner_mode, 0);
+ if (subreg_offset == -1)
+ fprintf (file, "}");
+ }
+}
+
/* Emit forking instructions for MASK. */
static void
@@ -366,6 +433,31 @@ write_as_kernel (tree attrs)
|| lookup_attribute ("omp target entrypoint", attrs) != NULL_TREE);
}
+/* Emit a linker marker for a function decl or defn. */
+
+static void
+write_fn_marker (std::stringstream &s, bool is_defn, bool globalize,
+ const char *name)
+{
+ s << "\n// BEGIN";
+ if (globalize)
+ s << " GLOBAL";
+ s << " FUNCTION " << (is_defn ? "DEF: " : "DECL: ");
+ s << name << "\n";
+}
+
+/* Emit a linker marker for a variable decl or defn. */
+
+static void
+write_var_marker (FILE *file, bool is_defn, bool globalize, const char *name)
+{
+ fprintf (file, "\n// BEGIN%s VAR %s: ",
+ globalize ? " GLOBAL" : "",
+ is_defn ? "DEF" : "DECL");
+ assemble_name_raw (file, name);
+ fputs ("\n", file);
+}
+
/* Write a .func or .kernel declaration or definition along with
a helper comment for use by ld. S is the stream to write to, DECL
the decl for the function with name NAME. For definitions, emit
@@ -386,11 +478,7 @@ write_fn_proto (std::stringstream &s, bool is_defn,
name++;
}
- /* Emit the linker marker. */
- s << "\n// BEGIN";
- if (TREE_PUBLIC (decl))
- s << " GLOBAL";
- s << " FUNCTION " << (is_defn ? "DEF" : "DECL") << ": " << name << "\n";
+ write_fn_marker (s, is_defn, TREE_PUBLIC (decl), name);
/* PTX declaration. */
if (DECL_EXTERNAL (decl))
@@ -500,7 +588,7 @@ write_fn_proto_from_insn (std::stringstream &s, const char *name,
else
{
name = nvptx_name_replacement (name);
- s << "\n// BEGIN GLOBAL FUNCTION DECL: " << name << "\n";
+ write_fn_marker (s, false, true, name);
s << "\t.extern .func ";
}
@@ -703,16 +791,12 @@ nvptx_declare_function_name (FILE *file, const char *name, const_tree decl)
{
machine_mode mode = PSEUDO_REGNO_MODE (i);
machine_mode split = maybe_split_mode (mode);
+
if (split != VOIDmode)
- {
- fprintf (file, "\t.reg%s %%r%d$%d;\n",
- nvptx_ptx_type_from_mode (split, true), i, 0);
- fprintf (file, "\t.reg%s %%r%d$%d;\n",
- nvptx_ptx_type_from_mode (split, true), i, 1);
- }
- else
- fprintf (file, "\t.reg%s %%r%d;\n",
- nvptx_ptx_type_from_mode (mode, true), i);
+ mode = split;
+ fprintf (file, "\t.reg%s ", nvptx_ptx_type_from_mode (mode, true));
+ output_reg (file, i, split, -2);
+ fprintf (file, ";\n");
}
}
@@ -733,15 +817,6 @@ nvptx_declare_function_name (FILE *file, const char *name, const_tree decl)
BITS_PER_WORD);
}
- if (cfun->machine->punning_buffer_size > 0)
- {
- fprintf (file, "\t.reg.u%d %%punbuffer;\n"
- "\t.local.align 8 .b8 %%punbuffer_ar[%d];\n",
- BITS_PER_WORD, cfun->machine->punning_buffer_size);
- fprintf (file, "\tcvta.local.u%d %%punbuffer, %%punbuffer_ar;\n",
- BITS_PER_WORD);
- }
-
/* Declare a local variable for the frame. */
sz = get_frame_size ();
if (sz > 0 || cfun->machine->has_call_with_sc)
@@ -975,15 +1050,13 @@ nvptx_function_incoming_arg (cumulative_args_t cum_v, machine_mode mode,
/* Implement TARGET_FUNCTION_ARG_ADVANCE. */
static void
-nvptx_function_arg_advance (cumulative_args_t cum_v, machine_mode mode,
- const_tree type ATTRIBUTE_UNUSED,
- bool named ATTRIBUTE_UNUSED)
+nvptx_function_arg_advance (cumulative_args_t cum_v,
+ machine_mode ARG_UNUSED (mode),
+ const_tree ARG_UNUSED (type),
+ bool ARG_UNUSED (named))
{
CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
- if (mode == TImode)
- cum->count += 2;
- else
- cum->count++;
+ cum->count++;
}
/* Handle the TARGET_STRICT_ARGUMENT_NAMING target hook.
@@ -1201,7 +1274,7 @@ nvptx_gen_pack (rtx dst, rtx src0, rtx src1)
across the vectors of a single warp. */
static rtx
-nvptx_gen_shuffle (rtx dst, rtx src, rtx idx, unsigned kind)
+nvptx_gen_shuffle (rtx dst, rtx src, rtx idx, nvptx_shuffle_kind kind)
{
rtx res;
@@ -1370,21 +1443,15 @@ nvptx_maybe_convert_symbolic_operand (rtx op)
return op;
nvptx_maybe_record_fnsym (sym);
-
- addr_space_t as = nvptx_addr_space_from_sym (sym);
- if (as == ADDR_SPACE_GENERIC)
- return op;
- enum unspec code;
- code = (as == ADDR_SPACE_GLOBAL ? UNSPEC_FROM_GLOBAL
- : as == ADDR_SPACE_LOCAL ? UNSPEC_FROM_LOCAL
- : as == ADDR_SPACE_SHARED ? UNSPEC_FROM_SHARED
- : as == ADDR_SPACE_CONST ? UNSPEC_FROM_CONST
- : UNSPEC_FROM_PARAM);
+ nvptx_data_area area = SYMBOL_DATA_AREA (sym);
+ if (area == DATA_AREA_GENERIC)
+ return op;
rtx dest = gen_reg_rtx (Pmode);
emit_insn (gen_rtx_SET (dest,
- gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op), code)));
+ gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op),
+ UNSPEC_TO_GENERIC)));
return dest;
}
@@ -1427,45 +1494,6 @@ nvptx_hard_regno_mode_ok (int regno, machine_mode mode)
return mode == cfun->machine->ret_reg_mode;
}
-/* Convert an address space AS to the corresponding ptx string. */
-
-const char *
-nvptx_section_from_addr_space (addr_space_t as)
-{
- switch (as)
- {
- case ADDR_SPACE_CONST:
- return ".const";
-
- case ADDR_SPACE_GLOBAL:
- return ".global";
-
- case ADDR_SPACE_SHARED:
- return ".shared";
-
- case ADDR_SPACE_GENERIC:
- return "";
-
- default:
- gcc_unreachable ();
- }
-}
-
-/* Determine whether DECL goes into .const or .global. */
-
-const char *
-nvptx_section_for_decl (const_tree decl)
-{
- bool is_const = (CONSTANT_CLASS_P (decl)
- || TREE_CODE (decl) == CONST_DECL
- || TREE_READONLY (decl));
- if (is_const)
- return ".const";
-
- return ".global";
-}
-
-
/* Machinery to output constant initializers. When beginning an initializer,
we decide on a chunk size (which is visible in ptx in the type used), and
then all initializer data is buffered until a chunk is filled and ready to
@@ -1640,9 +1668,7 @@ static void
init_output_initializer (FILE *file, const char *name, const_tree type,
bool is_public)
{
- fprintf (file, "\n// BEGIN%s VAR DEF: ", is_public ? " GLOBAL" : "");
- assemble_name_raw (file, name);
- fputc ('\n', file);
+ write_var_marker (file, true, is_public, name);
if (TREE_CODE (type) == ARRAY_TYPE)
type = TREE_TYPE (type);
@@ -1660,6 +1686,26 @@ init_output_initializer (FILE *file, const char *name, const_tree type,
object_finished = false;
}
+/* Output an uninitialized common or file-scope variable. */
+
+void
+nvptx_output_aligned_decl (FILE *file, const char *name,
+ const_tree decl, HOST_WIDE_INT size, unsigned align)
+{
+ write_var_marker (file, true, TREE_PUBLIC (decl), name);
+
+ /* If this is public, it is common. The nearest thing we have to
+ common is weak. */
+ fprintf (file, "\t%s%s .align %d .b8 ",
+ TREE_PUBLIC (decl) ? ".weak " : "",
+ section_for_decl (decl),
+ align / BITS_PER_UNIT);
+ assemble_name (file, name);
+ if (size > 0)
+ fprintf (file, "[" HOST_WIDE_INT_PRINT_DEC"]", size);
+ fprintf (file, ";\n");
+}
+
/* Implement TARGET_ASM_DECLARE_CONSTANT_NAME. Begin the process of
writing a constant variable EXP with NAME and SIZE and its
initializer to FILE. */
@@ -1685,27 +1731,24 @@ nvptx_asm_declare_constant_name (FILE *file, const char *name,
void
nvptx_declare_object_name (FILE *file, const char *name, const_tree decl)
{
- if (decl && DECL_SIZE (decl))
- {
- tree type = TREE_TYPE (decl);
- unsigned HOST_WIDE_INT size;
-
- init_output_initializer (file, name, type, TREE_PUBLIC (decl));
- size = tree_to_uhwi (DECL_SIZE_UNIT (decl));
- const char *section = nvptx_section_for_decl (decl);
- fprintf (file, "\t%s%s .align %d .u%d ",
- !TREE_PUBLIC (decl) ? ""
- : DECL_WEAK (decl) ? ".weak" : ".visible",
- section, DECL_ALIGN (decl) / BITS_PER_UNIT,
- decl_chunk_size * BITS_PER_UNIT);
- assemble_name (file, name);
- if (size > 0)
- fprintf (file, "[" HOST_WIDE_INT_PRINT_DEC "]",
- (size + decl_chunk_size - 1) / decl_chunk_size);
- else
- object_finished = true;
- object_size = size;
- }
+ tree type = TREE_TYPE (decl);
+
+ init_output_initializer (file, name, type, TREE_PUBLIC (decl));
+ fprintf (file, "\t%s%s .align %d .u%d ",
+ !TREE_PUBLIC (decl) ? ""
+ : DECL_WEAK (decl) ? ".weak " : ".visible ",
+ section_for_decl (decl),
+ DECL_ALIGN (decl) / BITS_PER_UNIT,
+ decl_chunk_size * BITS_PER_UNIT);
+ assemble_name (file, name);
+
+ unsigned HOST_WIDE_INT size = tree_to_uhwi (DECL_SIZE_UNIT (decl));
+ if (size > 0)
+ fprintf (file, "[" HOST_WIDE_INT_PRINT_DEC "]",
+ (size + decl_chunk_size - 1) / decl_chunk_size);
+ else
+ object_finished = true;
+ object_size = size;
}
/* Implement TARGET_ASM_GLOBALIZE_LABEL by doing nothing. */
@@ -1717,22 +1760,50 @@ nvptx_globalize_label (FILE *, const char *)
/* Implement TARGET_ASM_ASSEMBLE_UNDEFINED_DECL. Write an extern
declaration only for variable DECL with NAME to FILE. */
+
static void
nvptx_assemble_undefined_decl (FILE *file, const char *name, const_tree decl)
{
- if (TREE_CODE (decl) != VAR_DECL)
- return;
- const char *section = nvptx_section_for_decl (decl);
- fprintf (file, "\n// BEGIN%s VAR DECL: ",
- TREE_PUBLIC (decl) ? " GLOBAL" : "");
+ write_var_marker (file, false, TREE_PUBLIC (decl), name);
+
+ fprintf (file, "\t.extern %s .b8 ", section_for_decl (decl));
assemble_name_raw (file, name);
- fputs ("\n", file);
+
HOST_WIDE_INT size = int_size_in_bytes (TREE_TYPE (decl));
- fprintf (file, ".extern %s .b8 ", section);
- assemble_name_raw (file, name);
if (size > 0)
fprintf (file, "[" HOST_WIDE_INT_PRINT_DEC"]", size);
- fprintf (file, ";\n\n");
+ fprintf (file, ";\n");
+}
+
+/* Output a pattern for a move instruction. */
+
+const char *
+nvptx_output_mov_insn (rtx dst, rtx src)
+{
+ machine_mode dst_mode = GET_MODE (dst);
+ machine_mode dst_inner = (GET_CODE (dst) == SUBREG
+ ? GET_MODE (XEXP (dst, 0)) : dst_mode);
+ machine_mode src_inner = (GET_CODE (src) == SUBREG
+ ? GET_MODE (XEXP (src, 0)) : dst_mode);
+
+ if (REG_P (dst) && REGNO (dst) == NVPTX_RETURN_REGNUM && dst_mode == HImode)
+ /* Special handling for the return register. It's never really an
+ HI object, and only occurs as the destination of a move
+ insn. */
+ dst_inner = SImode;
+
+ if (src_inner == dst_inner)
+ return "%.\tmov%t0\t%0, %1;";
+
+ if (CONSTANT_P (src))
+ return (GET_MODE_CLASS (dst_inner) == MODE_INT
+ && GET_MODE_CLASS (src_inner) != MODE_FLOAT
+ ? "%.\tmov%t0\t%0, %1;" : "%.\tmov.b%T0\t%0, %1;");
+
+ if (GET_MODE_SIZE (dst_inner) == GET_MODE_SIZE (src_inner))
+ return "%.\tmov.b%T0\t%0, %1;";
+
+ return "%.\tcvt%t0%t1\t%0, %1;";
}
/* Output INSN, which is a call to CALLEE with result RESULT. For ptx, this
@@ -1882,9 +1953,9 @@ nvptx_print_operand_address (FILE *file, machine_mode mode, rtx addr)
unconditional one.
# -- print a rounding mode for the instruction
- A -- print an address space identifier for a MEM
+ A -- print a data area for a MEM
c -- print an opcode suffix for a comparison operator, including a type code
- f -- print a full reg even for something that must always be split
+ D -- print a data area for a MEM operand
S -- print a shuffle kind specified by CONST_INT
t -- print a type opcode suffix, promoting QImode to 32 bits
T -- print a type size in bits
@@ -1893,9 +1964,6 @@ nvptx_print_operand_address (FILE *file, machine_mode mode, rtx addr)
static void
nvptx_print_operand (FILE *file, rtx x, int code)
{
- rtx orig_x = x;
- machine_mode op_mode;
-
if (code == '.')
{
x = current_insn_predicate;
@@ -1917,47 +1985,49 @@ nvptx_print_operand (FILE *file, rtx x, int code)
}
enum rtx_code x_code = GET_CODE (x);
+ machine_mode mode = GET_MODE (x);
switch (code)
{
case 'A':
- {
- addr_space_t as = ADDR_SPACE_GENERIC;
- rtx sym = XEXP (x, 0);
-
- if (GET_CODE (sym) == CONST)
- sym = XEXP (sym, 0);
- if (GET_CODE (sym) == PLUS)
- sym = XEXP (sym, 0);
+ x = XEXP (x, 0);
+ /* FALLTHROUGH. */
- if (GET_CODE (sym) == SYMBOL_REF)
- as = nvptx_addr_space_from_sym (sym);
+ case 'D':
+ if (GET_CODE (x) == CONST)
+ x = XEXP (x, 0);
+ if (GET_CODE (x) == PLUS)
+ x = XEXP (x, 0);
- fputs (nvptx_section_from_addr_space (as), file);
- }
+ if (GET_CODE (x) == SYMBOL_REF)
+ fputs (section_for_sym (x), file);
break;
case 't':
- op_mode = nvptx_underlying_object_mode (x);
- fprintf (file, "%s", nvptx_ptx_type_from_mode (op_mode, true));
- break;
-
case 'u':
- op_mode = nvptx_underlying_object_mode (x);
- fprintf (file, "%s", nvptx_ptx_type_from_mode (op_mode, false));
+ if (x_code == SUBREG)
+ {
+ mode = GET_MODE (SUBREG_REG (x));
+ if (mode == TImode)
+ mode = DImode;
+ else if (COMPLEX_MODE_P (mode))
+ mode = GET_MODE_INNER (mode);
+ }
+ fprintf (file, "%s", nvptx_ptx_type_from_mode (mode, code == 't'));
break;
case 'S':
{
- unsigned kind = UINTVAL (x);
+ nvptx_shuffle_kind kind = (nvptx_shuffle_kind) UINTVAL (x);
+ /* Same order as nvptx_shuffle_kind. */
static const char *const kinds[] =
- {"up", "down", "bfly", "idx"};
- fprintf (file, ".%s", kinds[kind]);
+ {".up", ".down", ".bfly", ".idx"};
+ fputs (kinds[kind], file);
}
break;
case 'T':
- fprintf (file, "%d", GET_MODE_BITSIZE (GET_MODE (x)));
+ fprintf (file, "%d", GET_MODE_BITSIZE (mode));
break;
case 'j':
@@ -1969,14 +2039,14 @@ nvptx_print_operand (FILE *file, rtx x, int code)
goto common;
case 'c':
- op_mode = GET_MODE (XEXP (x, 0));
+ mode = GET_MODE (XEXP (x, 0));
switch (x_code)
{
case EQ:
fputs (".eq", file);
break;
case NE:
- if (FLOAT_MODE_P (op_mode))
+ if (FLOAT_MODE_P (mode))
fputs (".neu", file);
else
fputs (".ne", file);
@@ -2032,38 +2102,39 @@ nvptx_print_operand (FILE *file, rtx x, int code)
default:
gcc_unreachable ();
}
- if (FLOAT_MODE_P (op_mode)
+ if (FLOAT_MODE_P (mode)
|| x_code == EQ || x_code == NE
|| x_code == GEU || x_code == GTU
|| x_code == LEU || x_code == LTU)
- fputs (nvptx_ptx_type_from_mode (op_mode, true), file);
+ fputs (nvptx_ptx_type_from_mode (mode, true), file);
else
- fprintf (file, ".s%d", GET_MODE_BITSIZE (op_mode));
+ fprintf (file, ".s%d", GET_MODE_BITSIZE (mode));
break;
default:
common:
switch (x_code)
{
case SUBREG:
- x = SUBREG_REG (x);
- /* fall through */
+ {
+ rtx inner_x = SUBREG_REG (x);
+ machine_mode inner_mode = GET_MODE (inner_x);
+ machine_mode split = maybe_split_mode (inner_mode);
+
+ if (split != VOIDmode
+ && (GET_MODE_SIZE (inner_mode) == GET_MODE_SIZE (mode)))
+ output_reg (file, REGNO (inner_x), split);
+ else
+ output_reg (file, REGNO (inner_x), split, SUBREG_BYTE (x));
+ }
+ break;
case REG:
- if (HARD_REGISTER_P (x))
- fprintf (file, "%s", reg_names[REGNO (x)]);
- else
- fprintf (file, "%%r%d", REGNO (x));
- if (code != 'f' && maybe_split_mode (GET_MODE (x)) != VOIDmode)
- {
- gcc_assert (GET_CODE (orig_x) == SUBREG
- && maybe_split_mode (GET_MODE (orig_x)) == VOIDmode);
- fprintf (file, "$%d", SUBREG_BYTE (orig_x) / UNITS_PER_WORD);
- }
+ output_reg (file, REGNO (x), maybe_split_mode (mode));
break;
case MEM:
fputc ('[', file);
- nvptx_print_address_operand (file, XEXP (x, 0), GET_MODE (x));
+ nvptx_print_address_operand (file, XEXP (x, 0), mode);
fputc (']', file);
break;
@@ -2082,10 +2153,10 @@ nvptx_print_operand (FILE *file, rtx x, int code)
case CONST_DOUBLE:
long vals[2];
- real_to_target (vals, CONST_DOUBLE_REAL_VALUE (x), GET_MODE (x));
+ real_to_target (vals, CONST_DOUBLE_REAL_VALUE (x), mode);
vals[0] &= 0xffffffff;
vals[1] &= 0xffffffff;
- if (GET_MODE (x) == SFmode)
+ if (mode == SFmode)
fprintf (file, "0f%08lx", vals[0]);
else
fprintf (file, "0d%08lx%08lx", vals[1], vals[0]);
@@ -3878,7 +3949,7 @@ nvptx_file_end (void)
worker_bcast_size = (worker_bcast_size + worker_bcast_align - 1)
& ~(worker_bcast_align - 1);
- fprintf (asm_out_file, "\n// BEGIN VAR DEF: %s\n", worker_bcast_name);
+ write_var_marker (asm_out_file, true, false, worker_bcast_name);
fprintf (asm_out_file, ".shared .align %d .u8 %s[%d];\n",
worker_bcast_align,
worker_bcast_name, worker_bcast_size);
@@ -3890,8 +3961,8 @@ nvptx_file_end (void)
worker_red_size = ((worker_red_size + worker_red_align - 1)
& ~(worker_red_align - 1));
-
- fprintf (asm_out_file, "\n// BEGIN VAR DEF: %s\n", worker_red_name);
+
+ write_var_marker (asm_out_file, true, false, worker_red_name);
fprintf (asm_out_file, ".shared .align %d .u8 %s[%d];\n",
worker_red_align,
worker_red_name, worker_red_size);
@@ -3919,7 +3990,8 @@ nvptx_expand_shuffle (tree exp, rtx target, machine_mode mode, int ignore)
if (!REG_P (idx) && GET_CODE (idx) != CONST_INT)
idx = copy_to_mode_reg (SImode, idx);
- rtx pat = nvptx_gen_shuffle (target, src, idx, INTVAL (op));
+ rtx pat = nvptx_gen_shuffle (target, src, idx,
+ (nvptx_shuffle_kind) INTVAL (op));
if (pat)
emit_insn (pat);
@@ -3944,15 +4016,14 @@ nvptx_expand_worker_addr (tree exp, rtx target,
if (size + offset > worker_red_size)
worker_red_size = size + offset;
- emit_insn (gen_rtx_SET (target, worker_red_sym));
-
+ rtx addr = worker_red_sym;
if (offset)
- emit_insn (gen_rtx_SET (target,
- gen_rtx_PLUS (Pmode, target, GEN_INT (offset))));
+ {
+ addr = gen_rtx_PLUS (Pmode, addr, GEN_INT (offset));
+ addr = gen_rtx_CONST (Pmode, addr);
+ }
- emit_insn (gen_rtx_SET (target,
- gen_rtx_UNSPEC (Pmode, gen_rtvec (1, target),
- UNSPEC_FROM_SHARED)));
+ emit_move_insn (target, addr);
return target;
}
@@ -4817,6 +4888,8 @@ nvptx_goacc_reduction (gcall *call)
#undef TARGET_NO_REGISTER_ALLOCATION
#define TARGET_NO_REGISTER_ALLOCATION true
+#undef TARGET_ENCODE_SECTION_INFO
+#define TARGET_ENCODE_SECTION_INFO nvptx_encode_section_info
#undef TARGET_RECORD_OFFLOAD_SYMBOL
#define TARGET_RECORD_OFFLOAD_SYMBOL nvptx_record_offload_symbol
diff --git a/gcc/config/nvptx/nvptx.h b/gcc/config/nvptx/nvptx.h
index 4228ec073b8..66906e74fde 100644
--- a/gcc/config/nvptx/nvptx.h
+++ b/gcc/config/nvptx/nvptx.h
@@ -141,13 +141,6 @@ enum reg_class
(MODE) = SImode; \
}
-/* Address spaces. */
-#define ADDR_SPACE_GLOBAL 1
-#define ADDR_SPACE_SHARED 3
-#define ADDR_SPACE_CONST 4
-#define ADDR_SPACE_LOCAL 5
-#define ADDR_SPACE_PARAM 101
-
/* Stack and Calling. */
#define STARTING_FRAME_OFFSET 0
@@ -156,7 +149,6 @@ enum reg_class
#define STACK_POINTER_REGNUM 1
#define HARD_FRAME_POINTER_REGNUM 2
-#define NVPTX_PUNNING_BUFFER_REGNUM 3
#define NVPTX_RETURN_REGNUM 4
#define FRAME_POINTER_REGNUM 15
#define ARG_POINTER_REGNUM 14
@@ -231,7 +223,6 @@ struct GTY(()) machine_function
bool has_call_with_sc;
HOST_WIDE_INT outgoing_stdarg_size;
int ret_reg_mode; /* machine_mode not defined yet. */
- int punning_buffer_size;
rtx axis_predicate[2];
};
#endif
@@ -264,7 +255,7 @@ struct GTY(()) machine_function
#define REGISTER_NAMES \
{ \
- "%hr0", "%outargs", "%hfp", "%punbuffer", "%retval", "%retval_in", "%hr6", "%hr7", \
+ "%hr0", "%outargs", "%hfp", "%hr3", "%retval", "%retval_in", "%hr6", "%hr7", \
"%hr8", "%hr9", "%hr10", "%hr11", "%hr12", "%hr13", "%argp", "%frame" \
}
@@ -304,38 +295,11 @@ struct GTY(()) machine_function
#undef ASM_OUTPUT_ALIGNED_DECL_COMMON
#define ASM_OUTPUT_ALIGNED_DECL_COMMON(FILE, DECL, NAME, SIZE, ALIGN) \
- do \
- { \
- fprintf (FILE, "\n// BEGIN%s VAR DEF: ", \
- TREE_PUBLIC (DECL) ? " GLOBAL" : ""); \
- assemble_name_raw (FILE, NAME); \
- fputc ('\n', FILE); \
- const char *sec = nvptx_section_for_decl (DECL); \
- fprintf (FILE, ".visible%s.align %d .b8 ", sec, \
- (ALIGN) / BITS_PER_UNIT); \
- assemble_name ((FILE), (NAME)); \
- if ((SIZE) > 0) \
- fprintf (FILE, "[" HOST_WIDE_INT_PRINT_DEC"]", (SIZE)); \
- fprintf (FILE, ";\n"); \
- } \
- while (0)
+ nvptx_output_aligned_decl (FILE, NAME, DECL, SIZE, ALIGN)
#undef ASM_OUTPUT_ALIGNED_DECL_LOCAL
#define ASM_OUTPUT_ALIGNED_DECL_LOCAL(FILE, DECL, NAME, SIZE, ALIGN) \
- do \
- { \
- fprintf (FILE, "\n// BEGIN VAR DEF: "); \
- assemble_name_raw (FILE, NAME); \
- fputc ('\n', FILE); \
- const char *sec = nvptx_section_for_decl (DECL); \
- fprintf (FILE, ".visible%s.align %d .b8 ", sec, \
- (ALIGN) / BITS_PER_UNIT); \
- assemble_name ((FILE), (NAME)); \
- if ((SIZE) > 0) \
- fprintf (FILE, "[" HOST_WIDE_INT_PRINT_DEC"]", (SIZE)); \
- fprintf (FILE, ";\n"); \
- } \
- while (0)
+ nvptx_output_aligned_decl (FILE, NAME, DECL, SIZE, ALIGN)
#define CASE_VECTOR_PC_RELATIVE flag_pic
#define JUMP_TABLES_IN_TEXT_SECTION flag_pic
diff --git a/gcc/config/nvptx/nvptx.md b/gcc/config/nvptx/nvptx.md
index fd015631203..b0da63e389a 100644
--- a/gcc/config/nvptx/nvptx.md
+++ b/gcc/config/nvptx/nvptx.md
@@ -20,19 +20,7 @@
(define_c_enum "unspec" [
UNSPEC_ARG_REG
- UNSPEC_FROM_GLOBAL
- UNSPEC_FROM_LOCAL
- UNSPEC_FROM_PARAM
- UNSPEC_FROM_SHARED
- UNSPEC_FROM_CONST
- UNSPEC_TO_GLOBAL
- UNSPEC_TO_LOCAL
- UNSPEC_TO_PARAM
- UNSPEC_TO_SHARED
- UNSPEC_TO_CONST
-
- UNSPEC_CPLX_LOWPART
- UNSPEC_CPLX_HIGHPART
+ UNSPEC_TO_GENERIC
UNSPEC_COPYSIGN
UNSPEC_LOG2
@@ -103,20 +91,6 @@
(define_predicate "symbolic_operand"
(match_code "symbol_ref,const"))
-;; Allow registers or symbolic constants. We can allow frame, arg or stack
-;; pointers here since they are actually symbolic constants.
-(define_predicate "nvptx_register_or_symbolic_operand"
- (match_code "reg,subreg,symbol_ref,const")
-{
- if (GET_CODE (op) == SUBREG && MEM_P (SUBREG_REG (op)))
- return false;
- if (GET_CODE (op) == SUBREG)
- return false;
- if (CONSTANT_P (op))
- return true;
- return register_operand (op, mode);
-})
-
;; Registers or constants for normal instructions. Does not allow symbolic
;; constants.
(define_predicate "nvptx_nonmemory_operand"
@@ -258,74 +232,31 @@
%.\\tsetp.eq.u32\\t%0, 1, 1;")
(define_insn "*mov<mode>_insn"
- [(set (match_operand:QHSDIM 0 "nvptx_nonimmediate_operand" "=R,R,R,m")
- (match_operand:QHSDIM 1 "general_operand" "n,Ri,m,R"))]
- "!(MEM_P (operands[0])
- && (!REG_P (operands[1]) || REGNO (operands[1]) <= LAST_VIRTUAL_REGISTER))"
+ [(set (match_operand:QHSDIM 0 "nvptx_nonimmediate_operand" "=R,R,m")
+ (match_operand:QHSDIM 1 "general_operand" "Ri,m,R"))]
+ "!MEM_P (operands[0])
+ || (REG_P (operands[1]) && REGNO (operands[1]) > LAST_VIRTUAL_REGISTER)"
{
- if (which_alternative == 2)
+ if (which_alternative == 1)
return "%.\\tld%A1%u1\\t%0, %1;";
- if (which_alternative == 3)
+ if (which_alternative == 2)
return "%.\\tst%A0%u0\\t%0, %1;";
- rtx dst = operands[0];
- rtx src = operands[1];
-
- enum machine_mode dst_mode = nvptx_underlying_object_mode (dst);
- enum machine_mode src_mode = nvptx_underlying_object_mode (src);
- if (GET_CODE (dst) == SUBREG)
- dst = SUBREG_REG (dst);
- if (GET_CODE (src) == SUBREG)
- src = SUBREG_REG (src);
- if (src_mode == QImode)
- src_mode = SImode;
- if (dst_mode == QImode)
- dst_mode = SImode;
- if (CONSTANT_P (src))
- {
- if (GET_MODE_CLASS (dst_mode) != MODE_INT)
- return "%.\\tmov.b%T0\\t%0, %1;";
- else
- return "%.\\tmov%t0\\t%0, %1;";
- }
-
- /* Special handling for the return register; we allow this register to
- only occur in the destination of a move insn. */
- if (REG_P (dst) && REGNO (dst) == NVPTX_RETURN_REGNUM
- && dst_mode == HImode)
- dst_mode = SImode;
- if (dst_mode == src_mode)
- return "%.\\tmov%t0\\t%0, %1;";
- /* Mode-punning between floating point and integer. */
- if (GET_MODE_SIZE (dst_mode) == GET_MODE_SIZE (src_mode))
- return "%.\\tmov.b%T0\\t%0, %1;";
- return "%.\\tcvt%t0%t1\\t%0, %1;";
+ return nvptx_output_mov_insn (operands[0], operands[1]);
}
[(set_attr "subregs_ok" "true")])
(define_insn "*mov<mode>_insn"
[(set (match_operand:SDFM 0 "nvptx_nonimmediate_operand" "=R,R,m")
(match_operand:SDFM 1 "general_operand" "RF,m,R"))]
- "!(MEM_P (operands[0]) && !REG_P (operands[1]))"
+ "!MEM_P (operands[0]) || REG_P (operands[1])"
{
if (which_alternative == 1)
return "%.\\tld%A1%u0\\t%0, %1;";
if (which_alternative == 2)
return "%.\\tst%A0%u1\\t%0, %1;";
- rtx dst = operands[0];
- rtx src = operands[1];
- if (GET_CODE (dst) == SUBREG)
- dst = SUBREG_REG (dst);
- if (GET_CODE (src) == SUBREG)
- src = SUBREG_REG (src);
- enum machine_mode dst_mode = GET_MODE (dst);
- enum machine_mode src_mode = GET_MODE (src);
- if (dst_mode == src_mode)
- return "%.\\tmov%t0\\t%0, %1;";
- if (GET_MODE_SIZE (dst_mode) == GET_MODE_SIZE (src_mode))
- return "%.\\tmov.b%T0\\t%0, %1;";
- gcc_unreachable ();
+ return nvptx_output_mov_insn (operands[0], operands[1]);
}
[(set_attr "subregs_ok" "true")])
@@ -373,116 +304,6 @@
}
})
-(define_insn "highpartscsf2"
- [(set (match_operand:SF 0 "nvptx_register_operand" "=R")
- (unspec:SF [(match_operand:SC 1 "nvptx_register_operand")]
- UNSPEC_CPLX_HIGHPART))]
- ""
- "%.\\tmov%t0\\t%0, %f1$1;")
-
-(define_insn "set_highpartsfsc2"
- [(set (match_operand:SC 0 "nvptx_register_operand" "+R")
- (unspec:SC [(match_dup 0)
- (match_operand:SF 1 "nvptx_register_operand")]
- UNSPEC_CPLX_HIGHPART))]
- ""
- "%.\\tmov%t1\\t%f0$1, %1;")
-
-(define_insn "lowpartscsf2"
- [(set (match_operand:SF 0 "nvptx_register_operand" "=R")
- (unspec:SF [(match_operand:SC 1 "nvptx_register_operand")]
- UNSPEC_CPLX_LOWPART))]
- ""
- "%.\\tmov%t0\\t%0, %f1$0;")
-
-(define_insn "set_lowpartsfsc2"
- [(set (match_operand:SC 0 "nvptx_register_operand" "+R")
- (unspec:SC [(match_dup 0)
- (match_operand:SF 1 "nvptx_register_operand")]
- UNSPEC_CPLX_LOWPART))]
- ""
- "%.\\tmov%t1\\t%f0$0, %1;")
-
-(define_expand "mov<mode>"
- [(set (match_operand:SDCM 0 "nvptx_nonimmediate_operand" "")
- (match_operand:SDCM 1 "general_operand" ""))]
- ""
-{
- enum machine_mode submode = <MODE>mode == SCmode ? SFmode : DFmode;
- int sz = GET_MODE_SIZE (submode);
- rtx xops[4];
- rtx punning_reg = NULL_RTX;
- rtx copyback = NULL_RTX;
-
- if (GET_CODE (operands[0]) == SUBREG)
- {
- rtx inner = SUBREG_REG (operands[0]);
- enum machine_mode inner_mode = GET_MODE (inner);
- int sz2 = GET_MODE_SIZE (inner_mode);
- gcc_assert (sz2 >= sz);
- cfun->machine->punning_buffer_size
- = MAX (cfun->machine->punning_buffer_size, sz2);
- if (punning_reg == NULL_RTX)
- punning_reg = gen_rtx_REG (Pmode, NVPTX_PUNNING_BUFFER_REGNUM);
- copyback = gen_move_insn (inner, gen_rtx_MEM (inner_mode, punning_reg));
- operands[0] = gen_rtx_MEM (<MODE>mode, punning_reg);
- }
- if (GET_CODE (operands[1]) == SUBREG)
- {
- rtx inner = SUBREG_REG (operands[1]);
- enum machine_mode inner_mode = GET_MODE (inner);
- int sz2 = GET_MODE_SIZE (inner_mode);
- gcc_assert (sz2 >= sz);
- cfun->machine->punning_buffer_size
- = MAX (cfun->machine->punning_buffer_size, sz2);
- if (punning_reg == NULL_RTX)
- punning_reg = gen_rtx_REG (Pmode, NVPTX_PUNNING_BUFFER_REGNUM);
- emit_move_insn (gen_rtx_MEM (inner_mode, punning_reg), inner);
- operands[1] = gen_rtx_MEM (<MODE>mode, punning_reg);
- }
-
- if (REG_P (operands[0]) && submode == SFmode)
- {
- xops[0] = gen_reg_rtx (submode);
- xops[1] = gen_reg_rtx (submode);
- }
- else
- {
- xops[0] = gen_lowpart (submode, operands[0]);
- if (MEM_P (operands[0]))
- xops[1] = adjust_address_nv (operands[0], submode, sz);
- else
- xops[1] = gen_highpart (submode, operands[0]);
- }
-
- if (REG_P (operands[1]) && submode == SFmode)
- {
- xops[2] = gen_reg_rtx (submode);
- xops[3] = gen_reg_rtx (submode);
- emit_insn (gen_lowpartscsf2 (xops[2], operands[1]));
- emit_insn (gen_highpartscsf2 (xops[3], operands[1]));
- }
- else
- {
- xops[2] = gen_lowpart (submode, operands[1]);
- if (MEM_P (operands[1]))
- xops[3] = adjust_address_nv (operands[1], submode, sz);
- else
- xops[3] = gen_highpart (submode, operands[1]);
- }
-
- emit_move_insn (xops[0], xops[2]);
- emit_move_insn (xops[1], xops[3]);
- if (REG_P (operands[0]) && submode == SFmode)
- {
- emit_insn (gen_set_lowpartsfsc2 (operands[0], xops[0]));
- emit_insn (gen_set_highpartsfsc2 (operands[0], xops[1]));
- }
- if (copyback)
- emit_insn (copyback);
- DONE;
-})
-
(define_insn "zero_extendqihi2"
[(set (match_operand:HI 0 "nvptx_register_operand" "=R,R")
(zero_extend:HI (match_operand:QI 1 "nvptx_reg_or_mem_operand" "R,m")))]
@@ -555,43 +376,13 @@
%.\\tst%A0.u%T0\\t%0, %1;"
[(set_attr "subregs_ok" "true")])
-;; Pointer address space conversions
-
-(define_int_iterator cvt_code
- [UNSPEC_FROM_GLOBAL
- UNSPEC_FROM_LOCAL
- UNSPEC_FROM_SHARED
- UNSPEC_FROM_CONST
- UNSPEC_TO_GLOBAL
- UNSPEC_TO_LOCAL
- UNSPEC_TO_SHARED
- UNSPEC_TO_CONST])
-
-(define_int_attr cvt_name
- [(UNSPEC_FROM_GLOBAL "from_global")
- (UNSPEC_FROM_LOCAL "from_local")
- (UNSPEC_FROM_SHARED "from_shared")
- (UNSPEC_FROM_CONST "from_const")
- (UNSPEC_TO_GLOBAL "to_global")
- (UNSPEC_TO_LOCAL "to_local")
- (UNSPEC_TO_SHARED "to_shared")
- (UNSPEC_TO_CONST "to_const")])
-
-(define_int_attr cvt_str
- [(UNSPEC_FROM_GLOBAL ".global")
- (UNSPEC_FROM_LOCAL ".local")
- (UNSPEC_FROM_SHARED ".shared")
- (UNSPEC_FROM_CONST ".const")
- (UNSPEC_TO_GLOBAL ".to.global")
- (UNSPEC_TO_LOCAL ".to.local")
- (UNSPEC_TO_SHARED ".to.shared")
- (UNSPEC_TO_CONST ".to.const")])
-
-(define_insn "convaddr_<cvt_name><mode>"
+;; Pointer address space conversion
+(define_insn "convaddr_<mode>"
[(set (match_operand:P 0 "nvptx_register_operand" "=R")
- (unspec:P [(match_operand:P 1 "nvptx_register_or_symbolic_operand" "Rs")] cvt_code))]
+ (unspec:P [(match_operand:P 1 "symbolic_operand" "s")]
+ UNSPEC_TO_GENERIC))]
""
- "%.\\tcvta<cvt_str>%t0\\t%0, %1;")
+ "%.\\tcvta%D1%t0\\t%0, %1;")
;; Integer arithmetic
diff --git a/gcc/config/rs6000/freebsd64.h b/gcc/config/rs6000/freebsd64.h
index b5435c10838..c667f0dc7f8 100644
--- a/gcc/config/rs6000/freebsd64.h
+++ b/gcc/config/rs6000/freebsd64.h
@@ -65,6 +65,13 @@ extern int dot_symbols;
#define INVALID_64BIT "-m%s not supported in this configuration"
#define INVALID_32BIT INVALID_64BIT
+/* Use LINUX64 instead of FREEBSD64 for compat with e.g. sysv4le.h */
+#ifdef LINUX64_DEFAULT_ABI_ELFv2
+#define ELFv2_ABI_CHECK (rs6000_elf_abi != 1)
+#else
+#define ELFv2_ABI_CHECK (rs6000_elf_abi == 2)
+#endif
+
#undef SUBSUBTARGET_OVERRIDE_OPTIONS
#define SUBSUBTARGET_OVERRIDE_OPTIONS \
do \
@@ -84,6 +91,12 @@ extern int dot_symbols;
rs6000_isa_flags &= ~OPTION_MASK_RELOCATABLE; \
error (INVALID_64BIT, "relocatable"); \
} \
+ if (ELFv2_ABI_CHECK) \
+ { \
+ rs6000_current_abi = ABI_ELFv2; \
+ if (dot_symbols) \
+ error ("-mcall-aixdesc incompatible with -mabi=elfv2"); \
+ } \
if (rs6000_isa_flags & OPTION_MASK_EABI) \
{ \
rs6000_isa_flags &= ~OPTION_MASK_EABI; \
diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c
index c4e3f2fb538..2b2c170d6e9 100644
--- a/gcc/config/rs6000/rs6000.c
+++ b/gcc/config/rs6000/rs6000.c
@@ -1722,6 +1722,9 @@ static const struct attribute_spec rs6000_attribute_table[] =
#undef TARGET_INVALID_BINARY_OP
#define TARGET_INVALID_BINARY_OP rs6000_invalid_binary_op
+
+#undef TARGET_OPTAB_SUPPORTED_P
+#define TARGET_OPTAB_SUPPORTED_P rs6000_optab_supported_p
/* Processor table. */
@@ -24888,6 +24891,31 @@ split_stack_arg_pointer_used_p (void)
return bitmap_bit_p (DF_LR_OUT (bb), 12);
}
+/* Return whether we need to emit an ELFv2 global entry point prologue. */
+
+static bool
+rs6000_global_entry_point_needed_p (void)
+{
+ /* Only needed for the ELFv2 ABI. */
+ if (DEFAULT_ABI != ABI_ELFv2)
+ return false;
+
+ /* With -msingle-pic-base, we assume the whole program shares the same
+ TOC, so no global entry point prologues are needed anywhere. */
+ if (TARGET_SINGLE_PIC_BASE)
+ return false;
+
+ /* Ensure we have a global entry point for thunks. ??? We could
+ avoid that if the target routine doesn't need a global entry point,
+ but we do not know whether this is the case at this point. */
+ if (cfun->is_thunk)
+ return true;
+
+ /* For regular functions, rs6000_emit_prologue sets this flag if the
+ routine ever uses the TOC pointer. */
+ return cfun->machine->r2_setup_needed;
+}
+
/* Emit function prologue as insns. */
void
@@ -25951,12 +25979,52 @@ rs6000_output_function_prologue (FILE *file,
/* ELFv2 ABI r2 setup code and local entry point. This must follow
immediately after the global entry point label. */
- if (DEFAULT_ABI == ABI_ELFv2 && cfun->machine->r2_setup_needed)
+ if (rs6000_global_entry_point_needed_p ())
{
const char *name = XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0);
- fprintf (file, "0:\taddis 2,12,.TOC.-0b@ha\n");
- fprintf (file, "\taddi 2,2,.TOC.-0b@l\n");
+ (*targetm.asm_out.internal_label) (file, "LCF", rs6000_pic_labelno);
+
+ if (TARGET_CMODEL != CMODEL_LARGE)
+ {
+ /* In the small and medium code models, we assume the TOC is less
+ 2 GB away from the text section, so it can be computed via the
+ following two-instruction sequence. */
+ char buf[256];
+
+ ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
+ fprintf (file, "0:\taddis 2,12,.TOC.-");
+ assemble_name (file, buf);
+ fprintf (file, "@ha\n");
+ fprintf (file, "\taddi 2,2,.TOC.-");
+ assemble_name (file, buf);
+ fprintf (file, "@l\n");
+ }
+ else
+ {
+ /* In the large code model, we allow arbitrary offsets between the
+ TOC and the text section, so we have to load the offset from
+ memory. The data field is emitted directly before the global
+ entry point in rs6000_elf_declare_function_name. */
+ char buf[256];
+
+#ifdef HAVE_AS_ENTRY_MARKERS
+ /* If supported by the linker, emit a marker relocation. If the
+ total code size of the final executable or shared library
+ happens to fit into 2 GB after all, the linker will replace
+ this code sequence with the sequence for the small or medium
+ code model. */
+ fprintf (file, "\t.reloc .,R_PPC64_ENTRY\n");
+#endif
+ fprintf (file, "\tld 2,");
+ ASM_GENERATE_INTERNAL_LABEL (buf, "LCL", rs6000_pic_labelno);
+ assemble_name (file, buf);
+ fprintf (file, "-");
+ ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
+ assemble_name (file, buf);
+ fprintf (file, "(12)\n");
+ fprintf (file, "\tadd 2,2,12\n");
+ }
fputs ("\t.localentry\t", file);
assemble_name (file, name);
@@ -27620,13 +27688,6 @@ rs6000_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
SIBLING_CALL_P (insn) = 1;
emit_barrier ();
- /* Ensure we have a global entry point for the thunk. ??? We could
- avoid that if the target routine doesn't need a global entry point,
- but we do not know whether this is the case at this point. */
- if (DEFAULT_ABI == ABI_ELFv2
- && !TARGET_SINGLE_PIC_BASE)
- cfun->machine->r2_setup_needed = true;
-
/* Run just enough of rest_of_compilation to get the insns emitted.
There's not really enough bulk here to make other passes such as
instruction scheduling worth while. Note that use_thunk calls
@@ -31493,6 +31554,18 @@ rs6000_elf_declare_function_name (FILE *file, const char *name, tree decl)
ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
ASM_DECLARE_RESULT (file, DECL_RESULT (decl));
+ if (TARGET_CMODEL == CMODEL_LARGE && rs6000_global_entry_point_needed_p ())
+ {
+ char buf[256];
+
+ (*targetm.asm_out.internal_label) (file, "LCL", rs6000_pic_labelno);
+
+ fprintf (file, "\t.quad .TOC.-");
+ ASM_GENERATE_INTERNAL_LABEL (buf, "LCF", rs6000_pic_labelno);
+ assemble_name (file, buf);
+ putc ('\n', file);
+ }
+
if (DEFAULT_ABI == ABI_AIX)
{
const char *desc_name, *orig_name;
@@ -32643,77 +32716,25 @@ rs6000_memory_move_cost (machine_mode mode, reg_class_t rclass,
reciprocal of the function, or NULL_TREE if not available. */
static tree
-rs6000_builtin_reciprocal (gcall *call)
+rs6000_builtin_reciprocal (tree fndecl)
{
- if (optimize_insn_for_size_p ())
- return NULL_TREE;
-
- if (gimple_call_internal_p (call))
- switch (gimple_call_internal_fn (call))
- {
- tree type;
- case IFN_SQRT:
- type = TREE_TYPE (gimple_call_lhs (call));
- switch (TYPE_MODE (type))
- {
- case V2DFmode:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (V2DFmode))
- return NULL_TREE;
-
- return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_2DF];
-
- case V4SFmode:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (V4SFmode))
- return NULL_TREE;
-
- return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_4SF];
-
- default:
- return NULL_TREE;
- }
-
- default:
+ switch (DECL_FUNCTION_CODE (fndecl))
+ {
+ case VSX_BUILTIN_XVSQRTDP:
+ if (!RS6000_RECIP_AUTO_RSQRTE_P (V2DFmode))
return NULL_TREE;
- }
-
- tree fndecl = gimple_call_fndecl (call);
- if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
- switch (DECL_FUNCTION_CODE (fndecl))
- {
- case VSX_BUILTIN_XVSQRTDP:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (V2DFmode))
- return NULL_TREE;
-
- return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_2DF];
-
- case VSX_BUILTIN_XVSQRTSP:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (V4SFmode))
- return NULL_TREE;
- return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_4SF];
+ return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_2DF];
- default:
+ case VSX_BUILTIN_XVSQRTSP:
+ if (!RS6000_RECIP_AUTO_RSQRTE_P (V4SFmode))
return NULL_TREE;
- }
-
- else
- switch (DECL_FUNCTION_CODE (fndecl))
- {
- case BUILT_IN_SQRT:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (DFmode))
- return NULL_TREE;
-
- return rs6000_builtin_decls[RS6000_BUILTIN_RSQRT];
- case BUILT_IN_SQRTF:
- if (!RS6000_RECIP_AUTO_RSQRTE_P (SFmode))
- return NULL_TREE;
+ return rs6000_builtin_decls[VSX_BUILTIN_RSQRT_4SF];
- return rs6000_builtin_decls[RS6000_BUILTIN_RSQRTF];
-
- default:
- return NULL_TREE;
- }
+ default:
+ return NULL_TREE;
+ }
}
/* Load up a constant. If the mode is a vector mode, splat the value across
@@ -36613,7 +36634,12 @@ const_load_sequence_p (swap_web_entry *insn_entry, rtx insn)
rtx base, offset;
if (GET_CODE (tocrel_body) != SET)
return false;
- if (!toc_relative_expr_p (SET_SRC (tocrel_body), false))
+ /* There is an extra level of indirection for small/large
+ code models. */
+ rtx tocrel_expr = SET_SRC (tocrel_body);
+ if (GET_CODE (tocrel_expr) == MEM)
+ tocrel_expr = XEXP (tocrel_expr, 0);
+ if (!toc_relative_expr_p (tocrel_expr, false))
return false;
split_const (XVECEXP (tocrel_base, 0, 0), &base, &offset);
if (GET_CODE (base) != SYMBOL_REF || !CONSTANT_POOL_ADDRESS_P (base))
@@ -37294,10 +37320,19 @@ adjust_vperm (rtx_insn *insn)
to set tocrel_base; otherwise it would be unnecessary as we've
already established it will return true. */
rtx base, offset;
- if (!toc_relative_expr_p (SET_SRC (PATTERN (tocrel_insn)), false))
+ rtx tocrel_expr = SET_SRC (PATTERN (tocrel_insn));
+ /* There is an extra level of indirection for small/large code models. */
+ if (GET_CODE (tocrel_expr) == MEM)
+ tocrel_expr = XEXP (tocrel_expr, 0);
+ if (!toc_relative_expr_p (tocrel_expr, false))
gcc_unreachable ();
split_const (XVECEXP (tocrel_base, 0, 0), &base, &offset);
rtx const_vector = get_pool_constant (base);
+ /* With the extra indirection, get_pool_constant will produce the
+ real constant from the reg_equal expression, so get the real
+ constant. */
+ if (GET_CODE (const_vector) == SYMBOL_REF)
+ const_vector = get_pool_constant (const_vector);
gcc_assert (GET_CODE (const_vector) == CONST_VECTOR);
/* Create an adjusted mask from the initial mask. */
@@ -37923,6 +37958,22 @@ rs6000_atomic_assign_expand_fenv (tree *hold, tree *clear, tree *update)
*update = build2 (COMPOUND_EXPR, void_type_node, update_mffs, update_mtfsf);
}
+/* Implement the TARGET_OPTAB_SUPPORTED_P hook. */
+
+static bool
+rs6000_optab_supported_p (int op, machine_mode mode1, machine_mode,
+ optimization_type opt_type)
+{
+ switch (op)
+ {
+ case rsqrt_optab:
+ return (opt_type == OPTIMIZE_FOR_SPEED
+ && RS6000_RECIP_AUTO_RSQRTE_P (mode1));
+
+ default:
+ return true;
+ }
+}
struct gcc_target targetm = TARGET_INITIALIZER;
diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md
index a500d67efa9..26b0962ae7d 100644
--- a/gcc/config/rs6000/rs6000.md
+++ b/gcc/config/rs6000/rs6000.md
@@ -10564,6 +10564,51 @@
DONE;
})
+(define_expand "cstore_si_as_di"
+ [(use (match_operator 1 "unsigned_comparison_operator"
+ [(match_operand:SI 2 "gpc_reg_operand")
+ (match_operand:SI 3 "reg_or_short_operand")]))
+ (clobber (match_operand:SI 0 "register_operand"))]
+ ""
+{
+ int uns_flag = unsigned_comparison_operator (operands[1], VOIDmode) ? 1 : 0;
+ enum rtx_code cond_code = signed_condition (GET_CODE (operands[1]));
+
+ rtx op1 = gen_reg_rtx (DImode);
+ rtx op2 = gen_reg_rtx (DImode);
+ convert_move (op1, operands[2], uns_flag);
+ convert_move (op2, operands[3], uns_flag);
+
+ if (cond_code == GT || cond_code == LE)
+ {
+ cond_code = swap_condition (cond_code);
+ std::swap (op1, op2);
+ }
+
+ rtx tmp = gen_reg_rtx (DImode);
+ rtx tmp2 = gen_reg_rtx (DImode);
+ emit_insn (gen_subdi3 (tmp, op1, op2));
+ emit_insn (gen_lshrdi3 (tmp2, tmp, GEN_INT (63)));
+
+ rtx tmp3;
+ switch (cond_code)
+ {
+ default:
+ gcc_unreachable ();
+ case LT:
+ tmp3 = tmp2;
+ break;
+ case GE:
+ tmp3 = gen_reg_rtx (DImode);
+ emit_insn (gen_xordi3 (tmp3, tmp2, const1_rtx));
+ break;
+ }
+
+ convert_move (operands[0], tmp3, 1);
+
+ DONE;
+})
+
(define_expand "cstore<mode>4_signed_imm"
[(use (match_operator 1 "signed_comparison_operator"
[(match_operand:GPR 2 "gpc_reg_operand")
@@ -10688,6 +10733,11 @@
emit_insn (gen_cstore<mode>4_unsigned (operands[0], operands[1],
operands[2], operands[3]));
+ /* For comparisons smaller than Pmode we can cheaply do things in Pmode. */
+ else if (<MODE>mode == SImode && Pmode == DImode)
+ emit_insn (gen_cstore_si_as_di (operands[0], operands[1],
+ operands[2], operands[3]));
+
/* For signed comparisons against a constant, we can do some simple
bit-twiddling. */
else if (signed_comparison_operator (operands[1], VOIDmode)
diff --git a/gcc/config/s390/constraints.md b/gcc/config/s390/constraints.md
index 66d4acecdb3..1dab92ac66a 100644
--- a/gcc/config/s390/constraints.md
+++ b/gcc/config/s390/constraints.md
@@ -34,6 +34,8 @@
;; jm1: constant scalar or vector with all bits set
;; jxx: contiguous bitmask of 0 or 1 in all vector elements
;; jyy: constant consisting of byte chunks being either 0 or 0xff
+;; jKK: constant vector with all elements having the same value and
+;; matching K constraint
;; t -- Access registers 36 and 37.
;; v -- Vector registers v0-v31.
;; C -- A signed 8-bit constant (-128..127)
@@ -108,23 +110,6 @@
"FP_REGS"
"Floating point registers")
-(define_constraint "j00"
- "Zero scalar or vector constant"
- (match_test "op == CONST0_RTX (GET_MODE (op))"))
-
-(define_constraint "jm1"
- "All one bit scalar or vector constant"
- (match_test "op == CONSTM1_RTX (GET_MODE (op))"))
-
-(define_constraint "jxx"
- "@internal"
- (and (match_code "const_vector")
- (match_test "s390_contiguous_bitmask_vector_p (op, NULL, NULL)")))
-
-(define_constraint "jyy"
- "@internal"
- (and (match_code "const_vector")
- (match_test "s390_bytemask_vector_p (op, NULL)")))
(define_register_constraint "t"
"ACCESS_REGS"
@@ -402,6 +387,33 @@
(match_test "s390_O_constraint_str ('n', ival)")))
+;;
+;; Vector constraints follow.
+;;
+
+(define_constraint "j00"
+ "Zero scalar or vector constant"
+ (match_test "op == CONST0_RTX (GET_MODE (op))"))
+
+(define_constraint "jm1"
+ "All one bit scalar or vector constant"
+ (match_test "op == CONSTM1_RTX (GET_MODE (op))"))
+
+(define_constraint "jxx"
+ "@internal"
+ (and (match_code "const_vector")
+ (match_test "s390_contiguous_bitmask_vector_p (op, NULL, NULL)")))
+
+(define_constraint "jyy"
+ "@internal"
+ (and (match_code "const_vector")
+ (match_test "s390_bytemask_vector_p (op, NULL)")))
+
+(define_constraint "jKK"
+ "@internal"
+ (and (and (match_code "const_vector")
+ (match_test "const_vec_duplicate_p (op)"))
+ (match_test "satisfies_constraint_K (XVECEXP (op, 0, 0))")))
;;
diff --git a/gcc/config/s390/predicates.md b/gcc/config/s390/predicates.md
index 893092b9f46..6a5ebbbf303 100644
--- a/gcc/config/s390/predicates.md
+++ b/gcc/config/s390/predicates.md
@@ -34,6 +34,11 @@
(and (match_code "const_int, const_double,const_vector")
(match_test "op == CONSTM1_RTX (mode)")))
+;; Return true if OP is a 4 bit mask operand
+(define_predicate "const_mask_operand"
+ (and (match_code "const_int")
+ (match_test "UINTVAL (op) < 16")))
+
;; Return true if OP is constant.
(define_special_predicate "consttable_operand"
diff --git a/gcc/config/s390/s390-builtin-types.def b/gcc/config/s390/s390-builtin-types.def
index 245d5382512..bd3d534cbb2 100644
--- a/gcc/config/s390/s390-builtin-types.def
+++ b/gcc/config/s390/s390-builtin-types.def
@@ -58,695 +58,698 @@
s390_builtin_types[T4], \
s390_builtin_types[T5], \
s390_builtin_types[T6])
-DEF_TYPE (BT_DBL, B_VX, double_type_node, 0)
-DEF_TYPE (BT_DBLCONST, B_VX, double_type_node, 1)
-DEF_TYPE (BT_FLT, B_VX, float_type_node, 0)
+DEF_TYPE (BT_INT, B_HTM | B_VX, integer_type_node, 0)
+DEF_TYPE (BT_VOID, 0, void_type_node, 0)
DEF_TYPE (BT_FLTCONST, B_VX, float_type_node, 1)
+DEF_TYPE (BT_UINT64, B_HTM, c_uint64_type_node, 0)
+DEF_TYPE (BT_FLT, B_VX, float_type_node, 0)
+DEF_TYPE (BT_UINT, 0, unsigned_type_node, 0)
+DEF_TYPE (BT_VOIDCONST, B_VX, void_type_node, 1)
+DEF_TYPE (BT_ULONG, B_VX, long_unsigned_type_node, 0)
+DEF_TYPE (BT_USHORTCONST, B_VX, short_unsigned_type_node, 1)
+DEF_TYPE (BT_SHORTCONST, B_VX, short_integer_type_node, 1)
DEF_TYPE (BT_INTCONST, B_VX, integer_type_node, 1)
-DEF_TYPE (BT_INT, B_HTM | B_VX, integer_type_node, 0)
-DEF_TYPE (BT_LONGLONGCONST, B_VX, long_long_integer_type_node, 1)
-DEF_TYPE (BT_LONGLONG, B_VX, long_long_integer_type_node, 0)
-DEF_TYPE (BT_LONG, B_VX, long_integer_type_node, 0)
+DEF_TYPE (BT_UCHARCONST, B_VX, unsigned_char_type_node, 1)
DEF_TYPE (BT_UCHAR, B_VX, unsigned_char_type_node, 0)
-DEF_TYPE (BT_SCHAR, B_VX, signed_char_type_node, 0)
DEF_TYPE (BT_SCHARCONST, B_VX, signed_char_type_node, 1)
-DEF_TYPE (BT_SHORTCONST, B_VX, short_integer_type_node, 1)
DEF_TYPE (BT_SHORT, B_VX, short_integer_type_node, 0)
-DEF_TYPE (BT_UINT, 0, unsigned_type_node, 0)
-DEF_TYPE (BT_UINT64, B_HTM, c_uint64_type_node, 0)
-DEF_TYPE (BT_UCHARCONST, B_VX, unsigned_char_type_node, 1)
-DEF_TYPE (BT_UINTCONST, B_VX, unsigned_type_node, 1)
+DEF_TYPE (BT_LONG, B_VX, long_integer_type_node, 0)
+DEF_TYPE (BT_SCHAR, B_VX, signed_char_type_node, 0)
DEF_TYPE (BT_ULONGLONGCONST, B_VX, long_long_unsigned_type_node, 1)
-DEF_TYPE (BT_USHORTCONST, B_VX, short_unsigned_type_node, 1)
-DEF_TYPE (BT_VOIDCONST, B_VX, void_type_node, 1)
-DEF_TYPE (BT_VOID, 0, void_type_node, 0)
-DEF_TYPE (BT_ULONG, B_VX, long_unsigned_type_node, 0)
-DEF_TYPE (BT_ULONGLONG, B_VX, long_long_unsigned_type_node, 0)
DEF_TYPE (BT_USHORT, B_VX, short_unsigned_type_node, 0)
-DEF_DISTINCT_TYPE (BT_BCHAR, B_VX, BT_UCHAR)
-DEF_DISTINCT_TYPE (BT_BINT, B_VX, BT_UINT)
-DEF_DISTINCT_TYPE (BT_BLONGLONG, B_VX, BT_ULONGLONG)
-DEF_DISTINCT_TYPE (BT_BSHORT, B_VX, BT_USHORT)
-DEF_POINTER_TYPE (BT_DBLPTR, B_VX, BT_DBL)
+DEF_TYPE (BT_LONGLONG, B_VX, long_long_integer_type_node, 0)
+DEF_TYPE (BT_DBLCONST, B_VX, double_type_node, 1)
+DEF_TYPE (BT_ULONGLONG, B_VX, long_long_unsigned_type_node, 0)
+DEF_TYPE (BT_DBL, B_VX, double_type_node, 0)
+DEF_TYPE (BT_LONGLONGCONST, B_VX, long_long_integer_type_node, 1)
+DEF_TYPE (BT_UINTCONST, B_VX, unsigned_type_node, 1)
+DEF_VECTOR_TYPE (BT_UV2DI, B_VX, BT_ULONGLONG, 2)
+DEF_VECTOR_TYPE (BT_V4SI, B_VX, BT_INT, 4)
+DEF_VECTOR_TYPE (BT_V8HI, B_VX, BT_SHORT, 8)
+DEF_VECTOR_TYPE (BT_UV4SI, B_VX, BT_UINT, 4)
+DEF_VECTOR_TYPE (BT_V16QI, B_VX, BT_SCHAR, 16)
+DEF_VECTOR_TYPE (BT_V2DF, B_VX, BT_DBL, 2)
+DEF_VECTOR_TYPE (BT_V2DI, B_VX, BT_LONGLONG, 2)
+DEF_VECTOR_TYPE (BT_UV8HI, B_VX, BT_USHORT, 8)
+DEF_VECTOR_TYPE (BT_UV16QI, B_VX, BT_UCHAR, 16)
+DEF_POINTER_TYPE (BT_UCHARPTR, B_VX, BT_UCHAR)
DEF_POINTER_TYPE (BT_DBLCONSTPTR, B_VX, BT_DBLCONST)
+DEF_POINTER_TYPE (BT_VOIDPTR, B_HTM | B_VX, BT_VOID)
DEF_POINTER_TYPE (BT_FLTPTR, B_VX, BT_FLT)
-DEF_POINTER_TYPE (BT_FLTCONSTPTR, B_VX, BT_FLTCONST)
-DEF_POINTER_TYPE (BT_INTCONSTPTR, B_VX, BT_INTCONST)
-DEF_POINTER_TYPE (BT_INTPTR, B_VX, BT_INT)
-DEF_POINTER_TYPE (BT_LONGLONGCONSTPTR, B_VX, BT_LONGLONGCONST)
-DEF_POINTER_TYPE (BT_LONGLONGPTR, B_VX, BT_LONGLONG)
-DEF_POINTER_TYPE (BT_SCHARCONSTPTR, B_VX, BT_SCHARCONST)
+DEF_POINTER_TYPE (BT_UINT64PTR, B_HTM, BT_UINT64)
DEF_POINTER_TYPE (BT_SCHARPTR, B_VX, BT_SCHAR)
-DEF_POINTER_TYPE (BT_SHORTCONSTPTR, B_VX, BT_SHORTCONST)
-DEF_POINTER_TYPE (BT_SHORTPTR, B_VX, BT_SHORT)
-DEF_POINTER_TYPE (BT_UCHARCONSTPTR, B_VX, BT_UCHARCONST)
-DEF_POINTER_TYPE (BT_UCHARPTR, B_VX, BT_UCHAR)
-DEF_POINTER_TYPE (BT_UINTPTR, B_VX, BT_UINT)
DEF_POINTER_TYPE (BT_UINTCONSTPTR, B_VX, BT_UINTCONST)
-DEF_POINTER_TYPE (BT_UINT64PTR, B_HTM, BT_UINT64)
DEF_POINTER_TYPE (BT_ULONGLONGCONSTPTR, B_VX, BT_ULONGLONGCONST)
-DEF_POINTER_TYPE (BT_ULONGLONGPTR, B_VX, BT_ULONGLONG)
+DEF_POINTER_TYPE (BT_LONGLONGCONSTPTR, B_VX, BT_LONGLONGCONST)
+DEF_POINTER_TYPE (BT_SHORTPTR, B_VX, BT_SHORT)
DEF_POINTER_TYPE (BT_USHORTPTR, B_VX, BT_USHORT)
-DEF_POINTER_TYPE (BT_USHORTCONSTPTR, B_VX, BT_USHORTCONST)
-DEF_POINTER_TYPE (BT_VOIDPTR, B_HTM | B_VX, BT_VOID)
+DEF_POINTER_TYPE (BT_INTPTR, B_VX, BT_INT)
+DEF_POINTER_TYPE (BT_INTCONSTPTR, B_VX, BT_INTCONST)
+DEF_POINTER_TYPE (BT_LONGLONGPTR, B_VX, BT_LONGLONG)
+DEF_POINTER_TYPE (BT_ULONGLONGPTR, B_VX, BT_ULONGLONG)
+DEF_POINTER_TYPE (BT_DBLPTR, B_VX, BT_DBL)
DEF_POINTER_TYPE (BT_VOIDCONSTPTR, B_VX, BT_VOIDCONST)
-DEF_VECTOR_TYPE (BT_V16QI, B_VX, BT_SCHAR, 16)
-DEF_VECTOR_TYPE (BT_V2DI, B_VX, BT_LONGLONG, 2)
-DEF_VECTOR_TYPE (BT_V2DF, B_VX, BT_DBL, 2)
-DEF_VECTOR_TYPE (BT_V4SI, B_VX, BT_INT, 4)
-DEF_VECTOR_TYPE (BT_V8HI, B_VX, BT_SHORT, 8)
-DEF_VECTOR_TYPE (BT_UV16QI, B_VX, BT_UCHAR, 16)
-DEF_VECTOR_TYPE (BT_UV2DI, B_VX, BT_ULONGLONG, 2)
-DEF_VECTOR_TYPE (BT_UV4SI, B_VX, BT_UINT, 4)
-DEF_VECTOR_TYPE (BT_UV8HI, B_VX, BT_USHORT, 8)
+DEF_POINTER_TYPE (BT_USHORTCONSTPTR, B_VX, BT_USHORTCONST)
+DEF_POINTER_TYPE (BT_SHORTCONSTPTR, B_VX, BT_SHORTCONST)
+DEF_POINTER_TYPE (BT_UCHARCONSTPTR, B_VX, BT_UCHARCONST)
+DEF_POINTER_TYPE (BT_FLTCONSTPTR, B_VX, BT_FLTCONST)
+DEF_POINTER_TYPE (BT_SCHARCONSTPTR, B_VX, BT_SCHARCONST)
+DEF_POINTER_TYPE (BT_UINTPTR, B_VX, BT_UINT)
+DEF_DISTINCT_TYPE (BT_BLONGLONG, B_VX, BT_ULONGLONG)
+DEF_DISTINCT_TYPE (BT_BINT, B_VX, BT_UINT)
+DEF_DISTINCT_TYPE (BT_BSHORT, B_VX, BT_USHORT)
+DEF_DISTINCT_TYPE (BT_BCHAR, B_VX, BT_UCHAR)
DEF_OPAQUE_VECTOR_TYPE (BT_OV2DI, B_VX, BT_LONGLONG, 2)
+DEF_OPAQUE_VECTOR_TYPE (BT_BV16QI, B_VX, BT_BCHAR, 16)
DEF_OPAQUE_VECTOR_TYPE (BT_OV4SI, B_VX, BT_INT, 4)
DEF_OPAQUE_VECTOR_TYPE (BT_OUV4SI, B_VX, BT_UINT, 4)
-DEF_OPAQUE_VECTOR_TYPE (BT_BV16QI, B_VX, BT_BCHAR, 16)
-DEF_OPAQUE_VECTOR_TYPE (BT_BV2DI, B_VX, BT_BLONGLONG, 2)
DEF_OPAQUE_VECTOR_TYPE (BT_BV4SI, B_VX, BT_BINT, 4)
+DEF_OPAQUE_VECTOR_TYPE (BT_BV2DI, B_VX, BT_BLONGLONG, 2)
DEF_OPAQUE_VECTOR_TYPE (BT_BV8HI, B_VX, BT_BSHORT, 8)
-DEF_FN_TYPE_1 (BT_FN_UINT, 0, BT_UINT)
DEF_FN_TYPE_1 (BT_FN_INT, B_HTM, BT_INT)
-DEF_FN_TYPE_2 (BT_FN_VOID_UINT, 0, BT_VOID, BT_UINT)
-DEF_FN_TYPE_2 (BT_FN_VOID_INT, B_HTM, BT_VOID, BT_INT)
+DEF_FN_TYPE_1 (BT_FN_UINT, 0, BT_UINT)
DEF_FN_TYPE_2 (BT_FN_INT_INT, B_VX, BT_INT, BT_INT)
DEF_FN_TYPE_2 (BT_FN_INT_VOIDPTR, B_HTM, BT_INT, BT_VOIDPTR)
+DEF_FN_TYPE_2 (BT_FN_OV4SI_INT, B_VX, BT_OV4SI, BT_INT)
+DEF_FN_TYPE_2 (BT_FN_OV4SI_INTCONSTPTR, B_VX, BT_OV4SI, BT_INTCONSTPTR)
+DEF_FN_TYPE_2 (BT_FN_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI)
+DEF_FN_TYPE_2 (BT_FN_UV16QI_UCHAR, B_VX, BT_UV16QI, BT_UCHAR)
DEF_FN_TYPE_2 (BT_FN_UV16QI_UCHARCONSTPTR, B_VX, BT_UV16QI, BT_UCHARCONSTPTR)
DEF_FN_TYPE_2 (BT_FN_UV16QI_USHORT, B_VX, BT_UV16QI, BT_USHORT)
-DEF_FN_TYPE_2 (BT_FN_UV16QI_UCHAR, B_VX, BT_UV16QI, BT_UCHAR)
DEF_FN_TYPE_2 (BT_FN_UV16QI_UV16QI, B_VX, BT_UV16QI, BT_UV16QI)
DEF_FN_TYPE_2 (BT_FN_UV2DI_ULONGLONG, B_VX, BT_UV2DI, BT_ULONGLONG)
DEF_FN_TYPE_2 (BT_FN_UV2DI_ULONGLONGCONSTPTR, B_VX, BT_UV2DI, BT_ULONGLONGCONSTPTR)
+DEF_FN_TYPE_2 (BT_FN_UV2DI_USHORT, B_VX, BT_UV2DI, BT_USHORT)
DEF_FN_TYPE_2 (BT_FN_UV2DI_UV2DI, B_VX, BT_UV2DI, BT_UV2DI)
DEF_FN_TYPE_2 (BT_FN_UV2DI_UV4SI, B_VX, BT_UV2DI, BT_UV4SI)
-DEF_FN_TYPE_2 (BT_FN_OV4SI_INTCONSTPTR, B_VX, BT_OV4SI, BT_INTCONSTPTR)
-DEF_FN_TYPE_2 (BT_FN_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_2 (BT_FN_OV4SI_INT, B_VX, BT_OV4SI, BT_INT)
-DEF_FN_TYPE_2 (BT_FN_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI)
+DEF_FN_TYPE_2 (BT_FN_UV4SI_UINT, B_VX, BT_UV4SI, BT_UINT)
DEF_FN_TYPE_2 (BT_FN_UV4SI_UINTCONSTPTR, B_VX, BT_UV4SI, BT_UINTCONSTPTR)
+DEF_FN_TYPE_2 (BT_FN_UV4SI_USHORT, B_VX, BT_UV4SI, BT_USHORT)
+DEF_FN_TYPE_2 (BT_FN_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI)
DEF_FN_TYPE_2 (BT_FN_UV4SI_UV8HI, B_VX, BT_UV4SI, BT_UV8HI)
-DEF_FN_TYPE_2 (BT_FN_UV4SI_UINT, B_VX, BT_UV4SI, BT_UINT)
DEF_FN_TYPE_2 (BT_FN_UV8HI_USHORT, B_VX, BT_UV8HI, BT_USHORT)
+DEF_FN_TYPE_2 (BT_FN_UV8HI_USHORTCONSTPTR, B_VX, BT_UV8HI, BT_USHORTCONSTPTR)
DEF_FN_TYPE_2 (BT_FN_UV8HI_UV16QI, B_VX, BT_UV8HI, BT_UV16QI)
DEF_FN_TYPE_2 (BT_FN_UV8HI_UV8HI, B_VX, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_2 (BT_FN_UV8HI_USHORTCONSTPTR, B_VX, BT_UV8HI, BT_USHORTCONSTPTR)
+DEF_FN_TYPE_2 (BT_FN_V16QI_SCHAR, B_VX, BT_V16QI, BT_SCHAR)
DEF_FN_TYPE_2 (BT_FN_V16QI_UCHAR, B_VX, BT_V16QI, BT_UCHAR)
DEF_FN_TYPE_2 (BT_FN_V16QI_V16QI, B_VX, BT_V16QI, BT_V16QI)
+DEF_FN_TYPE_2 (BT_FN_V2DF_DBL, B_VX, BT_V2DF, BT_DBL)
+DEF_FN_TYPE_2 (BT_FN_V2DF_FLTCONSTPTR, B_VX, BT_V2DF, BT_FLTCONSTPTR)
+DEF_FN_TYPE_2 (BT_FN_V2DF_V2DF, B_VX, BT_V2DF, BT_V2DF)
+DEF_FN_TYPE_2 (BT_FN_V2DI_SHORT, B_VX, BT_V2DI, BT_SHORT)
DEF_FN_TYPE_2 (BT_FN_V2DI_V16QI, B_VX, BT_V2DI, BT_V16QI)
DEF_FN_TYPE_2 (BT_FN_V2DI_V2DI, B_VX, BT_V2DI, BT_V2DI)
-DEF_FN_TYPE_2 (BT_FN_V2DI_SHORT, B_VX, BT_V2DI, BT_SHORT)
-DEF_FN_TYPE_2 (BT_FN_V2DF_V2DF, B_VX, BT_V2DF, BT_V2DF)
-DEF_FN_TYPE_2 (BT_FN_V2DI_V8HI, B_VX, BT_V2DI, BT_V8HI)
-DEF_FN_TYPE_2 (BT_FN_V2DF_FLTCONSTPTR, B_VX, BT_V2DF, BT_FLTCONSTPTR)
DEF_FN_TYPE_2 (BT_FN_V2DI_V4SI, B_VX, BT_V2DI, BT_V4SI)
-DEF_FN_TYPE_2 (BT_FN_V2DF_DBL, B_VX, BT_V2DF, BT_DBL)
-DEF_FN_TYPE_2 (BT_FN_V4SI_V8HI, B_VX, BT_V4SI, BT_V8HI)
-DEF_FN_TYPE_2 (BT_FN_V4SI_V4SI, B_VX, BT_V4SI, BT_V4SI)
+DEF_FN_TYPE_2 (BT_FN_V2DI_V8HI, B_VX, BT_V2DI, BT_V8HI)
DEF_FN_TYPE_2 (BT_FN_V4SI_SHORT, B_VX, BT_V4SI, BT_SHORT)
+DEF_FN_TYPE_2 (BT_FN_V4SI_V4SI, B_VX, BT_V4SI, BT_V4SI)
+DEF_FN_TYPE_2 (BT_FN_V4SI_V8HI, B_VX, BT_V4SI, BT_V8HI)
+DEF_FN_TYPE_2 (BT_FN_V8HI_SHORT, B_VX, BT_V8HI, BT_SHORT)
DEF_FN_TYPE_2 (BT_FN_V8HI_V16QI, B_VX, BT_V8HI, BT_V16QI)
DEF_FN_TYPE_2 (BT_FN_V8HI_V8HI, B_VX, BT_V8HI, BT_V8HI)
-DEF_FN_TYPE_2 (BT_FN_V8HI_SHORT, B_VX, BT_V8HI, BT_SHORT)
-DEF_FN_TYPE_3 (BT_FN_INT_V2DI_V2DI, B_VX, BT_INT, BT_V2DI, BT_V2DI)
+DEF_FN_TYPE_2 (BT_FN_VOID_INT, B_HTM, BT_VOID, BT_INT)
+DEF_FN_TYPE_2 (BT_FN_VOID_UINT, 0, BT_VOID, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_DBL_V2DF_INT, B_VX, BT_DBL, BT_V2DF, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_INT_OV4SI_INT, B_VX, BT_INT, BT_OV4SI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_INT_OV4SI_OV4SI, B_VX, BT_INT, BT_OV4SI, BT_OV4SI)
-DEF_FN_TYPE_3 (BT_FN_INT_V2DF_V2DF, B_VX, BT_INT, BT_V2DF, BT_V2DF)
-DEF_FN_TYPE_3 (BT_FN_USHORT_UV8HI_INT, B_VX, BT_USHORT, BT_UV8HI, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_INT_UV16QI_UV16QI, B_VX, BT_INT, BT_UV16QI, BT_UV16QI)
DEF_FN_TYPE_3 (BT_FN_INT_UV2DI_UV2DI, B_VX, BT_INT, BT_UV2DI, BT_UV2DI)
-DEF_FN_TYPE_3 (BT_FN_ULONGLONG_UV2DI_INT, B_VX, BT_ULONGLONG, BT_UV2DI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_INT_UV4SI_UV4SI, B_VX, BT_INT, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_UCHAR_UV16QI_INT, B_VX, BT_UCHAR, BT_UV16QI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_INT_UV8HI_UV8HI, B_VX, BT_INT, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_3 (BT_FN_INT_V4SI_V4SI, B_VX, BT_INT, BT_V4SI, BT_V4SI)
-DEF_FN_TYPE_3 (BT_FN_INT_UV16QI_UV16QI, B_VX, BT_INT, BT_UV16QI, BT_UV16QI)
DEF_FN_TYPE_3 (BT_FN_INT_V16QI_V16QI, B_VX, BT_INT, BT_V16QI, BT_V16QI)
-DEF_FN_TYPE_3 (BT_FN_INT_VOIDPTR_INT, B_HTM, BT_INT, BT_VOIDPTR, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_DBL_V2DF_INT, B_VX, BT_DBL, BT_V2DF, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_VOID_UINT64PTR_UINT64, B_HTM, BT_VOID, BT_UINT64PTR, BT_UINT64)
+DEF_FN_TYPE_3 (BT_FN_INT_V2DF_V2DF, B_VX, BT_INT, BT_V2DF, BT_V2DF)
+DEF_FN_TYPE_3 (BT_FN_INT_V2DI_V2DI, B_VX, BT_INT, BT_V2DI, BT_V2DI)
+DEF_FN_TYPE_3 (BT_FN_INT_V4SI_V4SI, B_VX, BT_INT, BT_V4SI, BT_V4SI)
DEF_FN_TYPE_3 (BT_FN_INT_V8HI_V8HI, B_VX, BT_INT, BT_V8HI, BT_V8HI)
-DEF_FN_TYPE_3 (BT_FN_UINT_VOIDCONSTPTR_INT, B_VX, BT_UINT, BT_VOIDCONSTPTR, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_INT_OV4SI_INT, B_VX, BT_INT, BT_OV4SI, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_VOID_V2DF_FLTPTR, B_VX, BT_VOID, BT_V2DF, BT_FLTPTR)
+DEF_FN_TYPE_3 (BT_FN_INT_VOIDPTR_INT, B_HTM, BT_INT, BT_VOIDPTR, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_OV2DI_LONGLONG_LONGLONG, B_VX, BT_OV2DI, BT_LONGLONG, BT_LONGLONG)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_INTCONSTPTR_INT, B_VX, BT_OV4SI, BT_INTCONSTPTR, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_INTCONSTPTR_UINT, B_VX, BT_OV4SI, BT_INTCONSTPTR, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_INT_INT, B_VX, BT_OV4SI, BT_INT, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_INTPTR)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_UCHAR)
+DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_ULONG, B_VX, BT_OV4SI, BT_OV4SI, BT_ULONG)
+DEF_FN_TYPE_3 (BT_FN_UCHAR_UV16QI_INT, B_VX, BT_UCHAR, BT_UV16QI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_UINT_UV4SI_INT, B_VX, BT_UINT, BT_UV4SI, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV8HI_UV8HI, B_VX, BT_UV16QI, BT_UV8HI, BT_UV8HI)
+DEF_FN_TYPE_3 (BT_FN_UINT_VOIDCONSTPTR_INT, B_VX, BT_UINT, BT_VOIDCONSTPTR, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_ULONGLONG_UV2DI_INT, B_VX, BT_ULONGLONG, BT_UV2DI, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_USHORT_UV8HI_INT, B_VX, BT_USHORT, BT_UV8HI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_UV16QI_UCHARCONSTPTR_USHORT, B_VX, BT_UV16QI, BT_UCHARCONSTPTR, BT_USHORT)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UV16QI, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UCHAR, B_VX, BT_UV16QI, BT_UV16QI, BT_UCHAR)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV4SI_UV4SI, B_VX, BT_UV16QI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UCHAR_UCHAR, B_VX, BT_UV16QI, BT_UCHAR, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV16QI_UCHAR_INT, B_VX, BT_UV16QI, BT_UCHAR, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV2DI_UV2DI, B_VX, BT_UV16QI, BT_UV2DI, BT_UV2DI)
-DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UINT, B_VX, BT_UV16QI, BT_UV16QI, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UCHAR_UCHAR, B_VX, BT_UV16QI, BT_UCHAR, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_INTPTR, B_VX, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_FN_TYPE_3 (BT_FN_UV2DI_V2DF_INT, B_VX, BT_UV2DI, BT_V2DF, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UCHAR, B_VX, BT_UV16QI, BT_UV16QI, BT_UCHAR)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UINT, B_VX, BT_UV16QI, BT_UV16QI, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV16QI_UV16QI, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV2DI_UV2DI, B_VX, BT_UV16QI, BT_UV2DI, BT_UV2DI)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV4SI_UV4SI, B_VX, BT_UV16QI, BT_UV4SI, BT_UV4SI)
+DEF_FN_TYPE_3 (BT_FN_UV16QI_UV8HI_UV8HI, B_VX, BT_UV16QI, BT_UV8HI, BT_UV8HI)
+DEF_FN_TYPE_3 (BT_FN_UV2DI_UCHAR_UCHAR, B_VX, BT_UV2DI, BT_UCHAR, BT_UCHAR)
+DEF_FN_TYPE_3 (BT_FN_UV2DI_ULONGLONG_INT, B_VX, BT_UV2DI, BT_ULONGLONG, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_UV2DI_UV2DI_UCHAR, B_VX, BT_UV2DI, BT_UV2DI, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV2DI_UV2DI_UINT, B_VX, BT_UV2DI, BT_UV2DI, BT_UINT)
-DEF_FN_TYPE_3 (BT_FN_OV2DI_LONGLONG_LONGLONG, B_VX, BT_OV2DI, BT_LONGLONG, BT_LONGLONG)
DEF_FN_TYPE_3 (BT_FN_UV2DI_UV2DI_UV2DI, B_VX, BT_UV2DI, BT_UV2DI, BT_UV2DI)
-DEF_FN_TYPE_3 (BT_FN_UV2DI_UV2DI_UCHAR, B_VX, BT_UV2DI, BT_UV2DI, BT_UCHAR)
-DEF_FN_TYPE_3 (BT_FN_UV2DI_ULONGLONG_INT, B_VX, BT_UV2DI, BT_ULONGLONG, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_UV2DI_UV8HI_UV8HI, B_VX, BT_UV2DI, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_3 (BT_FN_UV2DI_UCHAR_UCHAR, B_VX, BT_UV2DI, BT_UCHAR, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV2DI_UV4SI_UV4SI, B_VX, BT_UV2DI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_INT_INT, B_VX, BT_OV4SI, BT_INT, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_UV2DI_UV8HI_UV8HI, B_VX, BT_UV2DI, BT_UV8HI, BT_UV8HI)
+DEF_FN_TYPE_3 (BT_FN_UV2DI_V2DF_INT, B_VX, BT_UV2DI, BT_V2DF, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_UV4SI_UCHAR_UCHAR, B_VX, BT_UV4SI, BT_UCHAR, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV4SI_UINT_INT, B_VX, BT_UV4SI, BT_UINT, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UCHAR, B_VX, BT_UV4SI, BT_UV4SI, BT_UCHAR)
-DEF_FN_TYPE_3 (BT_FN_UV4SI_UV8HI_UV8HI, B_VX, BT_UV4SI, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_UCHAR)
-DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UINT, B_VX, BT_UV4SI, BT_UV4SI, BT_UINT)
DEF_FN_TYPE_3 (BT_FN_UV4SI_UV16QI_UV16QI, B_VX, BT_UV4SI, BT_UV16QI, BT_UV16QI)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_INTCONSTPTR_INT, B_VX, BT_OV4SI, BT_INTCONSTPTR, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_INTPTR)
DEF_FN_TYPE_3 (BT_FN_UV4SI_UV2DI_UV2DI, B_VX, BT_UV4SI, BT_UV2DI, BT_UV2DI)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_INTCONSTPTR_UINT, B_VX, BT_OV4SI, BT_INTCONSTPTR, BT_UINT)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_ULONG, B_VX, BT_OV4SI, BT_OV4SI, BT_ULONG)
-DEF_FN_TYPE_3 (BT_FN_OV4SI_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI)
-DEF_FN_TYPE_3 (BT_FN_UV4SI_UCHAR_UCHAR, B_VX, BT_UV4SI, BT_UCHAR, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_INTPTR, B_VX, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_FN_TYPE_3 (BT_FN_UV8HI_UV4SI_UV4SI, B_VX, BT_UV8HI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_UV8HI_UV16QI_UV16QI, B_VX, BT_UV8HI, BT_UV16QI, BT_UV16QI)
+DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UCHAR, B_VX, BT_UV4SI, BT_UV4SI, BT_UCHAR)
+DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UINT, B_VX, BT_UV4SI, BT_UV4SI, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_UV4SI_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI)
+DEF_FN_TYPE_3 (BT_FN_UV4SI_UV8HI_UV8HI, B_VX, BT_UV4SI, BT_UV8HI, BT_UV8HI)
DEF_FN_TYPE_3 (BT_FN_UV8HI_UCHAR_UCHAR, B_VX, BT_UV8HI, BT_UCHAR, BT_UCHAR)
-DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_UV8HI, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_UCHAR, B_VX, BT_UV8HI, BT_UV8HI, BT_UCHAR)
+DEF_FN_TYPE_3 (BT_FN_UV8HI_USHORT_INT, B_VX, BT_UV8HI, BT_USHORT, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_UV8HI_UV16QI_UV16QI, B_VX, BT_UV8HI, BT_UV16QI, BT_UV16QI)
+DEF_FN_TYPE_3 (BT_FN_UV8HI_UV4SI_UV4SI, B_VX, BT_UV8HI, BT_UV4SI, BT_UV4SI)
DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_INTPTR, B_VX, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_UCHAR, B_VX, BT_UV8HI, BT_UV8HI, BT_UCHAR)
DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_UINT, B_VX, BT_UV8HI, BT_UV8HI, BT_UINT)
-DEF_FN_TYPE_3 (BT_FN_UV8HI_USHORT_INT, B_VX, BT_UV8HI, BT_USHORT, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_V16QI_UV16QI_UV16QI, B_VX, BT_V16QI, BT_UV16QI, BT_UV16QI)
-DEF_FN_TYPE_3 (BT_FN_V16QI_UINT_VOIDCONSTPTR, B_VX, BT_V16QI, BT_UINT, BT_VOIDCONSTPTR)
-DEF_FN_TYPE_3 (BT_FN_V16QI_V8HI_V8HI, B_VX, BT_V16QI, BT_V8HI, BT_V8HI)
+DEF_FN_TYPE_3 (BT_FN_UV8HI_UV8HI_UV8HI, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI)
DEF_FN_TYPE_3 (BT_FN_V16QI_BV16QI_V16QI, B_VX, BT_V16QI, BT_BV16QI, BT_V16QI)
+DEF_FN_TYPE_3 (BT_FN_V16QI_UINT_VOIDCONSTPTR, B_VX, BT_V16QI, BT_UINT, BT_VOIDCONSTPTR)
+DEF_FN_TYPE_3 (BT_FN_V16QI_UV16QI_UV16QI, B_VX, BT_V16QI, BT_UV16QI, BT_UV16QI)
DEF_FN_TYPE_3 (BT_FN_V16QI_V16QI_V16QI, B_VX, BT_V16QI, BT_V16QI, BT_V16QI)
-DEF_FN_TYPE_3 (BT_FN_V2DI_V2DF_INT, B_VX, BT_V2DI, BT_V2DF, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_V2DI_V2DF_V2DF, B_VX, BT_V2DI, BT_V2DF, BT_V2DF)
-DEF_FN_TYPE_3 (BT_FN_V2DI_V4SI_V4SI, B_VX, BT_V2DI, BT_V4SI, BT_V4SI)
-DEF_FN_TYPE_3 (BT_FN_V2DI_UV2DI_UV2DI, B_VX, BT_V2DI, BT_UV2DI, BT_UV2DI)
-DEF_FN_TYPE_3 (BT_FN_V2DI_V2DI_V2DI, B_VX, BT_V2DI, BT_V2DI, BT_V2DI)
-DEF_FN_TYPE_3 (BT_FN_V2DF_V2DI_INT, B_VX, BT_V2DF, BT_V2DI, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_V16QI_V8HI_V8HI, B_VX, BT_V16QI, BT_V8HI, BT_V8HI)
+DEF_FN_TYPE_3 (BT_FN_V2DF_DBL_INT, B_VX, BT_V2DF, BT_DBL, BT_INT)
DEF_FN_TYPE_3 (BT_FN_V2DF_UV2DI_INT, B_VX, BT_V2DF, BT_UV2DI, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_V2DF_UV4SI_INT, B_VX, BT_V2DF, BT_UV4SI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_V2DF_V2DF_V2DF, B_VX, BT_V2DF, BT_V2DF, BT_V2DF)
-DEF_FN_TYPE_3 (BT_FN_V2DF_DBL_INT, B_VX, BT_V2DF, BT_DBL, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_V2DF_V2DI_INT, B_VX, BT_V2DF, BT_V2DI, BT_INT)
DEF_FN_TYPE_3 (BT_FN_V2DI_BV2DI_V2DI, B_VX, BT_V2DI, BT_BV2DI, BT_V2DI)
-DEF_FN_TYPE_3 (BT_FN_V2DF_UV4SI_INT, B_VX, BT_V2DF, BT_UV4SI, BT_INT)
-DEF_FN_TYPE_3 (BT_FN_V4SI_V4SI_V4SI, B_VX, BT_V4SI, BT_V4SI, BT_V4SI)
-DEF_FN_TYPE_3 (BT_FN_V4SI_V8HI_V8HI, B_VX, BT_V4SI, BT_V8HI, BT_V8HI)
+DEF_FN_TYPE_3 (BT_FN_V2DI_UV2DI_UV2DI, B_VX, BT_V2DI, BT_UV2DI, BT_UV2DI)
+DEF_FN_TYPE_3 (BT_FN_V2DI_V2DF_INT, B_VX, BT_V2DI, BT_V2DF, BT_INT)
+DEF_FN_TYPE_3 (BT_FN_V2DI_V2DF_V2DF, B_VX, BT_V2DI, BT_V2DF, BT_V2DF)
+DEF_FN_TYPE_3 (BT_FN_V2DI_V2DI_V2DI, B_VX, BT_V2DI, BT_V2DI, BT_V2DI)
+DEF_FN_TYPE_3 (BT_FN_V2DI_V4SI_V4SI, B_VX, BT_V2DI, BT_V4SI, BT_V4SI)
+DEF_FN_TYPE_3 (BT_FN_V4SI_BV4SI_V4SI, B_VX, BT_V4SI, BT_BV4SI, BT_V4SI)
DEF_FN_TYPE_3 (BT_FN_V4SI_INT_VOIDPTR, B_VX, BT_V4SI, BT_INT, BT_VOIDPTR)
-DEF_FN_TYPE_3 (BT_FN_V4SI_V2DI_V2DI, B_VX, BT_V4SI, BT_V2DI, BT_V2DI)
DEF_FN_TYPE_3 (BT_FN_V4SI_UV4SI_UV4SI, B_VX, BT_V4SI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_3 (BT_FN_V4SI_BV4SI_V4SI, B_VX, BT_V4SI, BT_BV4SI, BT_V4SI)
+DEF_FN_TYPE_3 (BT_FN_V4SI_V2DI_V2DI, B_VX, BT_V4SI, BT_V2DI, BT_V2DI)
+DEF_FN_TYPE_3 (BT_FN_V4SI_V4SI_V4SI, B_VX, BT_V4SI, BT_V4SI, BT_V4SI)
+DEF_FN_TYPE_3 (BT_FN_V4SI_V8HI_V8HI, B_VX, BT_V4SI, BT_V8HI, BT_V8HI)
DEF_FN_TYPE_3 (BT_FN_V8HI_BV8HI_V8HI, B_VX, BT_V8HI, BT_BV8HI, BT_V8HI)
+DEF_FN_TYPE_3 (BT_FN_V8HI_UV8HI_UV8HI, B_VX, BT_V8HI, BT_UV8HI, BT_UV8HI)
DEF_FN_TYPE_3 (BT_FN_V8HI_V16QI_V16QI, B_VX, BT_V8HI, BT_V16QI, BT_V16QI)
DEF_FN_TYPE_3 (BT_FN_V8HI_V4SI_V4SI, B_VX, BT_V8HI, BT_V4SI, BT_V4SI)
-DEF_FN_TYPE_3 (BT_FN_V8HI_UV8HI_UV8HI, B_VX, BT_V8HI, BT_UV8HI, BT_UV8HI)
DEF_FN_TYPE_3 (BT_FN_V8HI_V8HI_V8HI, B_VX, BT_V8HI, BT_V8HI, BT_V8HI)
-DEF_FN_TYPE_4 (BT_FN_VOID_OV4SI_VOIDPTR_UINT, B_VX, BT_VOID, BT_OV4SI, BT_VOIDPTR, BT_UINT)
+DEF_FN_TYPE_3 (BT_FN_VOID_UINT64PTR_UINT64, B_HTM, BT_VOID, BT_UINT64PTR, BT_UINT64)
+DEF_FN_TYPE_3 (BT_FN_VOID_V2DF_FLTPTR, B_VX, BT_VOID, BT_V2DF, BT_FLTPTR)
DEF_FN_TYPE_4 (BT_FN_INT_OV4SI_OV4SI_INTPTR, B_VX, BT_INT, BT_OV4SI, BT_OV4SI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_VOID_V16QI_UINT_VOIDPTR, B_VX, BT_VOID, BT_V16QI, BT_UINT, BT_VOIDPTR)
-DEF_FN_TYPE_4 (BT_FN_VOID_OV4SI_INT_VOIDPTR, B_VX, BT_VOID, BT_OV4SI, BT_INT, BT_VOIDPTR)
-DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UV16QI_INTPTR, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UV16QI_INT, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_INT_OV4SI_INT, B_VX, BT_OV4SI, BT_INT, BT_OV4SI, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_INT, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_OV4SI)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_UCHAR)
+DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_ULONGLONG, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_ULONGLONG)
DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UCHAR_INT, B_VX, BT_UV16QI, BT_UV16QI, BT_UCHAR, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UV16QI_INT, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UV16QI_INTPTR, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_UV16QI_UV16QI_UV16QI_UV16QI, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
-DEF_FN_TYPE_4 (BT_FN_UV16QI_UV8HI_UV8HI_INTPTR, B_VX, BT_UV16QI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_UV16QI_UV2DI_UV2DI_UV16QI, B_VX, BT_UV16QI, BT_UV2DI, BT_UV2DI, BT_UV16QI)
+DEF_FN_TYPE_4 (BT_FN_UV16QI_UV8HI_UV8HI_INTPTR, B_VX, BT_UV16QI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_UV2DI_UV2DI_ULONGLONG_INT, B_VX, BT_UV2DI, BT_UV2DI, BT_ULONGLONG, BT_INT)
DEF_FN_TYPE_4 (BT_FN_UV2DI_UV2DI_UV2DI_INT, B_VX, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_INT)
DEF_FN_TYPE_4 (BT_FN_UV2DI_UV4SI_UV4SI_UV2DI, B_VX, BT_UV2DI, BT_UV4SI, BT_UV4SI, BT_UV2DI)
-DEF_FN_TYPE_4 (BT_FN_UV2DI_UV2DI_ULONGLONG_INT, B_VX, BT_UV2DI, BT_UV2DI, BT_ULONGLONG, BT_INT)
DEF_FN_TYPE_4 (BT_FN_UV4SI_UV2DI_UV2DI_INTPTR, B_VX, BT_UV4SI, BT_UV2DI, BT_UV2DI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_INT, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INT)
-DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UV4SI_INTPTR, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_INT_OV4SI_INT, B_VX, BT_OV4SI, BT_INT, BT_OV4SI, BT_INT)
+DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UINT_INT, B_VX, BT_UV4SI, BT_UV4SI, BT_UINT, BT_INT)
DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UV4SI_INT, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_ULONGLONG, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_ULONGLONG)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_OV4SI, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_OV4SI)
+DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UV4SI_INTPTR, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UV4SI_UV4SI, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
DEF_FN_TYPE_4 (BT_FN_UV4SI_UV8HI_UV8HI_UV4SI, B_VX, BT_UV4SI, BT_UV8HI, BT_UV8HI, BT_UV4SI)
-DEF_FN_TYPE_4 (BT_FN_UV4SI_UV4SI_UINT_INT, B_VX, BT_UV4SI, BT_UV4SI, BT_UINT, BT_INT)
-DEF_FN_TYPE_4 (BT_FN_OV4SI_OV4SI_OV4SI_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_UCHAR)
+DEF_FN_TYPE_4 (BT_FN_UV8HI_UV16QI_UV16QI_UV8HI, B_VX, BT_UV8HI, BT_UV16QI, BT_UV16QI, BT_UV8HI)
DEF_FN_TYPE_4 (BT_FN_UV8HI_UV4SI_UV4SI_INTPTR, B_VX, BT_UV8HI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_USHORT_INT, B_VX, BT_UV8HI, BT_UV8HI, BT_USHORT, BT_INT)
DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_UV8HI_INT, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT)
-DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_UV8HI_UV8HI, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
-DEF_FN_TYPE_4 (BT_FN_UV8HI_UV16QI_UV16QI_UV8HI, B_VX, BT_UV8HI, BT_UV16QI, BT_UV16QI, BT_UV8HI)
DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_UV8HI_INTPTR, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_USHORT_INT, B_VX, BT_UV8HI, BT_UV8HI, BT_USHORT, BT_INT)
-DEF_FN_TYPE_4 (BT_FN_V16QI_V8HI_V8HI_INTPTR, B_VX, BT_V16QI, BT_V8HI, BT_V8HI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_V16QI_V16QI_V16QI_INTPTR, B_VX, BT_V16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_UV8HI_UV8HI_UV8HI_UV8HI, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
DEF_FN_TYPE_4 (BT_FN_V16QI_UV16QI_UV16QI_INTPTR, B_VX, BT_V16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V16QI_V16QI_V16QI_INTPTR, B_VX, BT_V16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V16QI_V16QI_V16QI_V16QI, B_VX, BT_V16QI, BT_V16QI, BT_V16QI, BT_V16QI)
-DEF_FN_TYPE_4 (BT_FN_V2DI_V2DF_INT_INTPTR, B_VX, BT_V2DI, BT_V2DF, BT_INT, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_V2DI_V2DI_V2DI_INTPTR, B_VX, BT_V2DI, BT_V2DI, BT_V2DI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V16QI_V8HI_V8HI_INTPTR, B_VX, BT_V16QI, BT_V8HI, BT_V8HI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V2DF_V2DF_DBL_INT, B_VX, BT_V2DF, BT_V2DF, BT_DBL, BT_INT)
DEF_FN_TYPE_4 (BT_FN_V2DF_V2DF_UCHAR_UCHAR, B_VX, BT_V2DF, BT_V2DF, BT_UCHAR, BT_UCHAR)
-DEF_FN_TYPE_4 (BT_FN_V2DI_V2DF_V2DF_INTPTR, B_VX, BT_V2DI, BT_V2DF, BT_V2DF, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_V2DI_V4SI_V4SI_V2DI, B_VX, BT_V2DI, BT_V4SI, BT_V4SI, BT_V2DI)
DEF_FN_TYPE_4 (BT_FN_V2DF_V2DF_V2DF_V2DF, B_VX, BT_V2DF, BT_V2DF, BT_V2DF, BT_V2DF)
DEF_FN_TYPE_4 (BT_FN_V2DI_UV2DI_UV2DI_INTPTR, B_VX, BT_V2DI, BT_UV2DI, BT_UV2DI, BT_INTPTR)
-DEF_FN_TYPE_4 (BT_FN_V4SI_V8HI_V8HI_V4SI, B_VX, BT_V4SI, BT_V8HI, BT_V8HI, BT_V4SI)
+DEF_FN_TYPE_4 (BT_FN_V2DI_V2DF_INT_INTPTR, B_VX, BT_V2DI, BT_V2DF, BT_INT, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V2DI_V2DF_V2DF_INTPTR, B_VX, BT_V2DI, BT_V2DF, BT_V2DF, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V2DI_V2DI_V2DI_INTPTR, B_VX, BT_V2DI, BT_V2DI, BT_V2DI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V2DI_V4SI_V4SI_V2DI, B_VX, BT_V2DI, BT_V4SI, BT_V4SI, BT_V2DI)
DEF_FN_TYPE_4 (BT_FN_V4SI_UV4SI_UV4SI_INTPTR, B_VX, BT_V4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V4SI_V2DI_V2DI_INTPTR, B_VX, BT_V4SI, BT_V2DI, BT_V2DI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V4SI_V4SI_V4SI_INTPTR, B_VX, BT_V4SI, BT_V4SI, BT_V4SI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V4SI_V4SI_V4SI_V4SI, B_VX, BT_V4SI, BT_V4SI, BT_V4SI, BT_V4SI)
-DEF_FN_TYPE_4 (BT_FN_V8HI_V8HI_V8HI_V8HI, B_VX, BT_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
+DEF_FN_TYPE_4 (BT_FN_V4SI_V8HI_V8HI_V4SI, B_VX, BT_V4SI, BT_V8HI, BT_V8HI, BT_V4SI)
DEF_FN_TYPE_4 (BT_FN_V8HI_UV8HI_UV8HI_INTPTR, B_VX, BT_V8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V8HI_V16QI_V16QI_V8HI, B_VX, BT_V8HI, BT_V16QI, BT_V16QI, BT_V8HI)
-DEF_FN_TYPE_4 (BT_FN_V8HI_V8HI_V8HI_INTPTR, B_VX, BT_V8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
DEF_FN_TYPE_4 (BT_FN_V8HI_V4SI_V4SI_INTPTR, B_VX, BT_V8HI, BT_V4SI, BT_V4SI, BT_INTPTR)
-DEF_FN_TYPE_5 (BT_FN_VOID_UV4SI_UV4SI_UINTPTR_ULONGLONG, B_VX, BT_VOID, BT_UV4SI, BT_UV4SI, BT_UINTPTR, BT_ULONGLONG)
-DEF_FN_TYPE_5 (BT_FN_VOID_UV2DI_UV2DI_ULONGLONGPTR_ULONGLONG, B_VX, BT_VOID, BT_UV2DI, BT_UV2DI, BT_ULONGLONGPTR, BT_ULONGLONG)
-DEF_FN_TYPE_5 (BT_FN_VOID_V4SI_V4SI_INTPTR_ULONGLONG, B_VX, BT_VOID, BT_V4SI, BT_V4SI, BT_INTPTR, BT_ULONGLONG)
+DEF_FN_TYPE_4 (BT_FN_V8HI_V8HI_V8HI_INTPTR, B_VX, BT_V8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
+DEF_FN_TYPE_4 (BT_FN_V8HI_V8HI_V8HI_V8HI, B_VX, BT_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
+DEF_FN_TYPE_4 (BT_FN_VOID_OV4SI_INT_VOIDPTR, B_VX, BT_VOID, BT_OV4SI, BT_INT, BT_VOIDPTR)
+DEF_FN_TYPE_4 (BT_FN_VOID_OV4SI_VOIDPTR_UINT, B_VX, BT_VOID, BT_OV4SI, BT_VOIDPTR, BT_UINT)
+DEF_FN_TYPE_4 (BT_FN_VOID_V16QI_UINT_VOIDPTR, B_VX, BT_VOID, BT_V16QI, BT_UINT, BT_VOIDPTR)
+DEF_FN_TYPE_5 (BT_FN_OV4SI_OV4SI_OUV4SI_INTCONSTPTR_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_OUV4SI, BT_INTCONSTPTR, BT_UCHAR)
+DEF_FN_TYPE_5 (BT_FN_OV4SI_OV4SI_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INTPTR)
DEF_FN_TYPE_5 (BT_FN_UV16QI_UV16QI_UV16QI_INT_INTPTR, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT, BT_INTPTR)
DEF_FN_TYPE_5 (BT_FN_UV16QI_UV16QI_UV16QI_UV16QI_INT, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT)
-DEF_FN_TYPE_5 (BT_FN_UV2DI_UV2DI_UV2DI_UV2DI_INT, B_VX, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_INT)
DEF_FN_TYPE_5 (BT_FN_UV2DI_UV2DI_UV2DI_ULONGLONGCONSTPTR_UCHAR, B_VX, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UCHAR)
-DEF_FN_TYPE_5 (BT_FN_UV4SI_UV4SI_UV4SI_UV4SI_INT, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT)
+DEF_FN_TYPE_5 (BT_FN_UV2DI_UV2DI_UV2DI_UV2DI_INT, B_VX, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_INT)
DEF_FN_TYPE_5 (BT_FN_UV4SI_UV4SI_UV4SI_INT_INTPTR, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT, BT_INTPTR)
-DEF_FN_TYPE_5 (BT_FN_OV4SI_OV4SI_OV4SI_OV4SI_INTPTR, B_VX, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_OV4SI, BT_INTPTR)
-DEF_FN_TYPE_5 (BT_FN_OV4SI_OV4SI_OUV4SI_INTCONSTPTR_UCHAR, B_VX, BT_OV4SI, BT_OV4SI, BT_OUV4SI, BT_INTCONSTPTR, BT_UCHAR)
DEF_FN_TYPE_5 (BT_FN_UV4SI_UV4SI_UV4SI_UINTCONSTPTR_UCHAR, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UINTCONSTPTR, BT_UCHAR)
-DEF_FN_TYPE_5 (BT_FN_UV8HI_UV8HI_UV8HI_UV8HI_INT, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT)
+DEF_FN_TYPE_5 (BT_FN_UV4SI_UV4SI_UV4SI_UV4SI_INT, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT)
DEF_FN_TYPE_5 (BT_FN_UV8HI_UV8HI_UV8HI_INT_INTPTR, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT, BT_INTPTR)
+DEF_FN_TYPE_5 (BT_FN_UV8HI_UV8HI_UV8HI_UV8HI_INT, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT)
+DEF_FN_TYPE_5 (BT_FN_VOID_UV2DI_UV2DI_ULONGLONGPTR_ULONGLONG, B_VX, BT_VOID, BT_UV2DI, BT_UV2DI, BT_ULONGLONGPTR, BT_ULONGLONG)
+DEF_FN_TYPE_5 (BT_FN_VOID_UV4SI_UV4SI_UINTPTR_ULONGLONG, B_VX, BT_VOID, BT_UV4SI, BT_UV4SI, BT_UINTPTR, BT_ULONGLONG)
+DEF_FN_TYPE_5 (BT_FN_VOID_V4SI_V4SI_INTPTR_ULONGLONG, B_VX, BT_VOID, BT_V4SI, BT_V4SI, BT_INTPTR, BT_ULONGLONG)
DEF_FN_TYPE_6 (BT_FN_UV16QI_UV16QI_UV16QI_UV16QI_INT_INTPTR, B_VX, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT, BT_INTPTR)
DEF_FN_TYPE_6 (BT_FN_UV4SI_UV4SI_UV4SI_UV4SI_INT_INTPTR, B_VX, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT, BT_INTPTR)
DEF_FN_TYPE_6 (BT_FN_UV8HI_UV8HI_UV8HI_UV8HI_INT_INTPTR, B_VX, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT, BT_INTPTR)
DEF_OV_TYPE (BT_OV_BV16QI_BV16QI, BT_BV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHAR, BT_UV16QI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_UV16QI_V16QI, BT_UV16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR, BT_UV16QI, BT_UCHARCONSTPTR)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI, BT_UV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_INTPTR, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_UV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_INTPTR, BT_BV16QI, BT_BV16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UCHAR, BT_BV16QI, BT_BV16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV16QI, BT_BV16QI, BT_BV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV4SI, BT_BV16QI, BT_BV16QI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV8HI, BT_BV16QI, BT_BV16QI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV16QI_BV8HI_BV8HI, BT_BV16QI, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI, BT_BV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_INTPTR, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_UV16QI, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_UV16QI_INTPTR, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV16QI_V16QI_V16QI, BT_BV16QI, BT_V16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_BV16QI_V16QI_V16QI_INTPTR, BT_BV16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_INT, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_UV16QI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_UV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UCHAR, BT_BV2DI, BT_BV2DI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV16QI, BT_BV2DI, BT_BV2DI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV2DI_ULONGLONGCONSTPTR_UCHAR, BT_BV2DI, BT_BV2DI, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV4SI, BT_BV2DI, BT_BV2DI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV8HI, BT_BV2DI, BT_BV2DI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_BV2DI_BV4SI, BT_BV2DI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_UV2DI_V2DI, BT_UV2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV4SI, BT_UV2DI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG, BT_UV2DI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONGCONSTPTR, BT_UV2DI, BT_ULONGLONGCONSTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_V4SI, BT_UV4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV8HI, BT_BV4SI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR, BT_UV4SI, BT_UINTCONSTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UINT, BT_UV4SI, BT_UINT)
+DEF_OV_TYPE (BT_OV_BV2DI_UV2DI_UV2DI, BT_BV2DI, BT_UV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_BV2DI_V2DF_V2DF, BT_BV2DI, BT_V2DF, BT_V2DF)
+DEF_OV_TYPE (BT_OV_BV2DI_V2DI_V2DI, BT_BV2DI, BT_V2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV2DI_BV2DI, BT_BV4SI, BT_BV2DI, BT_BV2DI)
DEF_OV_TYPE (BT_OV_BV4SI_BV4SI, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV8HI, BT_UV4SI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_USHORTCONSTPTR, BT_UV8HI, BT_USHORTCONSTPTR)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_INTPTR, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_UV16QI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_UV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_INTPTR, BT_BV4SI, BT_BV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UCHAR, BT_BV4SI, BT_BV4SI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV16QI, BT_BV4SI, BT_BV4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV4SI, BT_BV4SI, BT_BV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV4SI_UINTCONSTPTR_UCHAR, BT_BV4SI, BT_BV4SI, BT_UV4SI, BT_UINTCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV8HI, BT_BV4SI, BT_BV4SI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV4SI_BV8HI, BT_BV4SI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI, BT_BV4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_INTPTR, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_UV4SI, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_UV4SI_INTPTR, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV4SI_V4SI_V4SI, BT_BV4SI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_BV4SI_V4SI_V4SI_INTPTR, BT_BV4SI, BT_V4SI, BT_V4SI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_BV8HI_BV16QI, BT_BV8HI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_UV8HI_USHORT, BT_UV8HI, BT_USHORT)
-DEF_OV_TYPE (BT_OV_UV8HI_V8HI, BT_UV8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV4SI_BV4SI, BT_BV8HI, BT_BV4SI, BT_BV4SI)
DEF_OV_TYPE (BT_OV_BV8HI_BV8HI, BT_BV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV16QI, BT_UV8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V16QI_SCHAR, BT_V16QI, BT_SCHAR)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V16QI_SCHARCONSTPTR, BT_V16QI, BT_SCHARCONSTPTR)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONG, BT_V2DI, BT_LONGLONG)
-DEF_OV_TYPE (BT_OV_V2DI_V8HI, BT_V2DI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V2DI_V16QI, BT_V2DI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONGCONSTPTR, BT_V2DI, BT_LONGLONGCONSTPTR)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V2DI_V4SI, BT_V2DI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V2DF_DBL, BT_V2DF, BT_DBL)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF, BT_V2DF, BT_V2DF)
-DEF_OV_TYPE (BT_OV_V2DF_DBLCONSTPTR, BT_V2DF, BT_DBLCONSTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_INTCONSTPTR, BT_V4SI, BT_INTCONSTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_INT, BT_V4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_V4SI_V8HI, BT_V4SI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V8HI_V16QI, BT_V8HI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR, BT_V8HI, BT_SHORTCONSTPTR)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V8HI_SHORT, BT_V8HI, BT_SHORT)
-DEF_OV_TYPE (BT_OV_INT_UV2DI_BV2DI, BT_INT, BT_UV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_INTPTR, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_UV16QI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_UV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_INTPTR, BT_BV8HI, BT_BV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UCHAR, BT_BV8HI, BT_BV8HI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV16QI, BT_BV8HI, BT_BV8HI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV4SI, BT_BV8HI, BT_BV8HI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV8HI, BT_BV8HI, BT_BV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI, BT_BV8HI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_INTPTR, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_UV8HI, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_UV8HI_INTPTR, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_BV8HI_V8HI_V8HI, BT_BV8HI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_BV8HI_V8HI_V8HI_INTPTR, BT_BV8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_DBL_V2DF_INT, BT_DBL, BT_V2DF, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_V8HI_UV8HI, BT_INT, BT_V8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_INT_BV8HI_BV8HI, BT_INT, BT_BV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_INT_V4SI_UV4SI, BT_INT, BT_V4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UCHAR_UV16QI_INT, BT_UCHAR, BT_UV16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_V2DI_UV2DI, BT_INT, BT_V2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_SHORT_V8HI_INT, BT_SHORT, BT_V8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_BV8HI_V8HI, BT_INT, BT_BV8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_USHORT_BV8HI_INT, BT_USHORT, BT_BV8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_BV8HI_UV8HI, BT_INT, BT_BV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UINT_UV4SI_INT, BT_UINT, BT_UV4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_UV8HI_UV8HI, BT_INT, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_LONGLONG_V2DI_INT, BT_LONGLONG, BT_V2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_UV8HI_BV8HI, BT_INT, BT_UV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_ULONGLONG_BV2DI_INT, BT_ULONGLONG, BT_BV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_V4SI_V4SI, BT_INT, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_INT_V8HI_BV8HI, BT_INT, BT_V8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_INT_V4SI_BV4SI, BT_INT, BT_V4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_INT_UV16QI_BV16QI, BT_INT, BT_UV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_INT_V2DF_UV2DI, BT_INT, BT_V2DF, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_INT_BV16QI_BV16QI, BT_INT, BT_BV16QI, BT_BV16QI)
DEF_OV_TYPE (BT_OV_INT_BV16QI_UV16QI, BT_INT, BT_BV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_INT_BV16QI_V16QI, BT_INT, BT_BV16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_INT_BV2DI_BV2DI, BT_INT, BT_BV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_INT_BV2DI_UV2DI, BT_INT, BT_BV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_INT_BV2DI_V2DI, BT_INT, BT_BV2DI, BT_V2DI)
DEF_OV_TYPE (BT_OV_INT_BV4SI_BV4SI, BT_INT, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_INT_BV16QI_BV16QI, BT_INT, BT_BV16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_INT_BV4SI_UV4SI, BT_INT, BT_BV4SI, BT_UV4SI)
DEF_OV_TYPE (BT_OV_INT_BV4SI_V4SI, BT_INT, BT_BV4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_INT_BV8HI_BV8HI, BT_INT, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_INT_BV8HI_UV8HI, BT_INT, BT_BV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_INT_BV8HI_V8HI, BT_INT, BT_BV8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_INT_UV16QI_BV16QI, BT_INT, BT_UV16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_INT_UV16QI_UV16QI, BT_INT, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_INT_UV2DI_BV2DI, BT_INT, BT_UV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_INT_UV2DI_UV2DI, BT_INT, BT_UV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_INT_UV4SI_BV4SI, BT_INT, BT_UV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_INT_UV4SI_UV4SI, BT_INT, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_INT_UV8HI_BV8HI, BT_INT, BT_UV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_INT_UV8HI_UV8HI, BT_INT, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_INT_V16QI_BV16QI, BT_INT, BT_V16QI, BT_BV16QI)
DEF_OV_TYPE (BT_OV_INT_V16QI_UV16QI, BT_INT, BT_V16QI, BT_UV16QI)
DEF_OV_TYPE (BT_OV_INT_V16QI_V16QI, BT_INT, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_UCHAR_BV16QI_INT, BT_UCHAR, BT_BV16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_BV4SI_UV4SI, BT_INT, BT_BV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_INT_V2DF_UV2DI, BT_INT, BT_V2DF, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_INT_V2DF_V2DF, BT_INT, BT_V2DF, BT_V2DF)
+DEF_OV_TYPE (BT_OV_INT_V2DI_BV2DI, BT_INT, BT_V2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_INT_V2DI_UV2DI, BT_INT, BT_V2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_INT_V2DI_V2DI, BT_INT, BT_V2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_INT_V4SI_BV4SI, BT_INT, BT_V4SI, BT_BV4SI)
DEF_OV_TYPE (BT_OV_INT_V4SI_INT, BT_INT, BT_V4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_UV4SI_UV4SI, BT_INT, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_ULONGLONG_UV2DI_INT, BT_ULONGLONG, BT_UV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_UV4SI_BV4SI, BT_INT, BT_UV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_INT_V4SI_UV4SI, BT_INT, BT_V4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_INT_V4SI_V4SI, BT_INT, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_INT_V8HI_BV8HI, BT_INT, BT_V8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_INT_V8HI_UV8HI, BT_INT, BT_V8HI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_INT_V8HI_V8HI, BT_INT, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_INT_V2DI_V2DI, BT_INT, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_INT_BV16QI_V16QI, BT_INT, BT_BV16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_INT_V2DI_BV2DI, BT_INT, BT_V2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_LONGLONG_V2DI_INT, BT_LONGLONG, BT_V2DI, BT_INT)
DEF_OV_TYPE (BT_OV_SCHAR_V16QI_INT, BT_SCHAR, BT_V16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_BV2DI_BV2DI, BT_INT, BT_BV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_SHORT_V8HI_INT, BT_SHORT, BT_V8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_UCHAR_BV16QI_INT, BT_UCHAR, BT_BV16QI, BT_INT)
+DEF_OV_TYPE (BT_OV_UCHAR_UV16QI_INT, BT_UCHAR, BT_UV16QI, BT_INT)
DEF_OV_TYPE (BT_OV_UINT_BV4SI_INT, BT_UINT, BT_BV4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_BV2DI_V2DI, BT_INT, BT_BV2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_INT_UV16QI_UV16QI, BT_INT, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_INT_BV2DI_UV2DI, BT_INT, BT_BV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_UINT_UV4SI_INT, BT_UINT, BT_UV4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_ULONGLONG_BV2DI_INT, BT_ULONGLONG, BT_BV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_ULONGLONG_UV2DI_INT, BT_ULONGLONG, BT_UV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_USHORT_BV8HI_INT, BT_USHORT, BT_BV8HI, BT_INT)
DEF_OV_TYPE (BT_OV_USHORT_UV8HI_INT, BT_USHORT, BT_UV8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_INT_V2DF_V2DF, BT_INT, BT_V2DF, BT_V2DF)
-DEF_OV_TYPE (BT_OV_INT_V16QI_BV16QI, BT_INT, BT_V16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_INT_UV2DI_UV2DI, BT_INT, BT_UV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_ULONG, BT_UV16QI, BT_UV16QI, BT_ULONG)
-DEF_OV_TYPE (BT_OV_BV16QI_BV8HI_BV8HI, BT_BV16QI, BT_BV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV2DI_UV2DI, BT_UV16QI, BT_UV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI)
DEF_OV_TYPE (BT_OV_UV16QI_BV16QI_BV16QI, BT_UV16QI, BT_BV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_V16QI_V16QI, BT_BV16QI, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_BV16QI, BT_UV16QI, BT_UV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR_UINT, BT_UV16QI, BT_UCHARCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_UV16QI_BV16QI_BV16QI_INTPTR, BT_UV16QI, BT_BV16QI, BT_BV16QI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_UV16QI_BV16QI_UV16QI, BT_UV16QI, BT_BV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR_USHORT, BT_UV16QI, BT_UCHARCONSTPTR, BT_USHORT)
DEF_OV_TYPE (BT_OV_UV16QI_LONG_UCHARPTR, BT_UV16QI, BT_LONG, BT_UCHARPTR)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHAR, BT_UV16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR, BT_UV16QI, BT_UCHARCONSTPTR)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR_UINT, BT_UV16QI, BT_UCHARCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHARCONSTPTR_USHORT, BT_UV16QI, BT_UCHARCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHAR_BV16QI_INT, BT_UV16QI, BT_UCHAR, BT_BV16QI, BT_INT)
DEF_OV_TYPE (BT_OV_UV16QI_UCHAR_INT, BT_UV16QI, BT_UCHAR, BT_INT)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV4SI, BT_BV16QI, BT_BV16QI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV8HI_UV8HI, BT_UV16QI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV8HI, BT_BV16QI, BT_BV16QI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UCHAR, BT_BV16QI, BT_BV16QI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_UV16QI, BT_BV16QI, BT_BV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI, BT_BV16QI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_INTPTR, BT_BV16QI, BT_BV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_V16QI, BT_UV16QI, BT_UV16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UCHAR_UV16QI_INT, BT_UV16QI, BT_UCHAR, BT_UV16QI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_BV16QI, BT_UV16QI, BT_UV16QI, BT_BV16QI)
DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_INTPTR, BT_UV16QI, BT_UV16QI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UCHAR, BT_UV16QI, BT_UV16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_ULONG, BT_UV16QI, BT_UV16QI, BT_ULONG)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_INT, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_INTPTR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UCHAR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_ULONGLONG, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UV16QI_INTPTR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV4SI, BT_UV16QI, BT_UV16QI, BT_UV4SI)
DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV8HI, BT_UV16QI, BT_UV16QI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV16QI_V8HI_V8HI, BT_UV16QI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_V16QI, BT_UV16QI, BT_UV16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV2DI_UV2DI, BT_UV16QI, BT_UV2DI, BT_UV2DI)
DEF_OV_TYPE (BT_OV_UV16QI_UV4SI_UV4SI, BT_UV16QI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV16QI, BT_UV2DI, BT_UV2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV4SI_UV4SI, BT_UV2DI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONGCONSTPTR_USHORT, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_UV16QI_UV8HI_UV8HI, BT_UV16QI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV16QI_UV8HI_UV8HI_INTPTR, BT_UV16QI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV16QI_V16QI, BT_UV16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_UV16QI_V8HI_V8HI, BT_UV16QI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_UV2DI_BV2DI_UV2DI, BT_UV2DI, BT_BV2DI, BT_UV2DI)
DEF_OV_TYPE (BT_OV_UV2DI_LONG_ULONGLONGPTR, BT_UV2DI, BT_LONG, BT_ULONGLONGPTR)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV8HI, BT_UV2DI, BT_UV2DI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_BV2DI, BT_UV2DI, BT_UV2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_ULONGLONG, BT_UV2DI, BT_ULONGLONG, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_V2DI, BT_UV2DI, BT_UV2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG, BT_UV2DI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONGCONSTPTR, BT_UV2DI, BT_ULONGLONGCONSTPTR)
DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONGCONSTPTR_UINT, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV4SI, BT_BV2DI, BT_BV2DI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_BV2DI_V2DI_V2DI, BT_BV2DI, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV16QI, BT_BV2DI, BT_BV2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV2DI_UV2DI_UV2DI, BT_BV2DI, BT_UV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONGCONSTPTR_USHORT, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_BV2DI_INT, BT_UV2DI, BT_ULONGLONG, BT_BV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_INT, BT_UV2DI, BT_ULONGLONG, BT_INT)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_ULONGLONG, BT_UV2DI, BT_ULONGLONG, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_UV2DI_INT, BT_UV2DI, BT_ULONGLONG, BT_UV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI, BT_UV2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_BV2DI, BT_UV2DI, BT_UV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UCHAR, BT_UV2DI, BT_UV2DI, BT_UCHAR)
DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_ULONG, BT_UV2DI, BT_UV2DI, BT_ULONG)
-DEF_OV_TYPE (BT_OV_BV2DI_V2DF_V2DF, BT_BV2DI, BT_V2DF, BT_V2DF)
-DEF_OV_TYPE (BT_OV_UV2DI_UV8HI_UV8HI, BT_UV2DI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV16QI, BT_UV2DI, BT_UV2DI, BT_UV16QI)
DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV8HI, BT_BV2DI, BT_BV2DI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UCHAR, BT_UV2DI, BT_UV2DI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_UV2DI_BV2DI_UV2DI, BT_UV2DI, BT_BV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UCHAR, BT_BV2DI, BT_BV2DI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_BV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_INT, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UCHAR, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_ULONGLONG, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_ULONGLONGCONSTPTR_UCHAR, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UV16QI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI)
DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV4SI, BT_UV2DI, BT_UV2DI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_INT, BT_UV2DI, BT_ULONGLONG, BT_INT)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV8HI, BT_UV4SI, BT_UV4SI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV4SI_V2DI_V2DI, BT_UV4SI, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV8HI, BT_BV4SI, BT_BV4SI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_V4SI, BT_UV4SI, BT_UV4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UCHAR, BT_UV4SI, BT_UV4SI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV8HI, BT_UV2DI, BT_UV2DI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_V2DI, BT_UV2DI, BT_UV2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV4SI, BT_UV2DI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV4SI_UV4SI, BT_UV2DI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV4SI_UV4SI_UV2DI, BT_UV2DI, BT_UV4SI, BT_UV4SI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_UV2DI_UV8HI_UV8HI, BT_UV2DI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV2DI_V2DI, BT_UV2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_BV4SI, BT_UV4SI, BT_BV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_BV4SI_INTPTR, BT_UV4SI, BT_BV4SI, BT_BV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_UV4SI, BT_UV4SI, BT_BV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_LONG_UINTPTR, BT_UV4SI, BT_LONG, BT_UINTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_UINT, BT_UV4SI, BT_UINT)
+DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR, BT_UV4SI, BT_UINTCONSTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR_UINT, BT_UV4SI, BT_UINTCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR_USHORT, BT_UV4SI, BT_UINTCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_UV4SI_UINT_BV4SI_INT, BT_UV4SI, BT_UINT, BT_BV4SI, BT_INT)
DEF_OV_TYPE (BT_OV_UV4SI_UINT_INT, BT_UV4SI, BT_UINT, BT_INT)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_INTPTR, BT_BV4SI, BT_BV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_ULONG, BT_UV4SI, BT_UV4SI, BT_ULONG)
-DEF_OV_TYPE (BT_OV_BV4SI_BV2DI_BV2DI, BT_BV4SI, BT_BV2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV4SI, BT_BV4SI, BT_BV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_BV4SI, BT_UV4SI, BT_UV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UINT_UV4SI_INT, BT_UV4SI, BT_UINT, BT_UV4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV4SI_UV16QI_UV16QI, BT_UV4SI, BT_UV16QI, BT_UV16QI)
DEF_OV_TYPE (BT_OV_UV4SI_UV2DI_UV2DI, BT_UV4SI, BT_UV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI, BT_BV4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV16QI, BT_UV4SI, BT_UV4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV2DI_UV2DI_INTPTR, BT_UV4SI, BT_UV2DI, BT_UV2DI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_BV4SI, BT_UV4SI, BT_UV4SI, BT_BV4SI)
DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_INTPTR, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR_USHORT, BT_UV4SI, BT_UINTCONSTPTR, BT_USHORT)
-DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_BV4SI, BT_UV4SI, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UCHAR, BT_BV4SI, BT_BV4SI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV16QI_UV16QI, BT_UV4SI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UCHAR, BT_UV4SI, BT_UV4SI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_ULONG, BT_UV4SI, BT_UV4SI, BT_ULONG)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV16QI, BT_UV4SI, BT_UV4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_INT, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_INTPTR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UCHAR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UINTCONSTPTR_UCHAR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UINTCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_ULONGLONG, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV16QI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV4SI_INTPTR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV8HI, BT_UV4SI, BT_UV4SI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_V4SI, BT_UV4SI, BT_UV4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV8HI, BT_UV4SI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_UV4SI_UV8HI_UV8HI, BT_UV4SI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV4SI_LONG_UINTPTR, BT_UV4SI, BT_LONG, BT_UINTPTR)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV16QI, BT_BV4SI, BT_BV4SI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV4SI_V4SI_V4SI, BT_BV4SI, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UINTCONSTPTR_UINT, BT_UV4SI, BT_UINTCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_UV4SI, BT_UV4SI, BT_BV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_V4SI_V4SI, BT_UV8HI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_UV8HI_UV8HI_UV4SI, BT_UV4SI, BT_UV8HI, BT_UV8HI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV4SI_V2DI_V2DI, BT_UV4SI, BT_V2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_UV4SI_V4SI, BT_UV4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_BV8HI, BT_UV8HI, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_BV8HI_INTPTR, BT_UV8HI, BT_BV8HI, BT_BV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_UV8HI, BT_UV8HI, BT_BV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_LONG_USHORTPTR, BT_UV8HI, BT_LONG, BT_USHORTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_USHORT, BT_UV8HI, BT_USHORT)
+DEF_OV_TYPE (BT_OV_UV8HI_USHORTCONSTPTR, BT_UV8HI, BT_USHORTCONSTPTR)
DEF_OV_TYPE (BT_OV_UV8HI_USHORTCONSTPTR_UINT, BT_UV8HI, BT_USHORTCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV4SI, BT_UV8HI, BT_UV8HI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_BV8HI_V8HI_V8HI, BT_BV8HI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_BV8HI_BV4SI_BV4SI, BT_BV8HI, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_V8HI, BT_UV8HI, BT_UV8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV4SI_UV4SI, BT_UV8HI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV8HI_USHORT_INT, BT_UV8HI, BT_USHORT, BT_INT)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV16QI, BT_BV8HI, BT_BV8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI, BT_BV8HI, BT_UV8HI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_UV8HI_USHORTCONSTPTR_USHORT, BT_UV8HI, BT_USHORTCONSTPTR, BT_USHORT)
-DEF_OV_TYPE (BT_OV_UV8HI_LONG_USHORTPTR, BT_UV8HI, BT_LONG, BT_USHORTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UCHAR, BT_UV8HI, BT_UV8HI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UCHAR, BT_BV8HI, BT_BV8HI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_INTPTR, BT_BV8HI, BT_BV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV8HI, BT_BV8HI, BT_BV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV16QI, BT_UV8HI, BT_UV8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_BV8HI, BT_UV8HI, BT_UV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_UV4SI, BT_BV8HI, BT_BV8HI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_BV8HI, BT_UV8HI, BT_BV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_USHORT_BV8HI_INT, BT_UV8HI, BT_USHORT, BT_BV8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV8HI_USHORT_INT, BT_UV8HI, BT_USHORT, BT_INT)
+DEF_OV_TYPE (BT_OV_UV8HI_USHORT_UV8HI_INT, BT_UV8HI, BT_USHORT, BT_UV8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV8HI_UV16QI, BT_UV8HI, BT_UV16QI)
DEF_OV_TYPE (BT_OV_UV8HI_UV16QI_UV16QI, BT_UV8HI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_UV8HI, BT_UV8HI, BT_BV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV16QI_UV16QI_UV8HI, BT_UV8HI, BT_UV16QI, BT_UV16QI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV4SI_UV4SI, BT_UV8HI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV4SI_UV4SI_INTPTR, BT_UV8HI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_BV8HI, BT_UV8HI, BT_UV8HI, BT_BV8HI)
DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_INTPTR, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UCHAR, BT_UV8HI, BT_UV8HI, BT_UCHAR)
DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_ULONG, BT_UV8HI, BT_UV8HI, BT_ULONG)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV16QI, BT_UV8HI, BT_UV8HI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV4SI, BT_UV8HI, BT_UV8HI, BT_UV4SI)
DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_INT, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_INTPTR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UCHAR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_ULONGLONG, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV16QI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV8HI_INTPTR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_V8HI, BT_UV8HI, BT_UV8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_UV8HI_V4SI_V4SI, BT_UV8HI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_UV8HI_V8HI, BT_UV8HI, BT_V8HI)
DEF_OV_TYPE (BT_OV_V16QI_BV16QI_V16QI, BT_V16QI, BT_BV16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UCHAR, BT_V16QI, BT_V16QI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_INTPTR, BT_V16QI, BT_V16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_BV16QI, BT_V16QI, BT_V16QI, BT_BV16QI)
DEF_OV_TYPE (BT_OV_V16QI_LONG_SCHARPTR, BT_V16QI, BT_LONG, BT_SCHARPTR)
+DEF_OV_TYPE (BT_OV_V16QI_SCHAR, BT_V16QI, BT_SCHAR)
+DEF_OV_TYPE (BT_OV_V16QI_SCHARCONSTPTR, BT_V16QI, BT_SCHARCONSTPTR)
DEF_OV_TYPE (BT_OV_V16QI_SCHARCONSTPTR_UINT, BT_V16QI, BT_SCHARCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV8HI, BT_V16QI, BT_V16QI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI, BT_V16QI, BT_V16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV4SI, BT_V16QI, BT_V16QI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_ULONG, BT_V16QI, BT_V16QI, BT_ULONG)
DEF_OV_TYPE (BT_OV_V16QI_SCHARCONSTPTR_USHORT, BT_V16QI, BT_SCHARCONSTPTR, BT_USHORT)
DEF_OV_TYPE (BT_OV_V16QI_SCHAR_INT, BT_V16QI, BT_SCHAR, BT_INT)
+DEF_OV_TYPE (BT_OV_V16QI_SCHAR_V16QI_INT, BT_V16QI, BT_SCHAR, BT_V16QI, BT_INT)
+DEF_OV_TYPE (BT_OV_V16QI_UV16QI_V16QI_V16QI, BT_V16QI, BT_UV16QI, BT_V16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI, BT_V16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_BV16QI, BT_V16QI, BT_V16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_INTPTR, BT_V16QI, BT_V16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UCHAR, BT_V16QI, BT_V16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_ULONG, BT_V16QI, BT_V16QI, BT_ULONG)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI, BT_V16QI, BT_V16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI_UCHAR, BT_V16QI, BT_V16QI, BT_UV16QI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI_UV16QI, BT_V16QI, BT_V16QI, BT_UV16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV4SI, BT_V16QI, BT_V16QI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV8HI, BT_V16QI, BT_V16QI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI, BT_V16QI, BT_V16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_BV16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_BV16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_INT, BT_V16QI, BT_V16QI, BT_V16QI, BT_INT)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_INTPTR, BT_V16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_ULONGLONG, BT_V16QI, BT_V16QI, BT_V16QI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_UV16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_V16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_V16QI)
DEF_OV_TYPE (BT_OV_V16QI_V8HI_V8HI, BT_V16QI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V2DF_UV2DI_INT, BT_V2DF, BT_UV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UCHAR, BT_V2DI, BT_V2DI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV16QI, BT_V2DI, BT_V2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V2DF_DBLCONSTPTR_USHORT, BT_V2DF, BT_DBLCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_V16QI_V8HI_V8HI_INTPTR, BT_V16QI, BT_V8HI, BT_V8HI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_V2DF_BV2DI_V2DF, BT_V2DF, BT_BV2DI, BT_V2DF)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_UCHAR, BT_V2DF, BT_V2DF, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_BV2DI, BT_V2DF, BT_V2DF, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV8HI, BT_V2DI, BT_V2DI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_V2DF_DBL, BT_V2DF, BT_DBL)
+DEF_OV_TYPE (BT_OV_V2DF_DBLCONSTPTR, BT_V2DF, BT_DBLCONSTPTR)
DEF_OV_TYPE (BT_OV_V2DF_DBLCONSTPTR_UINT, BT_V2DF, BT_DBLCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_V2DF_DBLCONSTPTR_USHORT, BT_V2DF, BT_DBLCONSTPTR, BT_USHORT)
DEF_OV_TYPE (BT_OV_V2DF_DBL_INT, BT_V2DF, BT_DBL, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DF_DBL_V2DF_INT, BT_V2DF, BT_DBL, BT_V2DF, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DF_LONG_DBLPTR, BT_V2DF, BT_LONG, BT_DBLPTR)
+DEF_OV_TYPE (BT_OV_V2DF_UV2DI_INT, BT_V2DF, BT_UV2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF, BT_V2DF, BT_V2DF)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_BV2DI, BT_V2DF, BT_V2DF, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_UCHAR, BT_V2DF, BT_V2DF, BT_UCHAR)
DEF_OV_TYPE (BT_OV_V2DF_V2DF_UV2DI, BT_V2DF, BT_V2DF, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV4SI, BT_V2DI, BT_V2DI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_UV2DI_DBLCONSTPTR_UCHAR, BT_V2DF, BT_V2DF, BT_UV2DI, BT_DBLCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF, BT_V2DF, BT_V2DF, BT_V2DF)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_BV2DI, BT_V2DF, BT_V2DF, BT_V2DF, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_INT, BT_V2DF, BT_V2DF, BT_V2DF, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_ULONGLONG, BT_V2DF, BT_V2DF, BT_V2DF, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_UV16QI, BT_V2DF, BT_V2DF, BT_V2DF, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_UV2DI, BT_V2DF, BT_V2DF, BT_V2DF, BT_UV2DI)
DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DI, BT_V2DF, BT_V2DF, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V2DI_BV2DI_V2DI, BT_V2DI, BT_BV2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V2DI_LONG_LONGLONGPTR, BT_V2DI, BT_LONG, BT_LONGLONGPTR)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI, BT_V2DI, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V2DI_V4SI_V4SI, BT_V2DI, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI, BT_V2DI, BT_V2DI, BT_UV2DI)
DEF_OV_TYPE (BT_OV_V2DF_V2DI_INT, BT_V2DF, BT_V2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_INT, BT_V2DI, BT_LONGLONG, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DI_BV2DI_V2DI, BT_V2DI, BT_BV2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONG, BT_V2DI, BT_LONGLONG)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONGCONSTPTR, BT_V2DI, BT_LONGLONGCONSTPTR)
DEF_OV_TYPE (BT_OV_V2DI_LONGLONGCONSTPTR_UINT, BT_V2DI, BT_LONGLONGCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONGCONSTPTR_USHORT, BT_V2DI, BT_LONGLONGCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_INT, BT_V2DI, BT_LONGLONG, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_LONGLONG, BT_V2DI, BT_LONGLONG, BT_LONGLONG)
+DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_V2DI_INT, BT_V2DI, BT_LONGLONG, BT_V2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DI_LONG_LONGLONGPTR, BT_V2DI, BT_LONG, BT_LONGLONGPTR)
+DEF_OV_TYPE (BT_OV_V2DI_V16QI, BT_V2DI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI, BT_V2DI, BT_V2DI)
DEF_OV_TYPE (BT_OV_V2DI_V2DI_BV2DI, BT_V2DI, BT_V2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_V2DF_LONG_DBLPTR, BT_V2DF, BT_LONG, BT_DBLPTR)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UCHAR, BT_V2DI, BT_V2DI, BT_UCHAR)
DEF_OV_TYPE (BT_OV_V2DI_V2DI_ULONG, BT_V2DI, BT_V2DI, BT_ULONG)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_LONGLONG, BT_V2DI, BT_LONGLONG, BT_LONGLONG)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONGCONSTPTR_USHORT, BT_V2DI, BT_LONGLONGCONSTPTR, BT_USHORT)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF, BT_V2DF, BT_V2DF, BT_V2DF)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV16QI, BT_V2DI, BT_V2DI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI, BT_V2DI, BT_V2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI_LONGLONGCONSTPTR_UCHAR, BT_V2DI, BT_V2DI, BT_UV2DI, BT_LONGLONGCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI_UCHAR, BT_V2DI, BT_V2DI, BT_UV2DI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV4SI, BT_V2DI, BT_V2DI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV8HI, BT_V2DI, BT_V2DI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI, BT_V2DI, BT_V2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_BV2DI, BT_V2DI, BT_V2DI, BT_V2DI, BT_BV2DI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_INT, BT_V2DI, BT_V2DI, BT_V2DI, BT_INT)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_ULONGLONG, BT_V2DI, BT_V2DI, BT_V2DI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_UV16QI, BT_V2DI, BT_V2DI, BT_V2DI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_UV2DI, BT_V2DI, BT_V2DI, BT_V2DI, BT_UV2DI)
+DEF_OV_TYPE (BT_OV_V2DI_V4SI, BT_V2DI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V2DI_V4SI_V4SI, BT_V2DI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V2DI_V4SI_V4SI_V2DI, BT_V2DI, BT_V4SI, BT_V4SI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_V2DI_V8HI, BT_V2DI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V4SI_BV4SI_V4SI, BT_V4SI, BT_BV4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V4SI_INT, BT_V4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_V4SI_INTCONSTPTR, BT_V4SI, BT_INTCONSTPTR)
+DEF_OV_TYPE (BT_OV_V4SI_INTCONSTPTR_UINT, BT_V4SI, BT_INTCONSTPTR, BT_UINT)
DEF_OV_TYPE (BT_OV_V4SI_INTCONSTPTR_USHORT, BT_V4SI, BT_INTCONSTPTR, BT_USHORT)
-DEF_OV_TYPE (BT_OV_V4SI_V8HI_V8HI, BT_V4SI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V4SI_INT_INT, BT_V4SI, BT_INT, BT_INT)
+DEF_OV_TYPE (BT_OV_V4SI_INT_V4SI_INT, BT_V4SI, BT_INT, BT_V4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_V4SI_LONG_INTPTR, BT_V4SI, BT_LONG, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V4SI_UV4SI_V4SI_V4SI, BT_V4SI, BT_UV4SI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V2DI_V2DI, BT_V4SI, BT_V2DI, BT_V2DI)
+DEF_OV_TYPE (BT_OV_V4SI_V2DI_V2DI_INTPTR, BT_V4SI, BT_V2DI, BT_V2DI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI, BT_V4SI, BT_V4SI)
DEF_OV_TYPE (BT_OV_V4SI_V4SI_BV4SI, BT_V4SI, BT_V4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_V4SI_INTCONSTPTR_UINT, BT_V4SI, BT_INTCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_V4SI_BV4SI_V4SI, BT_V4SI, BT_BV4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV8HI, BT_V4SI, BT_V4SI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_V4SI_V4SI_INTPTR, BT_V4SI, BT_V4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI, BT_V4SI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UCHAR, BT_V4SI, BT_V4SI, BT_UCHAR)
DEF_OV_TYPE (BT_OV_V4SI_V4SI_ULONG, BT_V4SI, BT_V4SI, BT_ULONG)
-DEF_OV_TYPE (BT_OV_V4SI_INT_INT, BT_V4SI, BT_INT, BT_INT)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI, BT_V4SI, BT_V4SI, BT_UV4SI)
DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV16QI, BT_V4SI, BT_V4SI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V4SI_LONG_INTPTR, BT_V4SI, BT_LONG, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UCHAR, BT_V4SI, BT_V4SI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V4SI_V2DI_V2DI, BT_V4SI, BT_V2DI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV8HI, BT_V8HI, BT_V8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_ULONG, BT_V8HI, BT_V8HI, BT_ULONG)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI, BT_V4SI, BT_V4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_INTCONSTPTR_UCHAR, BT_V4SI, BT_V4SI, BT_UV4SI, BT_INTCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_UCHAR, BT_V4SI, BT_V4SI, BT_UV4SI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_UV4SI, BT_V4SI, BT_V4SI, BT_UV4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV8HI, BT_V4SI, BT_V4SI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI, BT_V4SI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_BV4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_BV4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_INT, BT_V4SI, BT_V4SI, BT_V4SI, BT_INT)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_INTPTR, BT_V4SI, BT_V4SI, BT_V4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_ULONGLONG, BT_V4SI, BT_V4SI, BT_V4SI, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_UV16QI, BT_V4SI, BT_V4SI, BT_V4SI, BT_UV16QI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_UV4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_UV4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_V4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V4SI_V8HI, BT_V4SI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V4SI_V8HI_V8HI, BT_V4SI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V4SI_V8HI_V8HI_V4SI, BT_V4SI, BT_V8HI, BT_V8HI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V8HI_BV8HI_V8HI, BT_V8HI, BT_BV8HI, BT_V8HI)
DEF_OV_TYPE (BT_OV_V8HI_LONG_SHORTPTR, BT_V8HI, BT_LONG, BT_SHORTPTR)
+DEF_OV_TYPE (BT_OV_V8HI_SHORT, BT_V8HI, BT_SHORT)
+DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR, BT_V8HI, BT_SHORTCONSTPTR)
+DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR_UINT, BT_V8HI, BT_SHORTCONSTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR_USHORT, BT_V8HI, BT_SHORTCONSTPTR, BT_USHORT)
+DEF_OV_TYPE (BT_OV_V8HI_SHORT_INT, BT_V8HI, BT_SHORT, BT_INT)
+DEF_OV_TYPE (BT_OV_V8HI_SHORT_V8HI_INT, BT_V8HI, BT_SHORT, BT_V8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_V8HI_UV8HI_V8HI_V8HI, BT_V8HI, BT_UV8HI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V8HI_V16QI, BT_V8HI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V8HI_V16QI_V16QI, BT_V8HI, BT_V16QI, BT_V16QI)
+DEF_OV_TYPE (BT_OV_V8HI_V16QI_V16QI_V8HI, BT_V8HI, BT_V16QI, BT_V16QI, BT_V8HI)
DEF_OV_TYPE (BT_OV_V8HI_V4SI_V4SI, BT_V8HI, BT_V4SI, BT_V4SI)
+DEF_OV_TYPE (BT_OV_V8HI_V4SI_V4SI_INTPTR, BT_V8HI, BT_V4SI, BT_V4SI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_BV8HI, BT_V8HI, BT_V8HI, BT_BV8HI)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_INTPTR, BT_V8HI, BT_V8HI, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_UCHAR, BT_V8HI, BT_V8HI, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_ULONG, BT_V8HI, BT_V8HI, BT_ULONG)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV16QI, BT_V8HI, BT_V8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V8HI_BV8HI_V8HI, BT_V8HI, BT_BV8HI, BT_V8HI)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV4SI, BT_V8HI, BT_V8HI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_BV8HI, BT_V8HI, BT_V8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR_UINT, BT_V8HI, BT_SHORTCONSTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_V8HI_SHORT_INT, BT_V8HI, BT_SHORT, BT_INT)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_UCHAR, BT_V8HI, BT_V8HI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V8HI_SHORTCONSTPTR_USHORT, BT_V8HI, BT_SHORTCONSTPTR, BT_USHORT)
-DEF_OV_TYPE (BT_OV_V8HI_V16QI_V16QI, BT_V8HI, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_VOID_V2DF_DBLPTR_UINT, BT_VOID, BT_V2DF, BT_DBLPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_UV16QI_UCHARPTR_UINT, BT_VOID, BT_UV16QI, BT_UCHARPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_V4SI_INTPTR_UINT, BT_VOID, BT_V4SI, BT_INTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_UV4SI_LONG_UINTPTR, BT_VOID, BT_UV4SI, BT_LONG, BT_UINTPTR)
-DEF_OV_TYPE (BT_OV_VOID_V4SI_LONG_INTPTR, BT_VOID, BT_V4SI, BT_LONG, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_VOID_V2DI_LONG_LONGLONGPTR, BT_VOID, BT_V2DI, BT_LONG, BT_LONGLONGPTR)
-DEF_OV_TYPE (BT_OV_VOID_V8HI_SHORTPTR_UINT, BT_VOID, BT_V8HI, BT_SHORTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_V2DF_LONG_DBLPTR, BT_VOID, BT_V2DF, BT_LONG, BT_DBLPTR)
-DEF_OV_TYPE (BT_OV_VOID_UV8HI_USHORTPTR_UINT, BT_VOID, BT_UV8HI, BT_USHORTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_UV2DI_ULONGLONGPTR_UINT, BT_VOID, BT_UV2DI, BT_ULONGLONGPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_UV16QI_LONG_UCHARPTR, BT_VOID, BT_UV16QI, BT_LONG, BT_UCHARPTR)
-DEF_OV_TYPE (BT_OV_VOID_UV8HI_LONG_USHORTPTR, BT_VOID, BT_UV8HI, BT_LONG, BT_USHORTPTR)
-DEF_OV_TYPE (BT_OV_VOID_UV4SI_UINTPTR_UINT, BT_VOID, BT_UV4SI, BT_UINTPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_V16QI_SCHARPTR_UINT, BT_VOID, BT_V16QI, BT_SCHARPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_VOID_V16QI_LONG_SCHARPTR, BT_VOID, BT_V16QI, BT_LONG, BT_SCHARPTR)
-DEF_OV_TYPE (BT_OV_VOID_V8HI_LONG_SHORTPTR, BT_VOID, BT_V8HI, BT_LONG, BT_SHORTPTR)
-DEF_OV_TYPE (BT_OV_VOID_UV2DI_LONG_ULONGLONGPTR, BT_VOID, BT_UV2DI, BT_LONG, BT_ULONGLONGPTR)
-DEF_OV_TYPE (BT_OV_VOID_V2DI_LONGLONGPTR_UINT, BT_VOID, BT_V2DI, BT_LONGLONGPTR, BT_UINT)
-DEF_OV_TYPE (BT_OV_UV16QI_UV8HI_UV8HI_INTPTR, BT_UV16QI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UCHAR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_ULONGLONG, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_INT, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_UV16QI, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHAR_UV16QI_INT, BT_UV16QI, BT_UCHAR, BT_UV16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_UV16QI, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV16QI_BV16QI_BV16QI_INTPTR, BT_UV16QI, BT_BV16QI, BT_BV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_BV16QI_BV16QI_BV16QI_INTPTR, BT_BV16QI, BT_BV16QI, BT_BV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_INTPTR, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV16QI_V16QI_V16QI_INTPTR, BT_BV16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV16QI_UCHAR_BV16QI_INT, BT_UV16QI, BT_UCHAR, BT_BV16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_INTPTR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_ULONGLONG, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_UV2DI_INT, BT_UV2DI, BT_ULONGLONG, BT_UV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_INT, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_INT, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UCHAR, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV4SI_UV4SI_UV2DI, BT_UV2DI, BT_UV4SI, BT_UV4SI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_BV2DI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_UV16QI, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_UV2DI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_BV2DI_UV16QI, BT_BV2DI, BT_BV2DI, BT_BV2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV2DI_ULONGLONG_BV2DI_INT, BT_UV2DI, BT_ULONGLONG, BT_BV2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV8HI_UV8HI_UV4SI, BT_UV4SI, BT_UV8HI, BT_UV8HI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_BV4SI_V4SI_V4SI_INTPTR, BT_BV4SI, BT_V4SI, BT_V4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UCHAR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_INTPTR, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UINT_UV4SI_INT, BT_UV4SI, BT_UINT, BT_UV4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_INTPTR, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV2DI_UV2DI_INTPTR, BT_UV4SI, BT_UV2DI, BT_UV2DI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_BV4SI_BV4SI_INTPTR, BT_UV4SI, BT_BV4SI, BT_BV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV16QI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_UV4SI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_UV4SI, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UINT_BV4SI_INT, BT_UV4SI, BT_UINT, BT_BV4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_INT, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_INTPTR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_BV4SI_UV16QI, BT_BV4SI, BT_BV4SI, BT_BV4SI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_ULONGLONG, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_UV8HI, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_INTPTR, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_UV4SI_UV4SI_INTPTR, BT_UV8HI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_UV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_INTPTR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV16QI_UV16QI_UV8HI, BT_UV8HI, BT_UV16QI, BT_UV16QI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV16QI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_BV8HI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_ULONGLONG, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV8HI_USHORT_BV8HI_INT, BT_UV8HI, BT_USHORT, BT_BV8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV8HI_V8HI_V8HI_INTPTR, BT_BV8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_INT, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_BV8HI_BV8HI_BV8HI_UV16QI, BT_BV8HI, BT_BV8HI, BT_BV8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UCHAR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_INTPTR, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_BV8HI_BV8HI_INTPTR, BT_UV8HI, BT_BV8HI, BT_BV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_USHORT_UV8HI_INT, BT_UV8HI, BT_USHORT, BT_UV8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_V16QI_SCHAR_V16QI_INT, BT_V16QI, BT_SCHAR, BT_V16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_BV16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_BV16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_V16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_INTPTR, BT_V16QI, BT_V16QI, BT_V16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V16QI_UV16QI_V16QI_V16QI, BT_V16QI, BT_UV16QI, BT_V16QI, BT_V16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_ULONGLONG, BT_V16QI, BT_V16QI, BT_V16QI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_V16QI_V8HI_V8HI_INTPTR, BT_V16QI, BT_V8HI, BT_V8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI_UCHAR, BT_V16QI, BT_V16QI, BT_UV16QI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_UV16QI_UV16QI, BT_V16QI, BT_V16QI, BT_UV16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_INT, BT_V16QI, BT_V16QI, BT_V16QI, BT_INT)
-DEF_OV_TYPE (BT_OV_V16QI_V16QI_V16QI_UV16QI, BT_V16QI, BT_V16QI, BT_V16QI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI_UCHAR, BT_V2DI, BT_V2DI, BT_UV2DI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_INT, BT_V2DI, BT_V2DI, BT_V2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_ULONGLONG, BT_V2DF, BT_V2DF, BT_V2DF, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_UV16QI, BT_V2DI, BT_V2DI, BT_V2DI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_INT, BT_V2DF, BT_V2DF, BT_V2DF, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_UV2DI, BT_V2DI, BT_V2DI, BT_V2DI, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_UV16QI, BT_V2DF, BT_V2DF, BT_V2DF, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_ULONGLONG, BT_V2DI, BT_V2DI, BT_V2DI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_V2DF_DBL_V2DF_INT, BT_V2DF, BT_DBL, BT_V2DF, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DI_V4SI_V4SI_V2DI, BT_V2DI, BT_V4SI, BT_V4SI, BT_V2DI)
-DEF_OV_TYPE (BT_OV_V2DI_LONGLONG_V2DI_INT, BT_V2DI, BT_LONGLONG, BT_V2DI, BT_INT)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_V2DI_BV2DI, BT_V2DI, BT_V2DI, BT_V2DI, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_UV2DI, BT_V2DF, BT_V2DF, BT_V2DF, BT_UV2DI)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_V2DF_BV2DI, BT_V2DF, BT_V2DF, BT_V2DF, BT_BV2DI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_BV4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_BV4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_UV16QI, BT_V4SI, BT_V4SI, BT_V4SI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_INT, BT_V4SI, BT_V4SI, BT_V4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_UV4SI, BT_V4SI, BT_V4SI, BT_UV4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_ULONGLONG, BT_V4SI, BT_V4SI, BT_V4SI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_UCHAR, BT_V4SI, BT_V4SI, BT_UV4SI, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V4SI_V8HI_V8HI_V4SI, BT_V4SI, BT_V8HI, BT_V8HI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V4SI_UV4SI_V4SI_V4SI, BT_V4SI, BT_UV4SI, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_V4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_V4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V2DI_V2DI_INTPTR, BT_V4SI, BT_V2DI, BT_V2DI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_UV4SI, BT_V4SI, BT_V4SI, BT_V4SI, BT_UV4SI)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_V4SI_INTPTR, BT_V4SI, BT_V4SI, BT_V4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V4SI_INT_V4SI_INT, BT_V4SI, BT_INT, BT_V4SI, BT_INT)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_INT, BT_V8HI, BT_V8HI, BT_V8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV8HI, BT_V8HI, BT_V8HI, BT_UV8HI)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV8HI_UCHAR, BT_V8HI, BT_V8HI, BT_UV8HI, BT_UCHAR)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_UV8HI_UV8HI, BT_V8HI, BT_V8HI, BT_UV8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_UV8HI, BT_V8HI, BT_V8HI, BT_V8HI, BT_UV8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_INTPTR, BT_V8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V8HI_UV8HI_V8HI_V8HI, BT_V8HI, BT_UV8HI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V16QI_V16QI_V8HI, BT_V8HI, BT_V16QI, BT_V16QI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_BV8HI, BT_V8HI, BT_V8HI, BT_V8HI, BT_BV8HI)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_INT, BT_V8HI, BT_V8HI, BT_V8HI, BT_INT)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_INTPTR, BT_V8HI, BT_V8HI, BT_V8HI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_ULONGLONG, BT_V8HI, BT_V8HI, BT_V8HI, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_V8HI_SHORT_V8HI_INT, BT_V8HI, BT_SHORT, BT_V8HI, BT_INT)
-DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_V8HI, BT_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
-DEF_OV_TYPE (BT_OV_V8HI_V4SI_V4SI_INTPTR, BT_V8HI, BT_V4SI, BT_V4SI, BT_INTPTR)
DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_UV16QI, BT_V8HI, BT_V8HI, BT_V8HI, BT_UV16QI)
-DEF_OV_TYPE (BT_OV_VOID_V2DF_UV2DI_DBLPTR_ULONGLONG, BT_VOID, BT_V2DF, BT_UV2DI, BT_DBLPTR, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_VOID_V4SI_UV4SI_INTPTR_ULONGLONG, BT_VOID, BT_V4SI, BT_UV4SI, BT_INTPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_UV8HI, BT_V8HI, BT_V8HI, BT_V8HI, BT_UV8HI)
+DEF_OV_TYPE (BT_OV_V8HI_V8HI_V8HI_V8HI, BT_V8HI, BT_V8HI, BT_V8HI, BT_V8HI)
+DEF_OV_TYPE (BT_OV_VOID_BV2DI_UV2DI_ULONGLONGPTR_ULONGLONG, BT_VOID, BT_BV2DI, BT_UV2DI, BT_ULONGLONGPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_BV4SI_UV4SI_UINTPTR_ULONGLONG, BT_VOID, BT_BV4SI, BT_UV4SI, BT_UINTPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_UV16QI_LONG_UCHARPTR, BT_VOID, BT_UV16QI, BT_LONG, BT_UCHARPTR)
+DEF_OV_TYPE (BT_OV_VOID_UV16QI_UCHARPTR_UINT, BT_VOID, BT_UV16QI, BT_UCHARPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_UV2DI_LONG_ULONGLONGPTR, BT_VOID, BT_UV2DI, BT_LONG, BT_ULONGLONGPTR)
+DEF_OV_TYPE (BT_OV_VOID_UV2DI_ULONGLONGPTR_UINT, BT_VOID, BT_UV2DI, BT_ULONGLONGPTR, BT_UINT)
DEF_OV_TYPE (BT_OV_VOID_UV2DI_UV2DI_ULONGLONGPTR_ULONGLONG, BT_VOID, BT_UV2DI, BT_UV2DI, BT_ULONGLONGPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_UV4SI_LONG_UINTPTR, BT_VOID, BT_UV4SI, BT_LONG, BT_UINTPTR)
+DEF_OV_TYPE (BT_OV_VOID_UV4SI_UINTPTR_UINT, BT_VOID, BT_UV4SI, BT_UINTPTR, BT_UINT)
DEF_OV_TYPE (BT_OV_VOID_UV4SI_UV4SI_UINTPTR_ULONGLONG, BT_VOID, BT_UV4SI, BT_UV4SI, BT_UINTPTR, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_VOID_BV2DI_UV2DI_ULONGLONGPTR_ULONGLONG, BT_VOID, BT_BV2DI, BT_UV2DI, BT_ULONGLONGPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_UV8HI_LONG_USHORTPTR, BT_VOID, BT_UV8HI, BT_LONG, BT_USHORTPTR)
+DEF_OV_TYPE (BT_OV_VOID_UV8HI_USHORTPTR_UINT, BT_VOID, BT_UV8HI, BT_USHORTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_V16QI_LONG_SCHARPTR, BT_VOID, BT_V16QI, BT_LONG, BT_SCHARPTR)
+DEF_OV_TYPE (BT_OV_VOID_V16QI_SCHARPTR_UINT, BT_VOID, BT_V16QI, BT_SCHARPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_V2DF_DBLPTR_UINT, BT_VOID, BT_V2DF, BT_DBLPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_V2DF_LONG_DBLPTR, BT_VOID, BT_V2DF, BT_LONG, BT_DBLPTR)
+DEF_OV_TYPE (BT_OV_VOID_V2DF_UV2DI_DBLPTR_ULONGLONG, BT_VOID, BT_V2DF, BT_UV2DI, BT_DBLPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_V2DI_LONGLONGPTR_UINT, BT_VOID, BT_V2DI, BT_LONGLONGPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_V2DI_LONG_LONGLONGPTR, BT_VOID, BT_V2DI, BT_LONG, BT_LONGLONGPTR)
DEF_OV_TYPE (BT_OV_VOID_V2DI_UV2DI_LONGLONGPTR_ULONGLONG, BT_VOID, BT_V2DI, BT_UV2DI, BT_LONGLONGPTR, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_VOID_BV4SI_UV4SI_UINTPTR_ULONGLONG, BT_VOID, BT_BV4SI, BT_UV4SI, BT_UINTPTR, BT_ULONGLONG)
-DEF_OV_TYPE (BT_OV_UV16QI_UV16QI_UV16QI_UV16QI_INTPTR, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV16QI_UV16QI_UV16QI_UV16QI_INTPTR, BT_BV16QI, BT_UV16QI, BT_UV16QI, BT_UV16QI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_BV2DI_BV2DI_UV2DI_ULONGLONGCONSTPTR_UCHAR, BT_BV2DI, BT_BV2DI, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_UV2DI_UV2DI_UV2DI_ULONGLONGCONSTPTR_UCHAR, BT_UV2DI, BT_UV2DI, BT_UV2DI, BT_ULONGLONGCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV4SI_BV4SI_UV4SI_UINTCONSTPTR_UCHAR, BT_BV4SI, BT_BV4SI, BT_UV4SI, BT_UINTCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV4SI_UV4SI_UV4SI_UV4SI_INTPTR, BT_BV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UV4SI_INTPTR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV4SI_UV4SI_UV4SI_UINTCONSTPTR_UCHAR, BT_UV4SI, BT_UV4SI, BT_UV4SI, BT_UINTCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_BV8HI_UV8HI_UV8HI_UV8HI_INTPTR, BT_BV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_UV8HI_UV8HI_UV8HI_UV8HI_INTPTR, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_UV8HI, BT_INTPTR)
-DEF_OV_TYPE (BT_OV_V2DI_V2DI_UV2DI_LONGLONGCONSTPTR_UCHAR, BT_V2DI, BT_V2DI, BT_UV2DI, BT_LONGLONGCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V2DF_V2DF_UV2DI_DBLCONSTPTR_UCHAR, BT_V2DF, BT_V2DF, BT_UV2DI, BT_DBLCONSTPTR, BT_UCHAR)
-DEF_OV_TYPE (BT_OV_V4SI_V4SI_UV4SI_INTCONSTPTR_UCHAR, BT_V4SI, BT_V4SI, BT_UV4SI, BT_INTCONSTPTR, BT_UCHAR)
+DEF_OV_TYPE (BT_OV_VOID_V4SI_INTPTR_UINT, BT_VOID, BT_V4SI, BT_INTPTR, BT_UINT)
+DEF_OV_TYPE (BT_OV_VOID_V4SI_LONG_INTPTR, BT_VOID, BT_V4SI, BT_LONG, BT_INTPTR)
+DEF_OV_TYPE (BT_OV_VOID_V4SI_UV4SI_INTPTR_ULONGLONG, BT_VOID, BT_V4SI, BT_UV4SI, BT_INTPTR, BT_ULONGLONG)
+DEF_OV_TYPE (BT_OV_VOID_V8HI_LONG_SHORTPTR, BT_VOID, BT_V8HI, BT_LONG, BT_SHORTPTR)
+DEF_OV_TYPE (BT_OV_VOID_V8HI_SHORTPTR_UINT, BT_VOID, BT_V8HI, BT_SHORTPTR, BT_UINT)
diff --git a/gcc/config/s390/s390-builtins.def b/gcc/config/s390/s390-builtins.def
index b267b04e2a7..b0a86e97999 100644
--- a/gcc/config/s390/s390-builtins.def
+++ b/gcc/config/s390/s390-builtins.def
@@ -362,6 +362,15 @@ B_DEF (s390_vrepih, vec_splatsv8hi, 0,
B_DEF (s390_vrepif, vec_splatsv4si, 0, B_VX, O1_S16, BT_FN_V4SI_SHORT)
B_DEF (s390_vrepig, vec_splatsv2di, 0, B_VX, O1_S16, BT_FN_V2DI_SHORT)
+B_DEF (s390_vec_splat_u8, vec_splatsv16qi, 0, B_VX, O1_U8, BT_FN_UV16QI_UCHAR)
+B_DEF (s390_vec_splat_s8, vec_splatsv16qi, 0, B_VX, O1_S8, BT_FN_V16QI_SCHAR)
+B_DEF (s390_vec_splat_u16, vec_splatsv8hi, 0, B_VX, O1_U16, BT_FN_UV8HI_USHORT)
+B_DEF (s390_vec_splat_s16, vec_splatsv8hi, 0, B_VX, O1_S16, BT_FN_V8HI_SHORT)
+B_DEF (s390_vec_splat_u32, vec_splatsv4si, 0, B_VX, O1_U16, BT_FN_UV4SI_USHORT)
+B_DEF (s390_vec_splat_s32, vec_splatsv4si, 0, B_VX, O1_S16, BT_FN_V4SI_SHORT)
+B_DEF (s390_vec_splat_u64, vec_splatsv2di, 0, B_VX, O1_U16, BT_FN_UV2DI_USHORT)
+B_DEF (s390_vec_splat_s64, vec_splatsv2di, 0, B_VX, O1_S16, BT_FN_V2DI_SHORT)
+
OB_DEF (s390_vec_insert, s390_vec_insert_s8, s390_vec_insert_dbl,B_VX, BT_FN_OV4SI_INT_OV4SI_INT)
OB_DEF_VAR (s390_vec_insert_s8, s390_vlvgb, O3_ELEM, BT_OV_V16QI_SCHAR_V16QI_INT)
OB_DEF_VAR (s390_vec_insert_u8, s390_vlvgb, O3_ELEM, BT_OV_UV16QI_UCHAR_UV16QI_INT)
@@ -2461,15 +2470,15 @@ OB_DEF (s390_vec_ctd, s390_vec_ctd_s64, s390_vec_ctd_u64,
OB_DEF_VAR (s390_vec_ctd_s64, s390_vec_ctd_s64, O2_U5, BT_OV_V2DF_V2DI_INT) /* vcdgb */
OB_DEF_VAR (s390_vec_ctd_u64, s390_vec_ctd_u64, O2_U5, BT_OV_V2DF_UV2DI_INT) /* vcdlgb */
-B_DEF (s390_vec_ctd_s64, vec_ctd_s64, 0, B_VX, O2_U5, BT_FN_V2DF_V2DI_INT) /* vcdgb */
-B_DEF (s390_vec_ctd_u64, vec_ctd_u64, 0, B_VX, O2_U5, BT_FN_V2DF_UV2DI_INT) /* vcdlgb */
-B_DEF (s390_vcdgb, vec_di_to_df_s64, 0, B_VX, O2_U5, BT_FN_V2DF_V2DI_INT)
-B_DEF (s390_vcdlgb, vec_di_to_df_u64, 0, B_VX, O2_U5, BT_FN_V2DF_UV2DI_INT)
-B_DEF (s390_vec_ctsl, vec_ctsl, 0, B_VX, O2_U5, BT_FN_V2DI_V2DF_INT) /* vcgdb */
-B_DEF (s390_vec_ctul, vec_ctul, 0, B_VX, O2_U5, BT_FN_UV2DI_V2DF_INT) /* vclgdb */
-B_DEF (s390_vcgdb, vec_df_to_di_s64, 0, B_VX, O2_U5, BT_FN_V2DI_V2DF_INT)
-B_DEF (s390_vclgdb, vec_df_to_di_u64, 0, B_VX, O2_U5, BT_FN_UV2DI_V2DF_INT)
-B_DEF (s390_vfidb, vfidb, 0, B_VX, O2_U4 | O3_U4, BT_FN_V2DF_V2DF_UCHAR_UCHAR)
+B_DEF (s390_vec_ctd_s64, vec_ctd_s64, 0, B_VX, O2_U3, BT_FN_V2DF_V2DI_INT) /* vcdgb */
+B_DEF (s390_vec_ctd_u64, vec_ctd_u64, 0, B_VX, O2_U3, BT_FN_V2DF_UV2DI_INT) /* vcdlgb */
+B_DEF (s390_vcdgb, vec_di_to_df_s64, 0, B_VX, O2_U3, BT_FN_V2DF_V2DI_INT) /* vcdgb */
+B_DEF (s390_vcdlgb, vec_di_to_df_u64, 0, B_VX, O2_U3, BT_FN_V2DF_UV2DI_INT) /* vcdlgb */
+B_DEF (s390_vec_ctsl, vec_ctsl, 0, B_VX, O2_U3, BT_FN_V2DI_V2DF_INT) /* vcgdb */
+B_DEF (s390_vec_ctul, vec_ctul, 0, B_VX, O2_U3, BT_FN_UV2DI_V2DF_INT) /* vclgdb */
+B_DEF (s390_vcgdb, vec_df_to_di_s64, 0, B_VX, O2_U3, BT_FN_V2DI_V2DF_INT) /* vcgdb */
+B_DEF (s390_vclgdb, vec_df_to_di_u64, 0, B_VX, O2_U3, BT_FN_UV2DI_V2DF_INT) /* vclgdb */
+B_DEF (s390_vfidb, vfidb, 0, B_VX, O2_U4 | O3_U3, BT_FN_V2DF_V2DF_UCHAR_UCHAR)
B_DEF (s390_vec_ld2f, vec_ld2f, 0, B_VX, 0, BT_FN_V2DF_FLTCONSTPTR) /* vldeb */
B_DEF (s390_vec_st2f, vec_st2f, 0, B_VX, 0, BT_FN_VOID_V2DF_FLTPTR) /* vledb */
B_DEF (s390_vfmadb, fmav2df4, 0, B_VX, 0, BT_FN_V2DF_V2DF_V2DF_V2DF)
diff --git a/gcc/config/s390/s390-c.c b/gcc/config/s390/s390-c.c
index a94eda54c9f..fa69ed31fe5 100644
--- a/gcc/config/s390/s390-c.c
+++ b/gcc/config/s390/s390-c.c
@@ -414,22 +414,14 @@ s390_get_vstring_flags (int ob_fcode)
switch (ob_fcode)
{
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq_or_0_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne_or_0_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq_or_0_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne_or_0_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmprg_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmprg_or_0_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg_or_0_idx:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmprg_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmprg_or_0_idx_cc:
- case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg_or_0_idx_cc:
+ case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq:
+ case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne:
+ case S390_OVERLOADED_BUILTIN_s390_vec_find_any_eq_cc:
+ case S390_OVERLOADED_BUILTIN_s390_vec_find_any_ne_cc:
+ case S390_OVERLOADED_BUILTIN_s390_vec_cmprg:
+ case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg:
+ case S390_OVERLOADED_BUILTIN_s390_vec_cmprg_cc:
+ case S390_OVERLOADED_BUILTIN_s390_vec_cmpnrg_cc:
flags |= __VSTRING_FLAG_RT;
break;
default:
diff --git a/gcc/config/s390/s390.c b/gcc/config/s390/s390.c
index 5a7406c65ce..7e7ed45230a 100644
--- a/gcc/config/s390/s390.c
+++ b/gcc/config/s390/s390.c
@@ -74,6 +74,7 @@ along with GCC; see the file COPYING3. If not see
#include "builtins.h"
#include "rtl-iter.h"
#include "intl.h"
+#include "tm-constrs.h"
/* This file should be included last. */
#include "target-def.h"
@@ -834,6 +835,15 @@ s390_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
insn_op = &insn_data[icode].operand[arity + nonvoid];
op[arity] = expand_expr (arg, NULL_RTX, insn_op->mode, EXPAND_NORMAL);
+ /* expand_expr truncates constants to the target mode only if it
+ is "convenient". However, our checks below rely on this
+ being done. */
+ if (CONST_INT_P (op[arity])
+ && SCALAR_INT_MODE_P (insn_op->mode)
+ && GET_MODE (op[arity]) != insn_op->mode)
+ op[arity] = GEN_INT (trunc_int_for_mode (INTVAL (op[arity]),
+ insn_op->mode));
+
/* Wrap the expanded RTX for pointer types into a MEM expr with
the proper mode. This allows us to use e.g. (match_operand
"memory_operand"..) in the insn patterns instead of (mem
@@ -3643,9 +3653,11 @@ s390_legitimate_constant_p (machine_mode mode, rtx op)
if (GET_MODE_SIZE (mode) != 16)
return 0;
- if (!const0_operand (op, mode)
- && !s390_contiguous_bitmask_vector_p (op, NULL, NULL)
- && !s390_bytemask_vector_p (op, NULL))
+ if (!satisfies_constraint_j00 (op)
+ && !satisfies_constraint_jm1 (op)
+ && !satisfies_constraint_jKK (op)
+ && !satisfies_constraint_jxx (op)
+ && !satisfies_constraint_jyy (op))
return 0;
}
@@ -3826,14 +3838,12 @@ legitimate_reload_fp_constant_p (rtx op)
static bool
legitimate_reload_vector_constant_p (rtx op)
{
- /* FIXME: Support constant vectors with all the same 16 bit unsigned
- operands. These can be loaded with vrepi. */
-
if (TARGET_VX && GET_MODE_SIZE (GET_MODE (op)) == 16
- && (const0_operand (op, GET_MODE (op))
- || constm1_operand (op, GET_MODE (op))
- || s390_contiguous_bitmask_vector_p (op, NULL, NULL)
- || s390_bytemask_vector_p (op, NULL)))
+ && (satisfies_constraint_j00 (op)
+ || satisfies_constraint_jm1 (op)
+ || satisfies_constraint_jKK (op)
+ || satisfies_constraint_jxx (op)
+ || satisfies_constraint_jyy (op)))
return true;
return false;
@@ -7132,6 +7142,11 @@ print_operand (FILE *file, rtx x, int code)
case CONST_VECTOR:
switch (code)
{
+ case 'h':
+ gcc_assert (const_vec_duplicate_p (x));
+ fprintf (file, HOST_WIDE_INT_PRINT_DEC,
+ ((INTVAL (XVECEXP (x, 0, 0)) & 0xffff) ^ 0x8000) - 0x8000);
+ break;
case 'e':
case 's':
{
diff --git a/gcc/config/s390/s390.md b/gcc/config/s390/s390.md
index a5335ca510a..e5db537907c 100644
--- a/gcc/config/s390/s390.md
+++ b/gcc/config/s390/s390.md
@@ -10451,25 +10451,43 @@
; FIXME: There is also mvcin but we cannot use it since src and target
; may overlap.
(define_insn "bswap<mode>2"
- [(set (match_operand:GPR 0 "register_operand" "=d, d")
- (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,RT")))]
+ [(set (match_operand:GPR 0 "nonimmediate_operand" "=d, d,RT")
+ (bswap:GPR (match_operand:GPR 1 "nonimmediate_operand" " d,RT, d")))]
"TARGET_CPU_ZARCH"
"@
lrv<g>r\t%0,%1
- lrv<g>\t%0,%1"
- [(set_attr "type" "*,load")
- (set_attr "op_type" "RRE,RXY")
+ lrv<g>\t%0,%1
+ strv<g>\t%1,%0"
+ [(set_attr "type" "*,load,store")
+ (set_attr "op_type" "RRE,RXY,RXY")
(set_attr "z10prop" "z10_super")])
(define_insn "bswaphi2"
- [(set (match_operand:HI 0 "register_operand" "=d")
- (bswap:HI (match_operand:HI 1 "memory_operand" "RT")))]
+ [(set (match_operand:HI 0 "nonimmediate_operand" "=d, d,RT")
+ (bswap:HI (match_operand:HI 1 "nonimmediate_operand" " d,RT, d")))]
"TARGET_CPU_ZARCH"
- "lrvh\t%0,%1"
- [(set_attr "type" "load")
- (set_attr "op_type" "RXY")
+ "@
+ #
+ lrvh\t%0,%1
+ strvh\t%1,%0"
+ [(set_attr "type" "*,load,store")
+ (set_attr "op_type" "RRE,RXY,RXY")
(set_attr "z10prop" "z10_super")])
+(define_split
+ [(set (match_operand:HI 0 "register_operand" "")
+ (bswap:HI (match_operand:HI 1 "register_operand" "")))]
+ "TARGET_CPU_ZARCH"
+ [(set (match_dup 2) (bswap:SI (match_dup 3)))
+ (set (match_dup 2) (lshiftrt:SI (match_dup 2)
+ (const_int 16)))
+ (set (match_dup 0) (subreg:HI (match_dup 2) 2))]
+{
+ operands[2] = gen_reg_rtx (SImode);
+ operands[3] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
+})
+
+
;
; Population count instruction
;
diff --git a/gcc/config/s390/vecintrin.h b/gcc/config/s390/vecintrin.h
index 2e26e3a0653..c24dcb42eb4 100644
--- a/gcc/config/s390/vecintrin.h
+++ b/gcc/config/s390/vecintrin.h
@@ -67,14 +67,14 @@ __lcbb(const void *ptr, int bndry)
#define vec_genmasks_16 __builtin_s390_vgmh
#define vec_genmasks_32 __builtin_s390_vgmf
#define vec_genmasks_64 __builtin_s390_vgmg
-#define vec_splat_u8 __builtin_s390_vlrepb
-#define vec_splat_s8 __builtin_s390_vlrepb
-#define vec_splat_u16 __builtin_s390_vlreph
-#define vec_splat_s16 __builtin_s390_vlreph
-#define vec_splat_u32 __builtin_s390_vlrepf
-#define vec_splat_s32 __builtin_s390_vlrepf
-#define vec_splat_u64 __builtin_s390_vlrepg
-#define vec_splat_s64 __builtin_s390_vlrepg
+#define vec_splat_u8 __builtin_s390_vec_splat_u8
+#define vec_splat_s8 __builtin_s390_vec_splat_s8
+#define vec_splat_u16 __builtin_s390_vec_splat_u16
+#define vec_splat_s16 __builtin_s390_vec_splat_s16
+#define vec_splat_u32 __builtin_s390_vec_splat_u32
+#define vec_splat_s32 __builtin_s390_vec_splat_s32
+#define vec_splat_u64 __builtin_s390_vec_splat_u64
+#define vec_splat_s64 __builtin_s390_vec_splat_s64
#define vec_add_u128 __builtin_s390_vaq
#define vec_addc_u128 __builtin_s390_vaccq
#define vec_adde_u128 __builtin_s390_vacq
diff --git a/gcc/config/s390/vector.md b/gcc/config/s390/vector.md
index 16276e0de36..c9f589017dc 100644
--- a/gcc/config/s390/vector.md
+++ b/gcc/config/s390/vector.md
@@ -137,8 +137,8 @@
; Full HW vector size moves
(define_insn "mov<mode>"
- [(set (match_operand:V_128 0 "nonimmediate_operand" "=v, v,QR, v, v, v, v,v,d")
- (match_operand:V_128 1 "general_operand" " v,QR, v,j00,jm1,jyy,jxx,d,v"))]
+ [(set (match_operand:V_128 0 "nonimmediate_operand" "=v, v,QR, v, v, v, v, v,v,d")
+ (match_operand:V_128 1 "general_operand" " v,QR, v,j00,jm1,jyy,jxx,jKK,d,v"))]
"TARGET_VX"
"@
vlr\t%v0,%v1
@@ -148,9 +148,10 @@
vone\t%v0
vgbm\t%v0,%t1
vgm<bhfgq>\t%v0,%s1,%e1
+ vrepi<bhfgq>\t%v0,%h1
vlvgp\t%v0,%1,%N1
#"
- [(set_attr "op_type" "VRR,VRX,VRX,VRI,VRI,VRI,VRI,VRR,*")])
+ [(set_attr "op_type" "VRR,VRX,VRX,VRI,VRI,VRI,VRI,VRI,VRR,*")])
(define_split
[(set (match_operand:V_128 0 "register_operand" "")
@@ -313,7 +314,7 @@
(define_insn "*vec_set<mode>"
[(set (match_operand:V 0 "register_operand" "=v, v,v")
(unspec:V [(match_operand:<non_vec> 1 "general_operand" "d,QR,K")
- (match_operand:DI 2 "shift_count_or_setmem_operand" "Y, I,I")
+ (match_operand:SI 2 "shift_count_or_setmem_operand" "Y, I,I")
(match_operand:V 3 "register_operand" "0, 0,0")]
UNSPEC_VEC_SET))]
"TARGET_VX"
@@ -363,18 +364,18 @@
(vec_select:<non_vec>
(match_operand:V_HW 1 "register_operand" "v")
(parallel
- [(match_operand:QI 2 "immediate_operand" "C")]))))]
- "TARGET_VX"
+ [(match_operand:QI 2 "const_mask_operand" "C")]))))]
+ "TARGET_VX && UINTVAL (operands[2]) < GET_MODE_NUNITS (<V_HW:MODE>mode)"
"vrep<bhfgq>\t%v0,%v1,%2"
[(set_attr "op_type" "VRI")])
(define_insn "*vec_splats<mode>"
[(set (match_operand:V_HW 0 "register_operand" "=v,v,v,v")
- (vec_duplicate:V_HW (match_operand:<non_vec> 1 "general_operand" "QR,I,v,d")))]
+ (vec_duplicate:V_HW (match_operand:<non_vec> 1 "general_operand" "QR,K,v,d")))]
"TARGET_VX"
"@
vlrep<bhfgq>\t%v0,%1
- vrepi<bhfgq>\t%v0,%1
+ vrepi<bhfgq>\t%v0,%h1
vrep<bhfgq>\t%v0,%v1,0
#"
[(set_attr "op_type" "VRX,VRI,VRI,*")])
@@ -1072,7 +1073,7 @@
[(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
(unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
(match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:QI 3 "immediate_operand" "C")]
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_VFENE))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
diff --git a/gcc/config/s390/vx-builtins.md b/gcc/config/s390/vx-builtins.md
index ff7408a919f..b772439af54 100644
--- a/gcc/config/s390/vx-builtins.md
+++ b/gcc/config/s390/vx-builtins.md
@@ -67,20 +67,20 @@
; Vector gather element
(define_insn "vec_gather_element<mode>"
- [(set (match_operand:V_HW_32_64 0 "register_operand" "=v")
- (unspec:V_HW_32_64 [(match_operand:V_HW_32_64 1 "register_operand" "0")
- (match_operand:<tointvec> 2 "register_operand" "v")
- (match_operand:BLK 3 "memory_operand" "QR")
- (match_operand:QI 4 "immediate_operand" "C")]
+ [(set (match_operand:V_HW_32_64 0 "register_operand" "=v")
+ (unspec:V_HW_32_64 [(match_operand:V_HW_32_64 1 "register_operand" "0")
+ (match_operand:<tointvec> 2 "register_operand" "v")
+ (match_operand:BLK 3 "memory_operand" "QR")
+ (match_operand:QI 4 "const_mask_operand" "C")]
UNSPEC_VEC_GATHER))]
- "TARGET_VX"
+ "TARGET_VX && UINTVAL (operands[4]) < GET_MODE_NUNITS (<V_HW_32_64:MODE>mode)"
"vge<bhfgq>\t%0,%O3(%v2,%R3),%b4"
[(set_attr "op_type" "VRV")])
(define_expand "vec_genmask<mode>"
[(match_operand:VI_HW 0 "register_operand" "=v")
- (match_operand:QI 1 "immediate_operand" "C")
- (match_operand:QI 2 "immediate_operand" "C")]
+ (match_operand:QI 1 "const_int_operand" "C")
+ (match_operand:QI 2 "const_int_operand" "C")]
"TARGET_VX"
{
int nunits = GET_MODE_NUNITS (<VI_HW:MODE>mode);
@@ -120,8 +120,8 @@
(define_expand "vec_genbytemaskv16qi"
[(match_operand:V16QI 0 "register_operand" "")
- (match_operand 1 "immediate_operand" "")]
- "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[1]), 'K', \"K\")"
+ (match_operand:HI 1 "const_int_operand" "")]
+ "TARGET_VX"
{
int i;
unsigned mask = 0x8000;
@@ -177,11 +177,11 @@
[(set_attr "op_type" "VRX")])
(define_insn "vlbb"
- [(set (match_operand:V16QI 0 "register_operand" "=v")
- (unspec:V16QI [(match_operand:BLK 1 "memory_operand" "QR")
- (match_operand:HI 2 "immediate_operand" " K")]
+ [(set (match_operand:V16QI 0 "register_operand" "=v")
+ (unspec:V16QI [(match_operand:BLK 1 "memory_operand" "QR")
+ (match_operand:QI 2 "const_mask_operand" "C")]
UNSPEC_VEC_LOAD_BNDRY))]
- "TARGET_VX"
+ "TARGET_VX && UINTVAL (operands[2]) < 7"
"vlbb\t%v0,%1,%2"
[(set_attr "op_type" "VRX")])
@@ -351,10 +351,10 @@
[(set_attr "op_type" "VRR")])
(define_expand "vec_permi<mode>"
- [(set (match_operand:V_HW_64 0 "register_operand" "")
- (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "")
- (match_operand:V_HW_64 2 "register_operand" "")
- (match_operand:QI 3 "immediate_operand" "")]
+ [(set (match_operand:V_HW_64 0 "register_operand" "")
+ (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "")
+ (match_operand:V_HW_64 2 "register_operand" "")
+ (match_operand:QI 3 "const_mask_operand" "")]
UNSPEC_VEC_PERMI))]
"TARGET_VX"
{
@@ -363,12 +363,12 @@
})
(define_insn "*vec_permi<mode>"
- [(set (match_operand:V_HW_64 0 "register_operand" "=v")
- (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "v")
- (match_operand:V_HW_64 2 "register_operand" "v")
- (match_operand:QI 3 "immediate_operand" "C")]
+ [(set (match_operand:V_HW_64 0 "register_operand" "=v")
+ (unspec:V_HW_64 [(match_operand:V_HW_64 1 "register_operand" "v")
+ (match_operand:V_HW_64 2 "register_operand" "v")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_PERMI))]
- "TARGET_VX"
+ "TARGET_VX && (UINTVAL (operands[3]) & 10) == 0"
"vpdi\t%v0,%v1,%v2,%b3"
[(set_attr "op_type" "VRR")])
@@ -382,7 +382,7 @@
(vec_duplicate:V_HW (vec_select:<non_vec>
(match_operand:V_HW 1 "register_operand" "")
(parallel
- [(match_operand:QI 2 "immediate_operand" "")]))))]
+ [(match_operand:QI 2 "const_mask_operand" "")]))))]
"TARGET_VX")
; Vector scatter element
@@ -393,13 +393,13 @@
(define_insn "vec_scatter_elementv4si_DI"
[(set (mem:SI
(plus:DI (zero_extend:DI
- (unspec:SI [(match_operand:V4SI 1 "register_operand" "v")
- (match_operand:DI 3 "immediate_operand" "I")]
+ (unspec:SI [(match_operand:V4SI 1 "register_operand" "v")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_EXTRACT))
- (match_operand:SI 2 "address_operand" "ZQ")))
- (unspec:SI [(match_operand:V4SI 0 "register_operand" "v")
+ (match_operand:SI 2 "address_operand" "ZQ")))
+ (unspec:SI [(match_operand:V4SI 0 "register_operand" "v")
(match_dup 3)] UNSPEC_VEC_EXTRACT))]
- "TARGET_VX && TARGET_64BIT"
+ "TARGET_VX && TARGET_64BIT && UINTVAL (operands[3]) < 4"
"vscef\t%v0,%O2(%v1,%R2),%3"
[(set_attr "op_type" "VRV")])
@@ -407,13 +407,13 @@
(define_insn "vec_scatter_element<V_HW_64:mode>_SI"
[(set (mem:<non_vec>
(plus:SI (subreg:SI
- (unspec:<non_vec_int> [(match_operand:V_HW_64 1 "register_operand" "v")
- (match_operand:DI 3 "immediate_operand" "I")]
+ (unspec:<non_vec_int> [(match_operand:V_HW_64 1 "register_operand" "v")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_EXTRACT) 4)
- (match_operand:SI 2 "address_operand" "ZQ")))
- (unspec:<non_vec> [(match_operand:V_HW_64 0 "register_operand" "v")
+ (match_operand:SI 2 "address_operand" "ZQ")))
+ (unspec:<non_vec> [(match_operand:V_HW_64 0 "register_operand" "v")
(match_dup 3)] UNSPEC_VEC_EXTRACT))]
- "TARGET_VX && !TARGET_64BIT"
+ "TARGET_VX && !TARGET_64BIT && UINTVAL (operands[3]) < GET_MODE_NUNITS (<V_HW_64:MODE>mode)"
"vsce<V_HW_64:bhfgq>\t%v0,%O2(%v1,%R2),%3"
[(set_attr "op_type" "VRV")])
@@ -421,13 +421,13 @@
(define_insn "vec_scatter_element<mode>_<non_vec_int>"
[(set (mem:<non_vec>
(plus:<non_vec_int> (unspec:<non_vec_int>
- [(match_operand:<tointvec> 1 "register_operand" "v")
- (match_operand:DI 3 "immediate_operand" "I")]
+ [(match_operand:<tointvec> 1 "register_operand" "v")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_EXTRACT)
- (match_operand:DI 2 "address_operand" "ZQ")))
- (unspec:<non_vec> [(match_operand:V_HW_32_64 0 "register_operand" "v")
+ (match_operand:DI 2 "address_operand" "ZQ")))
+ (unspec:<non_vec> [(match_operand:V_HW_32_64 0 "register_operand" "v")
(match_dup 3)] UNSPEC_VEC_EXTRACT))]
- "TARGET_VX"
+ "TARGET_VX && UINTVAL (operands[3]) < GET_MODE_NUNITS (<V_HW_32_64:MODE>mode)"
"vsce<bhfgq>\t%v0,%O2(%v1,%R2),%3"
[(set_attr "op_type" "VRV")])
@@ -438,7 +438,7 @@
[(match_operand:V_HW_32_64 0 "register_operand" "")
(match_operand:<tointvec> 1 "register_operand" "")
(match_operand 2 "address_operand" "")
- (match_operand:DI 3 "immediate_operand" "")]
+ (match_operand:QI 3 "const_mask_operand" "")]
"TARGET_VX"
{
if (TARGET_64BIT)
@@ -1042,7 +1042,7 @@
(unspec:VI_HW [(match_operand:VI_HW 1 "register_operand" "0")
(match_operand:VI_HW 2 "register_operand" "v")
(match_operand:VI_HW 3 "register_operand" "v")
- (match_operand:SI 4 "immediate_operand" "I")]
+ (match_operand:QI 4 "const_int_operand" "C")]
UNSPEC_VEC_RL_MASK))]
"TARGET_VX"
"verim<bhfgq>\t%v0,%v2,%v3,%b4"
@@ -1079,7 +1079,7 @@
[(set (match_operand:V_HW 0 "register_operand" "=v")
(unspec:V_HW [(match_operand:V_HW 1 "register_operand" "v")
(match_operand:V_HW 2 "register_operand" "v")
- (match_operand:DI 3 "immediate_operand" "C")]
+ (match_operand:QI 3 "const_int_operand" "C")]
UNSPEC_VEC_SLDB))]
"TARGET_VX"
"vsldb\t%v0,%v1,%v2,%b3"
@@ -1089,7 +1089,7 @@
[(set (match_operand:V_HW 0 "register_operand" "")
(unspec:V_HW [(match_operand:V_HW 1 "register_operand" "")
(match_operand:V_HW 2 "register_operand" "")
- (match_operand:DI 3 "immediate_operand" "")]
+ (match_operand:QI 3 "const_int_operand" "")]
UNSPEC_VEC_SLDB))]
"TARGET_VX"
{
@@ -1262,7 +1262,7 @@
[(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
(unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
(match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:SI 3 "immediate_operand" "C")]
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_VFAE))]
"TARGET_VX"
{
@@ -1282,9 +1282,9 @@
; vfaezbs, vfaezhs, vfaezfs
(define_insn "*vfaes<mode>"
[(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
- (match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:SI 3 "immediate_operand" "C")]
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
+ (match_operand:VI_HW_QHS 2 "register_operand" "v")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_VFAE))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1307,9 +1307,9 @@
(define_expand "vfaez<mode>"
[(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
- (match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:SI 3 "immediate_operand" "C")]
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
+ (match_operand:VI_HW_QHS 2 "register_operand" "")
+ (match_operand:QI 3 "const_mask_operand" "")]
UNSPEC_VEC_VFAE))]
"TARGET_VX"
{
@@ -1319,9 +1319,9 @@
(define_expand "vfaes<mode>"
[(parallel
[(set (match_operand:VI_HW_QHS 0 "register_operand" "")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
- (match_operand:VI_HW_QHS 2 "register_operand" "")
- (match_operand:SI 3 "immediate_operand" "C")]
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
+ (match_operand:VI_HW_QHS 2 "register_operand" "")
+ (match_operand:QI 3 "const_mask_operand" "")]
UNSPEC_VEC_VFAE))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1338,9 +1338,9 @@
(define_expand "vfaezs<mode>"
[(parallel
[(set (match_operand:VI_HW_QHS 0 "register_operand" "")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
- (match_operand:VI_HW_QHS 2 "register_operand" "")
- (match_operand:SI 3 "immediate_operand" "C")]
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
+ (match_operand:VI_HW_QHS 2 "register_operand" "")
+ (match_operand:SI 3 "const_mask_operand" "")]
UNSPEC_VEC_VFAE))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1363,7 +1363,7 @@
[(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
(unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
(match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:QI 3 "immediate_operand" "C")]
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_VFEE))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1541,11 +1541,11 @@
; vstrcb, vstrch, vstrcf
; vstrczb, vstrczh, vstrczf
(define_insn "vstrc<mode>"
- [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
- (match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:VI_HW_QHS 3 "register_operand" "v")
- (match_operand:SI 4 "immediate_operand" "C")]
+ [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
+ (match_operand:VI_HW_QHS 2 "register_operand" "v")
+ (match_operand:VI_HW_QHS 3 "register_operand" "v")
+ (match_operand:QI 4 "const_mask_operand" "C")]
UNSPEC_VEC_VSTRC))]
"TARGET_VX"
{
@@ -1564,11 +1564,11 @@
; vstrcbs, vstrchs, vstrcfs
; vstrczbs, vstrczhs, vstrczfs
(define_insn "*vstrcs<mode>"
- [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
- (match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:VI_HW_QHS 3 "register_operand" "v")
- (match_operand:SI 4 "immediate_operand" "C")]
+ [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
+ (match_operand:VI_HW_QHS 2 "register_operand" "v")
+ (match_operand:VI_HW_QHS 3 "register_operand" "v")
+ (match_operand:QI 4 "const_mask_operand" "C")]
UNSPEC_VEC_VSTRC))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1591,11 +1591,11 @@
[(set_attr "op_type" "VRR")])
(define_expand "vstrcz<mode>"
- [(set (match_operand:VI_HW_QHS 0 "register_operand" "=v")
- (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "v")
- (match_operand:VI_HW_QHS 2 "register_operand" "v")
- (match_operand:VI_HW_QHS 3 "register_operand" "v")
- (match_operand:SI 4 "immediate_operand" "C")]
+ [(set (match_operand:VI_HW_QHS 0 "register_operand" "")
+ (unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
+ (match_operand:VI_HW_QHS 2 "register_operand" "")
+ (match_operand:VI_HW_QHS 3 "register_operand" "")
+ (match_operand:QI 4 "const_mask_operand" "")]
UNSPEC_VEC_VSTRC))]
"TARGET_VX"
{
@@ -1608,7 +1608,7 @@
(unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
(match_operand:VI_HW_QHS 2 "register_operand" "")
(match_operand:VI_HW_QHS 3 "register_operand" "")
- (match_operand:SI 4 "immediate_operand" "C")]
+ (match_operand:QI 4 "const_mask_operand" "")]
UNSPEC_VEC_VSTRC))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1629,7 +1629,7 @@
(unspec:VI_HW_QHS [(match_operand:VI_HW_QHS 1 "register_operand" "")
(match_operand:VI_HW_QHS 2 "register_operand" "")
(match_operand:VI_HW_QHS 3 "register_operand" "")
- (match_operand:SI 4 "immediate_operand" "C")]
+ (match_operand:QI 4 "const_mask_operand" "")]
UNSPEC_VEC_VSTRC))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1)
@@ -1647,11 +1647,11 @@
; Signed V2DI -> V2DF conversion - inexact exception disabled
(define_insn "vec_di_to_df_s64"
- [(set (match_operand:V2DF 0 "register_operand" "=v")
- (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "v")
- (match_operand:QI 2 "immediate_operand" "C")]
+ [(set (match_operand:V2DF 0 "register_operand" "=v")
+ (unspec:V2DF [(match_operand:V2DI 1 "register_operand" "v")
+ (match_operand:QI 2 "const_mask_operand" "C")]
UNSPEC_VEC_VCDGB))]
- "TARGET_VX"
+ "TARGET_VX && UINTVAL (operands[2]) != 2 && UINTVAL (operands[2]) <= 7"
"vcdgb\t%v0,%v1,4,%b2"
[(set_attr "op_type" "VRR")])
@@ -1661,7 +1661,7 @@
(unspec:V2DF [(match_operand:V2DI 1 "register_operand" "")
(const_int 0)] ; According to current BFP rounding mode
UNSPEC_VEC_VCDGB))
- (use (match_operand:QI 2 "immediate_operand" ""))
+ (use (match_operand:QI 2 "const_int_operand" ""))
(set (match_dup 0) (mult:V2DF (match_dup 0) (match_dup 3)))]
"TARGET_VX"
{
@@ -1679,7 +1679,7 @@
(define_insn "vec_di_to_df_u64"
[(set (match_operand:V2DF 0 "register_operand" "=v")
(unspec:V2DF [(match_operand:V2DI 1 "register_operand" "v")
- (match_operand:QI 2 "immediate_operand" "C")]
+ (match_operand:QI 2 "const_int_operand" "C")]
UNSPEC_VEC_VCDLGB))]
"TARGET_VX"
"vcdlgb\t%v0,%v1,4,%b2"
@@ -1691,7 +1691,7 @@
(unspec:V2DF [(match_operand:V2DI 1 "register_operand" "")
(const_int 0)] ; According to current BFP rounding mode
UNSPEC_VEC_VCDLGB))
- (use (match_operand:QI 2 "immediate_operand" ""))
+ (use (match_operand:QI 2 "const_int_operand" ""))
(set (match_dup 0) (mult:V2DF (match_dup 0) (match_dup 3)))]
"TARGET_VX"
{
@@ -1710,7 +1710,7 @@
(define_insn "vec_df_to_di_s64"
[(set (match_operand:V2DI 0 "register_operand" "=v")
(unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v")
- (match_operand:QI 2 "immediate_operand" "C")]
+ (match_operand:QI 2 "const_int_operand" "C")]
UNSPEC_VEC_VCGDB))]
"TARGET_VX"
"vcgdb\t%v0,%v1,4,%b2"
@@ -1718,7 +1718,7 @@
; The input needs to be multiplied with 2**op2
(define_expand "vec_ctsl"
- [(use (match_operand:QI 2 "immediate_operand" ""))
+ [(use (match_operand:QI 2 "const_int_operand" ""))
(set (match_dup 4) (mult:V2DF (match_operand:V2DF 1 "register_operand" "")
(match_dup 3)))
(set (match_operand:V2DI 0 "register_operand" "")
@@ -1741,15 +1741,15 @@
(define_insn "vec_df_to_di_u64"
[(set (match_operand:V2DI 0 "register_operand" "=v")
(unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v")
- (match_operand:QI 2 "immediate_operand" "C")]
+ (match_operand:QI 2 "const_mask_operand" "C")]
UNSPEC_VEC_VCLGDB))]
- "TARGET_VX"
+ "TARGET_VX && UINTVAL (operands[2]) <= 7"
"vclgdb\t%v0,%v1,4,%b2"
[(set_attr "op_type" "VRR")])
; The input needs to be multiplied with 2**op2
(define_expand "vec_ctul"
- [(use (match_operand:QI 2 "immediate_operand" ""))
+ [(use (match_operand:QI 2 "const_int_operand" ""))
(set (match_dup 4) (mult:V2DF (match_operand:V2DF 1 "register_operand" "")
(match_dup 3)))
(set (match_operand:V2DI 0 "register_operand" "")
@@ -1770,12 +1770,12 @@
; Vector load fp integer - IEEE inexact exception is suppressed
(define_insn "vfidb"
- [(set (match_operand:V2DI 0 "register_operand" "=v")
- (unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v")
- (match_operand:QI 2 "immediate_operand" "C")
- (match_operand:QI 3 "immediate_operand" "C")]
+ [(set (match_operand:V2DI 0 "register_operand" "=v")
+ (unspec:V2DI [(match_operand:V2DF 1 "register_operand" "v")
+ (match_operand:QI 2 "const_mask_operand" "C")
+ (match_operand:QI 3 "const_mask_operand" "C")]
UNSPEC_VEC_VFIDB))]
- "TARGET_VX"
+ "TARGET_VX && !(UINTVAL (operands[2]) & 3) && UINTVAL (operands[3]) <= 7"
"vfidb\t%v0,%v1,%b2,%b3"
[(set_attr "op_type" "VRR")])
@@ -1887,21 +1887,21 @@
(define_insn "*vftcidb"
[(set (match_operand:V2DF 0 "register_operand" "=v")
(unspec:V2DF [(match_operand:V2DF 1 "register_operand" "v")
- (match_operand:SI 2 "immediate_operand" "J")]
+ (match_operand:HI 2 "const_int_operand" "J")]
UNSPEC_VEC_VFTCIDB))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1) (match_dup 2)] UNSPEC_VEC_VFTCIDBCC))]
- "TARGET_VX"
+ "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")"
"vftcidb\t%v0,%v1,%x2"
[(set_attr "op_type" "VRR")])
(define_insn "*vftcidb_cconly"
[(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_operand:V2DF 1 "register_operand" "v")
- (match_operand:SI 2 "immediate_operand" "J")]
+ (match_operand:HI 2 "const_int_operand" "J")]
UNSPEC_VEC_VFTCIDBCC))
(clobber (match_scratch:V2DI 0 "=v"))]
- "TARGET_VX"
+ "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")"
"vftcidb\t%v0,%v1,%x2"
[(set_attr "op_type" "VRR")])
@@ -1909,13 +1909,13 @@
[(parallel
[(set (match_operand:V2DF 0 "register_operand" "")
(unspec:V2DF [(match_operand:V2DF 1 "register_operand" "")
- (match_operand:SI 2 "immediate_operand" "")]
+ (match_operand:HI 2 "const_int_operand" "")]
UNSPEC_VEC_VFTCIDB))
(set (reg:CCRAW CC_REGNUM)
(unspec:CCRAW [(match_dup 1) (match_dup 2)] UNSPEC_VEC_VFTCIDBCC))])
(set (match_operand:SI 3 "memory_operand" "")
(unspec:SI [(reg:CCRAW CC_REGNUM)] UNSPEC_CC_TO_INT))]
- "TARGET_VX")
+ "TARGET_VX && CONST_OK_FOR_CONSTRAINT_P (INTVAL (operands[2]), 'J', \"J\")")
;;
;; Integer compares
diff --git a/gcc/configure b/gcc/configure
index bb5e02bec50..b21c864466d 100755
--- a/gcc/configure
+++ b/gcc/configure
@@ -26534,6 +26534,41 @@ $as_echo "#define HAVE_AS_TLS_MARKERS 1" >>confdefs.h
fi
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking assembler for prologue entry point marker support" >&5
+$as_echo_n "checking assembler for prologue entry point marker support... " >&6; }
+if test "${gcc_cv_as_powerpc_entry_markers+set}" = set; then :
+ $as_echo_n "(cached) " >&6
+else
+ gcc_cv_as_powerpc_entry_markers=no
+ if test $in_tree_gas = yes; then
+ if test $gcc_cv_gas_vers -ge `expr \( \( 2 \* 1000 \) + 26 \) \* 1000 + 0`
+ then gcc_cv_as_powerpc_entry_markers=yes
+fi
+ elif test x$gcc_cv_as != x; then
+ $as_echo ' .reloc .,R_PPC64_ENTRY; nop' > conftest.s
+ if { ac_try='$gcc_cv_as $gcc_cv_as_flags -a64 --fatal-warnings -o conftest.o conftest.s >&5'
+ { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_try\""; } >&5
+ (eval $ac_try) 2>&5
+ ac_status=$?
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+ test $ac_status = 0; }; }
+ then
+ gcc_cv_as_powerpc_entry_markers=yes
+ else
+ echo "configure: failed program was" >&5
+ cat conftest.s >&5
+ fi
+ rm -f conftest.o conftest.s
+ fi
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $gcc_cv_as_powerpc_entry_markers" >&5
+$as_echo "$gcc_cv_as_powerpc_entry_markers" >&6; }
+if test $gcc_cv_as_powerpc_entry_markers = yes; then
+
+$as_echo "#define HAVE_AS_ENTRY_MARKERS 1" >>confdefs.h
+
+fi
+
case $target in
*-*-aix*)
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking assembler for .ref support" >&5
diff --git a/gcc/configure.ac b/gcc/configure.ac
index 5990b7cadeb..cff95bc9c6d 100644
--- a/gcc/configure.ac
+++ b/gcc/configure.ac
@@ -4371,6 +4371,12 @@ LCF0:
[AC_DEFINE(HAVE_AS_TLS_MARKERS, 1,
[Define if your assembler supports arg info for __tls_get_addr.])])
+ gcc_GAS_CHECK_FEATURE([prologue entry point marker support],
+ gcc_cv_as_powerpc_entry_markers, [2,26,0],-a64 --fatal-warnings,
+ [ .reloc .,R_PPC64_ENTRY; nop],,
+ [AC_DEFINE(HAVE_AS_ENTRY_MARKERS, 1,
+ [Define if your assembler supports the R_PPC64_ENTRY relocation.])])
+
case $target in
*-*-aix*)
gcc_GAS_CHECK_FEATURE([.ref support],
diff --git a/gcc/coretypes.h b/gcc/coretypes.h
index d4a75db3b28..5a9fb630527 100644
--- a/gcc/coretypes.h
+++ b/gcc/coretypes.h
@@ -200,6 +200,18 @@ enum node_frequency {
NODE_FREQUENCY_HOT
};
+/* Ways of optimizing code. */
+enum optimization_type {
+ /* Prioritize speed over size. */
+ OPTIMIZE_FOR_SPEED,
+
+ /* Only do things that are good for both size and speed. */
+ OPTIMIZE_FOR_BOTH,
+
+ /* Prioritize size over speed. */
+ OPTIMIZE_FOR_SIZE
+};
+
/* Possible initialization status of a variable. When requested
by the user, this information is tracked and recorded in the DWARF
debug information, along with the variable's location. */
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index b4243369fb2..711169e8f02 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,81 @@
+2015-12-03 Cesar Philippidis <cesar@codesourcery.com>
+
+ * parser.c (cp_ensure_no_oacc_routine): Update error message.
+ (cp_parser_oacc_routine): Likewise.
+ (cp_parser_late_parsing_oacc_routine): Likewise. Update comment
+ describing this function.
+ (cp_finalize_oacc_routine): Update error message.
+
+2015-12-02 Jason Merrill <jason@redhat.com>
+
+ * Make-lang.in (check-c++1z, check-c++-all): New.
+
+2015-12-02 Markus Trippelsdorf <markus@trippelsdorf.de>
+
+ PR c++/67337
+ * mangle.c (write_template_prefix): Guard against context==NULL.
+
+2015-12-02 Jason Merrill <jason@redhat.com>
+
+ * call.c (build_new_op_1): Don't fold arguments to
+ warn_logical_operator or maybe_warn_bool_compare.
+
+ * cp-gimplify.c (cp_fold_maybe_rvalue, cp_fold_rvalue): New.
+ (c_fully_fold): Use cp_fold_rvalue.
+ (cp_fold): Use them for rvalue operands.
+
+ * cp-gimplify.c (c_fully_fold): Define.
+
+ * cp-gimplify.c (cp_fold): Use fold_build*.
+
+2015-12-02 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/68162
+ * tree.c (c_build_qualified_type): Add extra arguments.
+
+2015-12-02 Eric Botcazou <ebotcazou@adacore.com>
+
+ PR c++/68290
+ * constraint.cc (make_constrained_auto): Move to...
+ * pt.c (make_auto_1): Add set_canonical parameter and set
+ TYPE_CANONICAL on the type only if it is true.
+ (make_decltype_auto): Adjust call to make_auto_1.
+ (make_auto): Likewise.
+ (splice_late_return_type): Likewise.
+ (make_constrained_auto): ...here. Call make_auto_1 instead of
+ make_auto and pass false. Set TYPE_CANONICAL directly.
+
+2015-12-02 Thomas Schwinge <thomas@codesourcery.com>
+
+ * parser.c (cp_parser_omp_clause_name)
+ (cp_parser_oacc_all_clauses): Alphabetical sorting.
+ * pt.c (tsubst_omp_clauses): Handle OMP_CLAUSE_USE_DEVICE.
+
+2015-12-02 Andreas Arnez <arnez@linux.vnet.ibm.com>
+
+ PR gcov-profile/68603
+ * cp-gimplify.c (genericize_cp_loop): For the back-jump's location
+ use the start of the loop body only if the loop is unconditional.
+
+2015-11-26 Andreas Arnez <arnez@linux.vnet.ibm.com>
+
+ * cp-gimplify.c (genericize_cp_loop): Change LOOP_EXPR's location
+ to start of loop body instead of start of loop.
+
+2015-12-01 Julian Brown <julian@codesourcery.com>
+ Cesar Philippidis <cesar@codesourcery.com>
+ James Norris <James_Norris@mentor.com>
+
+ * cp-tree.h (finish_oacc_host_data): Add prototype.
+ * parser.c (cp_parser_omp_clause_name): Add use_device support.
+ (cp_parser_oacc_all_clauses): Add use_device support.
+ (OACC_HOST_DATA_CLAUSE_MASK): New macro.
+ (cp_parser_oacc_host_data): New function.
+ (cp_parser_omp_construct): Add host_data support.
+ (cp_parser_pragma): Add host_data support.
+ * semantics.c (finish_omp_clauses): Add use_device support.
+ (finish_oacc_host_data): New function.
+
2015-11-27 Martin Liska <mliska@suse.cz>
PR c++/68312
diff --git a/gcc/cp/Make-lang.in b/gcc/cp/Make-lang.in
index a16f228146c..50a13590a0d 100644
--- a/gcc/cp/Make-lang.in
+++ b/gcc/cp/Make-lang.in
@@ -145,9 +145,15 @@ c++.srcman: doc/g++.1
# check targets. However, our DejaGNU framework requires 'check-g++' as its
# entry point. We feed the former to the latter here.
check-c++ : check-g++
-# Run the testsute in C++0x mode.
-check-c++0x:
- @echo Normal 'make check' now runs the testsuite in C++11 mode as well as C++98.
+
+# Run the testsuite in C++1z mode.
+check-c++1z:
+ $(MAKE) RUNTESTFLAGS="$(RUNTESTFLAGS) --stds=1z" check-g++
+
+# Run the testsuite in all standard conformance levels.
+check-c++-all:
+ $(MAKE) RUNTESTFLAGS="$(RUNTESTFLAGS) --stds=98,11,14,1z" check-g++
+
# Run the testsuite with garbage collection at every opportunity.
check-g++-strict-gc:
$(MAKE) RUNTESTFLAGS="$(RUNTESTFLAGS) --extra_opts,--param,ggc-min-heapsize=0,--param,ggc-min-expand=0" \
diff --git a/gcc/cp/call.c b/gcc/cp/call.c
index 8cdda6200e1..117dd7991ff 100644
--- a/gcc/cp/call.c
+++ b/gcc/cp/call.c
@@ -5687,8 +5687,8 @@ build_new_op_1 (location_t loc, enum tree_code code, int flags, tree arg1,
decaying an enumerator to its value. */
if (complain & tf_warning)
warn_logical_operator (loc, code, boolean_type_node,
- code_orig_arg1, fold (arg1),
- code_orig_arg2, fold (arg2));
+ code_orig_arg1, arg1,
+ code_orig_arg2, arg2);
arg2 = convert_like (conv, arg2, complain);
}
@@ -5726,8 +5726,8 @@ build_new_op_1 (location_t loc, enum tree_code code, int flags, tree arg1,
case TRUTH_OR_EXPR:
if (complain & tf_warning)
warn_logical_operator (loc, code, boolean_type_node,
- code_orig_arg1, fold (arg1),
- code_orig_arg2, fold (arg2));
+ code_orig_arg1, arg1,
+ code_orig_arg2, arg2);
/* Fall through. */
case GT_EXPR:
case LT_EXPR:
@@ -5738,8 +5738,7 @@ build_new_op_1 (location_t loc, enum tree_code code, int flags, tree arg1,
if ((complain & tf_warning)
&& ((code_orig_arg1 == BOOLEAN_TYPE)
^ (code_orig_arg2 == BOOLEAN_TYPE)))
- maybe_warn_bool_compare (loc, code, fold (arg1),
- fold (arg2));
+ maybe_warn_bool_compare (loc, code, arg1, arg2);
if (complain & tf_warning && warn_tautological_compare)
warn_tautological_cmp (loc, code, arg1, arg2);
/* Fall through. */
diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc
index c6eaf754606..71e3e0d6f1c 100644
--- a/gcc/cp/constraint.cc
+++ b/gcc/cp/constraint.cc
@@ -1353,32 +1353,6 @@ finish_template_introduction (tree tmpl_decl, tree intro_list)
}
-/* Make a "constrained auto" type-specifier. This is an
- auto type with constraints that must be associated after
- deduction. The constraint is formed from the given
- CONC and its optional sequence of arguments, which are
- non-null if written as partial-concept-id. */
-tree
-make_constrained_auto (tree con, tree args)
-{
- tree type = make_auto();
-
- /* Build the constraint. */
- tree tmpl = DECL_TI_TEMPLATE (con);
- tree expr;
- if (VAR_P (con))
- expr = build_concept_check (tmpl, type, args);
- else
- expr = build_concept_check (build_overload (tmpl, NULL_TREE), type, args);
-
- tree constr = make_predicate_constraint (expr);
- PLACEHOLDER_TYPE_CONSTRAINTS (type) = constr;
-
- /* Attach the constraint to the type declaration. */
- tree decl = TYPE_NAME (type);
- return decl;
-}
-
/* Given the predicate constraint T from a constrained-type-specifier, extract
its TMPL and ARGS. FIXME why do we need two different forms of
constrained-type-specifier? */
diff --git a/gcc/cp/cp-gimplify.c b/gcc/cp/cp-gimplify.c
index a9a34cd81cc..177e2717aa5 100644
--- a/gcc/cp/cp-gimplify.c
+++ b/gcc/cp/cp-gimplify.c
@@ -264,7 +264,9 @@ genericize_cp_loop (tree *stmt_p, location_t start_locus, tree cond, tree body,
}
else
{
- location_t loc = EXPR_LOCATION (expr_first (body));
+ location_t loc = start_locus;
+ if (!cond || integer_nonzerop (cond))
+ loc = EXPR_LOCATION (expr_first (body));
if (loc == UNKNOWN_LOCATION)
loc = start_locus;
loop = build1_loc (loc, LOOP_EXPR, void_type_node, stmt_list);
@@ -1881,6 +1883,41 @@ cp_fully_fold (tree x)
return cp_fold (x);
}
+/* Fold expression X which is used as an rvalue if RVAL is true. */
+
+static tree
+cp_fold_maybe_rvalue (tree x, bool rval)
+{
+ if (rval && DECL_P (x))
+ {
+ tree v = decl_constant_value (x);
+ if (v != error_mark_node)
+ x = v;
+ }
+ return cp_fold (x);
+}
+
+/* Fold expression X which is used as an rvalue. */
+
+static tree
+cp_fold_rvalue (tree x)
+{
+ return cp_fold_maybe_rvalue (x, true);
+}
+
+/* c-common interface to cp_fold. If IN_INIT, this is in a static initializer
+ and certain changes are made to the folding done. Or should be (FIXME). We
+ never touch maybe_const, as it is only used for the C front-end
+ C_MAYBE_CONST_EXPR. */
+
+tree
+c_fully_fold (tree x, bool /*in_init*/, bool */*maybe_const*/)
+{
+ /* c_fully_fold is only used on rvalues, and we need to fold CONST_DECL to
+ INTEGER_CST. */
+ return cp_fold_rvalue (x);
+}
+
static GTY((cache, deletable)) cache_map fold_cache;
/* This function tries to fold an expression X.
@@ -1897,6 +1934,7 @@ cp_fold (tree x)
tree org_x = x, r = NULL_TREE;
enum tree_code code;
location_t loc;
+ bool rval_ops = true;
if (!x || error_operand_p (x))
return x;
@@ -1920,6 +1958,7 @@ cp_fold (tree x)
break;
case VIEW_CONVERT_EXPR:
+ rval_ops = false;
case CONVERT_EXPR:
case NOP_EXPR:
case NON_LVALUE_EXPR:
@@ -1939,12 +1978,12 @@ cp_fold (tree x)
&& TREE_TYPE (x) == TREE_TYPE (op0))
return x;
- op0 = cp_fold (op0);
+ op0 = cp_fold_maybe_rvalue (op0, rval_ops);
if (op0 != TREE_OPERAND (x, 0))
- x = build1_loc (loc, code, TREE_TYPE (x), op0);
-
- x = fold (x);
+ x = fold_build1_loc (loc, code, TREE_TYPE (x), op0);
+ else
+ x = fold (x);
/* Conversion of an out-of-range value has implementation-defined
behavior; the language considers it different from arithmetic
@@ -1955,10 +1994,10 @@ cp_fold (tree x)
break;
- case SAVE_EXPR:
case ADDR_EXPR:
case REALPART_EXPR:
case IMAGPART_EXPR:
+ rval_ops = false;
case CONJ_EXPR:
case FIX_TRUNC_EXPR:
case FLOAT_EXPR:
@@ -1971,12 +2010,12 @@ cp_fold (tree x)
case INDIRECT_REF:
loc = EXPR_LOCATION (x);
- op0 = cp_fold (TREE_OPERAND (x, 0));
+ op0 = cp_fold_maybe_rvalue (TREE_OPERAND (x, 0), rval_ops);
if (op0 != TREE_OPERAND (x, 0))
- x = build1_loc (loc, code, TREE_TYPE (x), op0);
-
- x = fold (x);
+ x = fold_build1_loc (loc, code, TREE_TYPE (x), op0);
+ else
+ x = fold (x);
gcc_assert (TREE_CODE (x) != COND_EXPR
|| !VOID_TYPE_P (TREE_TYPE (TREE_OPERAND (x, 0))));
@@ -1988,7 +2027,7 @@ cp_fold (tree x)
loc = EXPR_LOCATION (x);
op0 = cp_fold (TREE_OPERAND (x, 0));
- op1 = cp_fold (TREE_OPERAND (x, 1));
+ op1 = cp_fold_rvalue (TREE_OPERAND (x, 1));
if (TREE_OPERAND (x, 0) != op0 || TREE_OPERAND (x, 1) != op1)
x = build2_loc (loc, code, TREE_TYPE (x), op0, op1);
@@ -1998,6 +2037,8 @@ cp_fold (tree x)
case PREDECREMENT_EXPR:
case PREINCREMENT_EXPR:
case COMPOUND_EXPR:
+ case MODIFY_EXPR:
+ rval_ops = false;
case POINTER_PLUS_EXPR:
case PLUS_EXPR:
case MINUS_EXPR:
@@ -2033,11 +2074,10 @@ cp_fold (tree x)
case UNGT_EXPR: case UNGE_EXPR:
case UNEQ_EXPR: case LTGT_EXPR:
case RANGE_EXPR: case COMPLEX_EXPR:
- case MODIFY_EXPR:
loc = EXPR_LOCATION (x);
- op0 = cp_fold (TREE_OPERAND (x, 0));
- op1 = cp_fold (TREE_OPERAND (x, 1));
+ op0 = cp_fold_maybe_rvalue (TREE_OPERAND (x, 0), rval_ops);
+ op1 = cp_fold_rvalue (TREE_OPERAND (x, 1));
if ((code == COMPOUND_EXPR || code == MODIFY_EXPR)
&& ((op1 && TREE_SIDE_EFFECTS (op1))
|| (op0 && TREE_SIDE_EFFECTS (op0))))
@@ -2046,9 +2086,9 @@ cp_fold (tree x)
op0 = build_empty_stmt (loc);
if (op0 != TREE_OPERAND (x, 0) || op1 != TREE_OPERAND (x, 1))
- x = build2_loc (loc, code, TREE_TYPE (x), op0, op1);
-
- x = fold (x);
+ x = fold_build2_loc (loc, code, TREE_TYPE (x), op0, op1);
+ else
+ x = fold (x);
if (TREE_CODE (x) == COMPOUND_EXPR && TREE_OPERAND (x, 0) == NULL_TREE
&& TREE_OPERAND (x, 1))
@@ -2059,7 +2099,7 @@ cp_fold (tree x)
case COND_EXPR:
loc = EXPR_LOCATION (x);
- op0 = cp_fold (TREE_OPERAND (x, 0));
+ op0 = cp_fold_rvalue (TREE_OPERAND (x, 0));
if (TREE_SIDE_EFFECTS (op0))
break;
diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
index caa601d1c98..38ae70f7461 100644
--- a/gcc/cp/cp-tree.h
+++ b/gcc/cp/cp-tree.h
@@ -6360,6 +6360,7 @@ extern void finish_omp_threadprivate (tree);
extern tree begin_omp_structured_block (void);
extern tree finish_omp_structured_block (tree);
extern tree finish_oacc_data (tree, tree);
+extern tree finish_oacc_host_data (tree, tree);
extern tree finish_omp_construct (enum tree_code, tree, tree);
extern tree begin_omp_parallel (void);
extern tree finish_omp_parallel (tree, tree);
diff --git a/gcc/cp/mangle.c b/gcc/cp/mangle.c
index 6f8bf68d951..3ff30663f08 100644
--- a/gcc/cp/mangle.c
+++ b/gcc/cp/mangle.c
@@ -1145,7 +1145,7 @@ write_template_prefix (const tree node)
So, for the example above, `Outer<int>::Inner' is represented as a
substitution candidate by a TREE_LIST whose purpose is `Outer<int>'
and whose value is `Outer<T>::Inner<U>'. */
- if (TYPE_P (context))
+ if (context && TYPE_P (context))
substitution = build_tree_list (context, templ);
else
substitution = templ;
diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c
index 90a0673a38c..1c143541045 100644
--- a/gcc/cp/parser.c
+++ b/gcc/cp/parser.c
@@ -1329,7 +1329,7 @@ cp_ensure_no_oacc_routine (cp_parser *parser)
tree clauses = parser->oacc_routine->clauses;
location_t loc = OMP_CLAUSE_LOCATION (TREE_PURPOSE (clauses));
- error_at (loc, "%<#pragma oacc routine%> not followed by function "
+ error_at (loc, "%<#pragma acc routine%> not followed by a function "
"declaration or definition");
parser->oacc_routine = NULL;
}
@@ -29230,6 +29230,8 @@ cp_parser_omp_clause_name (cp_parser *parser)
result = PRAGMA_OMP_CLAUSE_UNIFORM;
else if (!strcmp ("untied", p))
result = PRAGMA_OMP_CLAUSE_UNTIED;
+ else if (!strcmp ("use_device", p))
+ result = PRAGMA_OACC_CLAUSE_USE_DEVICE;
else if (!strcmp ("use_device_ptr", p))
result = PRAGMA_OMP_CLAUSE_USE_DEVICE_PTR;
break;
@@ -31607,6 +31609,11 @@ cp_parser_oacc_all_clauses (cp_parser *parser, omp_clause_mask mask,
clauses = cp_parser_oacc_clause_tile (parser, here, clauses);
c_name = "tile";
break;
+ case PRAGMA_OACC_CLAUSE_USE_DEVICE:
+ clauses = cp_parser_omp_var_list (parser, OMP_CLAUSE_USE_DEVICE,
+ clauses);
+ c_name = "use_device";
+ break;
case PRAGMA_OACC_CLAUSE_VECTOR:
c_name = "vector";
clauses = cp_parser_oacc_shape_clause (parser, OMP_CLAUSE_VECTOR,
@@ -34510,6 +34517,30 @@ cp_parser_oacc_data (cp_parser *parser, cp_token *pragma_tok)
}
/* OpenACC 2.0:
+ # pragma acc host_data <clauses> new-line
+ structured-block */
+
+#define OACC_HOST_DATA_CLAUSE_MASK \
+ ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_USE_DEVICE) )
+
+static tree
+cp_parser_oacc_host_data (cp_parser *parser, cp_token *pragma_tok)
+{
+ tree stmt, clauses, block;
+ unsigned int save;
+
+ clauses = cp_parser_oacc_all_clauses (parser, OACC_HOST_DATA_CLAUSE_MASK,
+ "#pragma acc host_data", pragma_tok);
+
+ block = begin_omp_parallel ();
+ save = cp_parser_begin_omp_structured_block (parser);
+ cp_parser_statement (parser, NULL_TREE, false, NULL);
+ cp_parser_end_omp_structured_block (parser, save);
+ stmt = finish_oacc_host_data (clauses, block);
+ return stmt;
+}
+
+/* OpenACC 2.0:
# pragma acc declare oacc-data-clause[optseq] new-line
*/
@@ -35826,7 +35857,7 @@ cp_parser_oacc_routine (cp_parser *parser, cp_token *pragma_tok,
cp_parser_require_pragma_eol (parser, pragma_tok);
error_at (OMP_CLAUSE_LOCATION (parser->oacc_routine->clauses),
- "%<#pragma oacc routine%> not followed by a single "
+ "%<#pragma acc routine%> not followed by a "
"function declaration or definition");
parser->oacc_routine->error_seen = true;
@@ -35931,7 +35962,7 @@ cp_parser_oacc_routine (cp_parser *parser, cp_token *pragma_tok,
if (parser->oacc_routine
&& !parser->oacc_routine->error_seen
&& !parser->oacc_routine->fndecl_seen)
- error_at (loc, "%<#pragma acc routine%> not followed by "
+ error_at (loc, "%<#pragma acc routine%> not followed by a "
"function declaration or definition");
data.tokens.release ();
@@ -35941,7 +35972,7 @@ cp_parser_oacc_routine (cp_parser *parser, cp_token *pragma_tok,
}
/* Finalize #pragma acc routine clauses after direct declarator has
- been parsed, and put that into "oacc routine" attribute. */
+ been parsed, and put that into "oacc function" attribute. */
static tree
cp_parser_late_parsing_oacc_routine (cp_parser *parser, tree attrs)
@@ -35956,7 +35987,7 @@ cp_parser_late_parsing_oacc_routine (cp_parser *parser, tree attrs)
if ((!data->error_seen && data->fndecl_seen)
|| data->tokens.length () != 1)
{
- error_at (loc, "%<#pragma oacc routine%> not followed by a single "
+ error_at (loc, "%<#pragma acc routine%> not followed by a "
"function declaration or definition");
data->error_seen = true;
return attrs;
@@ -35972,7 +36003,7 @@ cp_parser_late_parsing_oacc_routine (cp_parser *parser, tree attrs)
cp_token *pragma_tok = cp_lexer_consume_token (parser->lexer);
cl = cp_parser_oacc_all_clauses (parser, OACC_ROUTINE_CLAUSE_MASK,
- "#pragma oacc routine", pragma_tok);
+ "#pragma acc routine", pragma_tok);
cp_parser_pop_lexer (parser);
tree c_head = build_omp_clause (loc, OMP_CLAUSE_SEQ);
@@ -36013,7 +36044,8 @@ cp_finalize_oacc_routine (cp_parser *parser, tree fndecl, bool is_defn)
if (!fndecl || TREE_CODE (fndecl) != FUNCTION_DECL)
{
error_at (loc,
- "%<#pragma acc routine%> not followed by single function");
+ "%<#pragma acc routine%> not followed by a function "
+ "declaration or definition");
parser->oacc_routine = NULL;
}
@@ -36068,6 +36100,9 @@ cp_parser_omp_construct (cp_parser *parser, cp_token *pragma_tok)
case PRAGMA_OACC_EXIT_DATA:
stmt = cp_parser_oacc_enter_exit_data (parser, pragma_tok, false);
break;
+ case PRAGMA_OACC_HOST_DATA:
+ stmt = cp_parser_oacc_host_data (parser, pragma_tok);
+ break;
case PRAGMA_OACC_KERNELS:
case PRAGMA_OACC_PARALLEL:
strcpy (p_name, "#pragma acc");
@@ -36645,6 +36680,7 @@ cp_parser_pragma (cp_parser *parser, enum pragma_context context)
case PRAGMA_OACC_DATA:
case PRAGMA_OACC_ENTER_DATA:
case PRAGMA_OACC_EXIT_DATA:
+ case PRAGMA_OACC_HOST_DATA:
case PRAGMA_OACC_KERNELS:
case PRAGMA_OACC_PARALLEL:
case PRAGMA_OACC_LOOP:
diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
index 5befd644c09..8435ddc224a 100644
--- a/gcc/cp/pt.c
+++ b/gcc/cp/pt.c
@@ -14387,6 +14387,7 @@ tsubst_omp_clauses (tree clauses, bool declare_simd, bool allow_fields,
case OMP_CLAUSE_FROM:
case OMP_CLAUSE_TO:
case OMP_CLAUSE_MAP:
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
OMP_CLAUSE_DECL (nc)
@@ -14513,6 +14514,7 @@ tsubst_omp_clauses (tree clauses, bool declare_simd, bool allow_fields,
case OMP_CLAUSE_COPYPRIVATE:
case OMP_CLAUSE_LINEAR:
case OMP_CLAUSE_REDUCTION:
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
/* tsubst_expr on SCOPE_REF results in returning
@@ -23467,10 +23469,10 @@ make_args_non_dependent (vec<tree, va_gc> *args)
/* Returns a type which represents 'auto' or 'decltype(auto)'. We use a
TEMPLATE_TYPE_PARM with a level one deeper than the actual template
- parms. */
+ parms. If set_canonical is true, we set TYPE_CANONICAL on it. */
static tree
-make_auto_1 (tree name)
+make_auto_1 (tree name, bool set_canonical)
{
tree au = cxx_make_type (TEMPLATE_TYPE_PARM);
TYPE_NAME (au) = build_decl (input_location,
@@ -23479,7 +23481,8 @@ make_auto_1 (tree name)
TEMPLATE_TYPE_PARM_INDEX (au) = build_template_parm_index
(0, processing_template_decl + 1, processing_template_decl + 1,
TYPE_NAME (au), NULL_TREE);
- TYPE_CANONICAL (au) = canonical_type_parameter (au);
+ if (set_canonical)
+ TYPE_CANONICAL (au) = canonical_type_parameter (au);
DECL_ARTIFICIAL (TYPE_NAME (au)) = 1;
SET_DECL_TEMPLATE_PARM_P (TYPE_NAME (au));
@@ -23489,13 +23492,43 @@ make_auto_1 (tree name)
tree
make_decltype_auto (void)
{
- return make_auto_1 (get_identifier ("decltype(auto)"));
+ return make_auto_1 (get_identifier ("decltype(auto)"), true);
}
tree
make_auto (void)
{
- return make_auto_1 (get_identifier ("auto"));
+ return make_auto_1 (get_identifier ("auto"), true);
+}
+
+/* Make a "constrained auto" type-specifier. This is an
+ auto type with constraints that must be associated after
+ deduction. The constraint is formed from the given
+ CONC and its optional sequence of arguments, which are
+ non-null if written as partial-concept-id. */
+
+tree
+make_constrained_auto (tree con, tree args)
+{
+ tree type = make_auto_1 (get_identifier ("auto"), false);
+
+ /* Build the constraint. */
+ tree tmpl = DECL_TI_TEMPLATE (con);
+ tree expr;
+ if (VAR_P (con))
+ expr = build_concept_check (tmpl, type, args);
+ else
+ expr = build_concept_check (build_overload (tmpl, NULL_TREE), type, args);
+
+ tree constr = make_predicate_constraint (expr);
+ PLACEHOLDER_TYPE_CONSTRAINTS (type) = constr;
+
+ /* Our canonical type depends on the constraint. */
+ TYPE_CANONICAL (type) = canonical_type_parameter (type);
+
+ /* Attach the constraint to the type declaration. */
+ tree decl = TYPE_NAME (type);
+ return decl;
}
/* Given type ARG, return std::initializer_list<ARG>. */
@@ -23811,7 +23844,7 @@ splice_late_return_type (tree type, tree late_return_type)
/* In an abbreviated function template we didn't know we were dealing
with a function template when we saw the auto return type, so update
it to have the correct level. */
- return make_auto_1 (TYPE_IDENTIFIER (type));
+ return make_auto_1 (TYPE_IDENTIFIER (type), true);
}
return type;
}
diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c
index e7e5d8ecfaa..3bb61847ca8 100644
--- a/gcc/cp/semantics.c
+++ b/gcc/cp/semantics.c
@@ -6835,6 +6835,7 @@ finish_omp_clauses (tree clauses, bool allow_fields, bool declare_simd)
}
break;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_IS_DEVICE_PTR:
case OMP_CLAUSE_USE_DEVICE_PTR:
field_ok = allow_fields;
@@ -7390,6 +7391,24 @@ finish_oacc_data (tree clauses, tree block)
return add_stmt (stmt);
}
+/* Generate OACC_HOST_DATA, with CLAUSES and BLOCK as its compound
+ statement. */
+
+tree
+finish_oacc_host_data (tree clauses, tree block)
+{
+ tree stmt;
+
+ block = finish_omp_structured_block (block);
+
+ stmt = make_node (OACC_HOST_DATA);
+ TREE_TYPE (stmt) = void_type_node;
+ OACC_HOST_DATA_CLAUSES (stmt) = clauses;
+ OACC_HOST_DATA_BODY (stmt) = block;
+
+ return add_stmt (stmt);
+}
+
/* Generate OMP construct CODE, with BODY and CLAUSES as its compound
statement. */
diff --git a/gcc/cp/tree.c b/gcc/cp/tree.c
index d2db31a628a..5dad0a77d41 100644
--- a/gcc/cp/tree.c
+++ b/gcc/cp/tree.c
@@ -995,7 +995,8 @@ move (tree expr)
the C version of this function does not properly maintain canonical
types (which are not used in C). */
tree
-c_build_qualified_type (tree type, int type_quals)
+c_build_qualified_type (tree type, int type_quals, tree /* orig_qual_type */,
+ size_t /* orig_qual_indirect */)
{
return cp_build_qualified_type (type, type_quals);
}
diff --git a/gcc/doc/md.texi b/gcc/doc/md.texi
index 8e3f8f58e5d..4848e649836 100644
--- a/gcc/doc/md.texi
+++ b/gcc/doc/md.texi
@@ -4753,6 +4753,8 @@ is true. GCC assumes that, if a target supports this kind of
instruction for some mode @var{n}, it also supports unaligned
loads for vectors of mode @var{n}.
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{vec_store_lanes@var{m}@var{n}} instruction pattern
@item @samp{vec_store_lanes@var{m}@var{n}}
Equivalent to @samp{vec_load_lanes@var{m}@var{n}}, with the memory
@@ -4768,6 +4770,8 @@ for (j = 0; j < GET_MODE_NUNITS (@var{n}); j++)
for a memory operand 0 and register operand 1.
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{vec_set@var{m}} instruction pattern
@item @samp{vec_set@var{m}}
Set given field in the vector value. Operand 0 is the vector to modify,
@@ -4822,12 +4826,16 @@ Perform a masked load of vector from memory operand 1 of mode @var{m}
into register operand 0. Mask is provided in register operand 2 of
mode @var{n}.
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{maskstore@var{m}@var{n}} instruction pattern
-@item @samp{maskload@var{m}@var{n}}
+@item @samp{maskstore@var{m}@var{n}}
Perform a masked store of vector from register operand 1 of mode @var{m}
into memory operand 0. Mask is provided in register operand 2 of
mode @var{n}.
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{vec_perm@var{m}} instruction pattern
@item @samp{vec_perm@var{m}}
Output a (variable) vector permutation. Operand 0 is the destination
@@ -4993,6 +5001,9 @@ IEEE-conformant minimum and maximum operations. If one operand is a quiet
signalling @code{NaN} (-fsignaling-nans) an invalid floating point exception is
raised and a quiet @code{NaN} is returned.
+All operands have mode @var{m}, which is a scalar or vector
+floating-point mode. These patterns are not allowed to @code{FAIL}.
+
@cindex @code{reduc_smin_@var{m}} instruction pattern
@cindex @code{reduc_smax_@var{m}} instruction pattern
@item @samp{reduc_smin_@var{m}}, @samp{reduc_smax_@var{m}}
@@ -5324,60 +5335,80 @@ Store the absolute value of operand 1 into operand 0.
@cindex @code{sqrt@var{m}2} instruction pattern
@item @samp{sqrt@var{m}2}
-Store the square root of operand 1 into operand 0.
+Store the square root of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
-The @code{sqrt} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{sqrtf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+@cindex @code{rsqrt@var{m}2} instruction pattern
+@item @samp{rsqrt@var{m}2}
+Store the reciprocal of the square root of operand 1 into operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
+
+On most architectures this pattern is only approximate, so either
+its C condition or the @code{TARGET_OPTAB_SUPPORTED_P} hook should
+check for the appropriate math flags. (Using the C condition is
+more direct, but using @code{TARGET_OPTAB_SUPPORTED_P} can be useful
+if a target-specific built-in also uses the @samp{rsqrt@var{m}2}
+pattern.)
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{fmod@var{m}3} instruction pattern
@item @samp{fmod@var{m}3}
Store the remainder of dividing operand 1 by operand 2 into
-operand 0, rounded towards zero to an integer.
+operand 0, rounded towards zero to an integer. All operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
-The @code{fmod} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{fmodf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{remainder@var{m}3} instruction pattern
@item @samp{remainder@var{m}3}
Store the remainder of dividing operand 1 by operand 2 into
-operand 0, rounded to the nearest integer.
+operand 0, rounded to the nearest integer. All operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{scalb@var{m}3} instruction pattern
+@item @samp{scalb@var{m}3}
+Raise @code{FLT_RADIX} to the power of operand 2, multiply it by
+operand 1, and store the result in operand 0. All operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{ldexp@var{m}3} instruction pattern
+@item @samp{ldexp@var{m}3}
+Raise 2 to the power of operand 2, multiply it by operand 1, and store
+the result in operand 0. Operands 0 and 1 have mode @var{m}, which is
+a scalar or vector floating-point mode. Operand 2's mode has
+the same number of elements as @var{m} and each element is wide
+enough to store an @code{int}. The integers are signed.
-The @code{remainder} built-in function of C always uses the mode
-which corresponds to the C data type @code{double} and the
-@code{remainderf} built-in function uses the mode which corresponds
-to the C data type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{cos@var{m}2} instruction pattern
@item @samp{cos@var{m}2}
-Store the cosine of operand 1 into operand 0.
+Store the cosine of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
-The @code{cos} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{cosf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{sin@var{m}2} instruction pattern
@item @samp{sin@var{m}2}
-Store the sine of operand 1 into operand 0.
+Store the sine of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
-The @code{sin} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{sinf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{sincos@var{m}3} instruction pattern
@item @samp{sincos@var{m}3}
Store the cosine of operand 2 into operand 0 and the sine of
-operand 2 into operand 1.
+operand 2 into operand 1. All operands have mode @var{m},
+which is a scalar or vector floating-point mode.
-The @code{sin} and @code{cos} built-in functions of C always use the
-mode which corresponds to the C data type @code{double} and the
-@code{sinf} and @code{cosf} built-in function use the mode which
-corresponds to the C data type @code{float}.
Targets that can calculate the sine and cosine simultaneously can
implement this pattern as opposed to implementing individual
@code{sin@var{m}2} and @code{cos@var{m}2} patterns. The @code{sin}
@@ -5385,100 +5416,185 @@ and @code{cos} built-in functions will then be expanded to the
@code{sincos@var{m}3} pattern, with one of the output values
left unused.
+@cindex @code{tan@var{m}2} instruction pattern
+@item @samp{tan@var{m}2}
+Store the tangent of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{asin@var{m}2} instruction pattern
+@item @samp{asin@var{m}2}
+Store the arc sine of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{acos@var{m}2} instruction pattern
+@item @samp{acos@var{m}2}
+Store the arc cosine of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{atan@var{m}2} instruction pattern
+@item @samp{atan@var{m}2}
+Store the arc tangent of operand 1 into operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{exp@var{m}2} instruction pattern
@item @samp{exp@var{m}2}
-Store the exponential of operand 1 into operand 0.
+Raise e (the base of natural logarithms) to the power of operand 1
+and store the result in operand 0. Both operands have mode @var{m},
+which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{expm1@var{m}2} instruction pattern
+@item @samp{expm1@var{m}2}
+Raise e (the base of natural logarithms) to the power of operand 1,
+subtract 1, and store the result in operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
+
+For inputs close to zero, the pattern is expected to be more
+accurate than a separate @code{exp@var{m}2} and @code{sub@var{m}3}
+would be.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{exp10@var{m}2} instruction pattern
+@item @samp{exp10@var{m}2}
+Raise 10 to the power of operand 1 and store the result in operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
-The @code{exp} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{expf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{exp2@var{m}2} instruction pattern
+@item @samp{exp2@var{m}2}
+Raise 2 to the power of operand 1 and store the result in operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{log@var{m}2} instruction pattern
@item @samp{log@var{m}2}
-Store the natural logarithm of operand 1 into operand 0.
+Store the natural logarithm of operand 1 into operand 0. Both operands
+have mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{log1p@var{m}2} instruction pattern
+@item @samp{log1p@var{m}2}
+Add 1 to operand 1, compute the natural logarithm, and store
+the result in operand 0. Both operands have mode @var{m}, which is
+a scalar or vector floating-point mode.
+
+For inputs close to zero, the pattern is expected to be more
+accurate than a separate @code{add@var{m}3} and @code{log@var{m}2}
+would be.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{log10@var{m}2} instruction pattern
+@item @samp{log10@var{m}2}
+Store the base-10 logarithm of operand 1 into operand 0. Both operands
+have mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{log2@var{m}2} instruction pattern
+@item @samp{log2@var{m}2}
+Store the base-2 logarithm of operand 1 into operand 0. Both operands
+have mode @var{m}, which is a scalar or vector floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{logb@var{m}2} instruction pattern
+@item @samp{logb@var{m}2}
+Store the base-@code{FLT_RADIX} logarithm of operand 1 into operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
+
+This pattern is not allowed to @code{FAIL}.
+
+@cindex @code{significand@var{m}2} instruction pattern
+@item @samp{significand@var{m}2}
+Store the significand of floating-point operand 1 in operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
-The @code{log} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{logf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{pow@var{m}3} instruction pattern
@item @samp{pow@var{m}3}
Store the value of operand 1 raised to the exponent operand 2
-into operand 0.
+into operand 0. All operands have mode @var{m}, which is a scalar
+or vector floating-point mode.
-The @code{pow} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{powf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{atan2@var{m}3} instruction pattern
@item @samp{atan2@var{m}3}
Store the arc tangent (inverse tangent) of operand 1 divided by
operand 2 into operand 0, using the signs of both arguments to
-determine the quadrant of the result.
+determine the quadrant of the result. All operands have mode
+@var{m}, which is a scalar or vector floating-point mode.
-The @code{atan2} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{atan2f}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{floor@var{m}2} instruction pattern
@item @samp{floor@var{m}2}
-Store the largest integral value not greater than argument.
+Store the largest integral value not greater than operand 1 in operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
-The @code{floor} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{floorf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{btrunc@var{m}2} instruction pattern
@item @samp{btrunc@var{m}2}
-Store the argument rounded to integer towards zero.
+Round operand 1 to an integer, towards zero, and store the result in
+operand 0. Both operands have mode @var{m}, which is a scalar or
+vector floating-point mode.
-The @code{trunc} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{truncf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{round@var{m}2} instruction pattern
@item @samp{round@var{m}2}
-Store the argument rounded to integer away from zero.
+Round operand 1 to the nearest integer, rounding away from zero in the
+event of a tie, and store the result in operand 0. Both operands have
+mode @var{m}, which is a scalar or vector floating-point mode.
-The @code{round} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{roundf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{ceil@var{m}2} instruction pattern
@item @samp{ceil@var{m}2}
-Store the argument rounded to integer away from zero.
+Store the smallest integral value not less than operand 1 in operand 0.
+Both operands have mode @var{m}, which is a scalar or vector
+floating-point mode.
-The @code{ceil} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{ceilf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{nearbyint@var{m}2} instruction pattern
@item @samp{nearbyint@var{m}2}
-Store the argument rounded according to the default rounding mode
+Round operand 1 to an integer, using the current rounding mode, and
+store the result in operand 0. Do not raise an inexact condition when
+the result is different from the argument. Both operands have mode
+@var{m}, which is a scalar or vector floating-point mode.
-The @code{nearbyint} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{nearbyintf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{rint@var{m}2} instruction pattern
@item @samp{rint@var{m}2}
-Store the argument rounded according to the default rounding mode and
-raise the inexact exception when the result differs in value from
-the argument
+Round operand 1 to an integer, using the current rounding mode, and
+store the result in operand 0. Raise an inexact condition when
+the result is different from the argument. Both operands have mode
+@var{m}, which is a scalar or vector floating-point mode.
-The @code{rint} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{rintf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{lrint@var{m}@var{n}2}
@item @samp{lrint@var{m}@var{n}2}
@@ -5507,23 +5623,24 @@ operand 0 (which has mode @var{n}).
@cindex @code{copysign@var{m}3} instruction pattern
@item @samp{copysign@var{m}3}
Store a value with the magnitude of operand 1 and the sign of operand
-2 into operand 0.
+2 into operand 0. All operands have mode @var{m}, which is a scalar or
+vector floating-point mode.
-The @code{copysign} built-in function of C always uses the mode which
-corresponds to the C data type @code{double} and the @code{copysignf}
-built-in function uses the mode which corresponds to the C data
-type @code{float}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{ffs@var{m}2} instruction pattern
@item @samp{ffs@var{m}2}
Store into operand 0 one plus the index of the least significant 1-bit
-of operand 1. If operand 1 is zero, store zero. @var{m} is the mode
-of operand 0; operand 1's mode is specified by the instruction
-pattern, and the compiler will convert the operand to that mode before
-generating the instruction.
+of operand 1. If operand 1 is zero, store zero.
+
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
-The @code{ffs} built-in function of C always uses the mode which
-corresponds to the C data type @code{int}.
+This pattern is not allowed to @code{FAIL}.
@cindex @code{clrsb@var{m}2} instruction pattern
@item @samp{clrsb@var{m}2}
@@ -5533,15 +5650,30 @@ at the most significant bit position.
A redundant sign bit is defined as any sign bit after the first. As such,
this count will be one less than the count of leading sign bits.
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
+
+This pattern is not allowed to @code{FAIL}.
+
@cindex @code{clz@var{m}2} instruction pattern
@item @samp{clz@var{m}2}
Store into operand 0 the number of leading 0-bits in operand 1, starting
at the most significant bit position. If operand 1 is 0, the
@code{CLZ_DEFINED_VALUE_AT_ZERO} (@pxref{Misc}) macro defines if
the result is undefined or has a useful value.
-@var{m} is the mode of operand 0; operand 1's mode is
-specified by the instruction pattern, and the compiler will convert the
-operand to that mode before generating the instruction.
+
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{ctz@var{m}2} instruction pattern
@item @samp{ctz@var{m}2}
@@ -5549,23 +5681,42 @@ Store into operand 0 the number of trailing 0-bits in operand 1, starting
at the least significant bit position. If operand 1 is 0, the
@code{CTZ_DEFINED_VALUE_AT_ZERO} (@pxref{Misc}) macro defines if
the result is undefined or has a useful value.
-@var{m} is the mode of operand 0; operand 1's mode is
-specified by the instruction pattern, and the compiler will convert the
-operand to that mode before generating the instruction.
+
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{popcount@var{m}2} instruction pattern
@item @samp{popcount@var{m}2}
-Store into operand 0 the number of 1-bits in operand 1. @var{m} is the
-mode of operand 0; operand 1's mode is specified by the instruction
-pattern, and the compiler will convert the operand to that mode before
-generating the instruction.
+Store into operand 0 the number of 1-bits in operand 1.
+
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{parity@var{m}2} instruction pattern
@item @samp{parity@var{m}2}
Store into operand 0 the parity of operand 1, i.e.@: the number of 1-bits
-in operand 1 modulo 2. @var{m} is the mode of operand 0; operand 1's mode
-is specified by the instruction pattern, and the compiler will convert
-the operand to that mode before generating the instruction.
+in operand 1 modulo 2.
+
+@var{m} is either a scalar or vector integer mode. When it is a scalar,
+operand 1 has mode @var{m} but operand 0 can have whatever scalar
+integer mode is suitable for the target. The compiler will insert
+conversion instructions as necessary (typically to convert the result
+to the same width as @code{int}). When @var{m} is a vector, both
+operands must have mode @var{m}.
+
+This pattern is not allowed to @code{FAIL}.
@cindex @code{one_cmpl@var{m}2} instruction pattern
@item @samp{one_cmpl@var{m}2}
diff --git a/gcc/doc/tm.texi b/gcc/doc/tm.texi
index 7146ec55836..1ce7181c3d4 100644
--- a/gcc/doc/tm.texi
+++ b/gcc/doc/tm.texi
@@ -5608,9 +5608,9 @@ be placed in an @code{object_block} structure.
The default version returns true for all decls.
@end deftypefn
-@deftypefn {Target Hook} tree TARGET_BUILTIN_RECIPROCAL (gcall *@var{call})
-This hook should return the DECL of a function that implements reciprocal of
-the builtin or internal function call @var{call}, or
+@deftypefn {Target Hook} tree TARGET_BUILTIN_RECIPROCAL (tree @var{fndecl})
+This hook should return the DECL of a function that implements the
+reciprocal of the machine-specific builtin function @var{fndecl}, or
@code{NULL_TREE} if such a function is not available.
@end deftypefn
@@ -6425,6 +6425,20 @@ Define this macro if a non-short-circuit operation produced by
@code{BRANCH_COST} is greater than or equal to the value 2.
@end defmac
+@deftypefn {Target Hook} bool TARGET_OPTAB_SUPPORTED_P (int @var{op}, machine_mode @var{mode1}, machine_mode @var{mode2}, optimization_type @var{opt_type})
+Return true if the optimizers should use optab @var{op} with
+modes @var{mode1} and @var{mode2} for optimization type @var{opt_type}.
+The optab is known to have an associated @file{.md} instruction
+whose C condition is true. @var{mode2} is only meaningful for conversion
+optabs; for direct optabs it is a copy of @var{mode1}.
+
+For example, when called with @var{op} equal to @code{rint_optab} and
+@var{mode1} equal to @code{DFmode}, the hook should say whether the
+optimizers should use optab @code{rintdf2}.
+
+The default hook returns true for all inputs.
+@end deftypefn
+
@deftypefn {Target Hook} bool TARGET_RTX_COSTS (rtx @var{x}, machine_mode @var{mode}, int @var{outer_code}, int @var{opno}, int *@var{total}, bool @var{speed})
This target hook describes the relative costs of RTL expressions.
diff --git a/gcc/doc/tm.texi.in b/gcc/doc/tm.texi.in
index 0677fc1c8cc..a0a0a812fc1 100644
--- a/gcc/doc/tm.texi.in
+++ b/gcc/doc/tm.texi.in
@@ -4746,6 +4746,8 @@ Define this macro if a non-short-circuit operation produced by
@code{BRANCH_COST} is greater than or equal to the value 2.
@end defmac
+@hook TARGET_OPTAB_SUPPORTED_P
+
@hook TARGET_RTX_COSTS
@hook TARGET_ADDRESS_COST
diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c
index 357f1148ede..6af57b58864 100644
--- a/gcc/dwarf2out.c
+++ b/gcc/dwarf2out.c
@@ -19268,7 +19268,9 @@ gen_subprogram_die (tree decl, dw_die_ref context_die)
rtx tloc = NULL_RTX, tlocc = NULL_RTX;
rtx arg, next_arg;
- for (arg = NOTE_VAR_LOCATION (ca_loc->call_arg_loc_note);
+ for (arg = (ca_loc->call_arg_loc_note != NULL_RTX
+ ? NOTE_VAR_LOCATION (ca_loc->call_arg_loc_note)
+ : NULL_RTX);
arg; arg = next_arg)
{
dw_loc_descr_ref reg, val;
@@ -19291,18 +19293,23 @@ gen_subprogram_die (tree decl, dw_die_ref context_die)
}
if (mode == VOIDmode || mode == BLKmode)
continue;
- if (XEXP (XEXP (arg, 0), 0) == pc_rtx)
+ /* Get dynamic information about call target only if we
+ have no static information: we cannot generate both
+ DW_AT_abstract_origin and DW_AT_GNU_call_site_target
+ attributes. */
+ if (ca_loc->symbol_ref == NULL_RTX)
{
- gcc_assert (ca_loc->symbol_ref == NULL_RTX);
- tloc = XEXP (XEXP (arg, 0), 1);
- continue;
- }
- else if (GET_CODE (XEXP (XEXP (arg, 0), 0)) == CLOBBER
- && XEXP (XEXP (XEXP (arg, 0), 0), 0) == pc_rtx)
- {
- gcc_assert (ca_loc->symbol_ref == NULL_RTX);
- tlocc = XEXP (XEXP (arg, 0), 1);
- continue;
+ if (XEXP (XEXP (arg, 0), 0) == pc_rtx)
+ {
+ tloc = XEXP (XEXP (arg, 0), 1);
+ continue;
+ }
+ else if (GET_CODE (XEXP (XEXP (arg, 0), 0)) == CLOBBER
+ && XEXP (XEXP (XEXP (arg, 0), 0), 0) == pc_rtx)
+ {
+ tlocc = XEXP (XEXP (arg, 0), 1);
+ continue;
+ }
}
reg = NULL;
if (REG_P (XEXP (XEXP (arg, 0), 0)))
@@ -22289,6 +22296,7 @@ dwarf2out_var_location (rtx_insn *loc_note)
char loclabel[MAX_ARTIFICIAL_LABEL_BYTES + 2];
struct var_loc_node *newloc;
rtx_insn *next_real, *next_note;
+ rtx_insn *call_insn = NULL;
static const char *last_label;
static const char *last_postcall_label;
static bool last_in_cold_section_p;
@@ -22303,6 +22311,35 @@ dwarf2out_var_location (rtx_insn *loc_note)
call_site_count++;
if (SIBLING_CALL_P (loc_note))
tail_call_site_count++;
+ if (optimize == 0 && !flag_var_tracking)
+ {
+ /* When the var-tracking pass is not running, there is no note
+ for indirect calls whose target is compile-time known. In this
+ case, process such calls specifically so that we generate call
+ sites for them anyway. */
+ rtx x = PATTERN (loc_note);
+ if (GET_CODE (x) == PARALLEL)
+ x = XVECEXP (x, 0, 0);
+ if (GET_CODE (x) == SET)
+ x = SET_SRC (x);
+ if (GET_CODE (x) == CALL)
+ x = XEXP (x, 0);
+ if (!MEM_P (x)
+ || GET_CODE (XEXP (x, 0)) != SYMBOL_REF
+ || !SYMBOL_REF_DECL (XEXP (x, 0))
+ || (TREE_CODE (SYMBOL_REF_DECL (XEXP (x, 0)))
+ != FUNCTION_DECL))
+ {
+ call_insn = loc_note;
+ loc_note = NULL;
+ var_loc_p = false;
+
+ next_real = next_real_insn (call_insn);
+ next_note = NULL;
+ cached_next_real_insn = NULL;
+ goto create_label;
+ }
+ }
}
return;
}
@@ -22348,6 +22385,8 @@ dwarf2out_var_location (rtx_insn *loc_note)
&& !NOTE_DURING_CALL_P (loc_note))
return;
+create_label:
+
if (next_real == NULL_RTX)
next_real = get_last_insn ();
@@ -22427,12 +22466,16 @@ dwarf2out_var_location (rtx_insn *loc_note)
}
}
+ gcc_assert ((loc_note == NULL_RTX && call_insn != NULL_RTX)
+ || (loc_note != NULL_RTX && call_insn == NULL_RTX));
+
if (!var_loc_p)
{
struct call_arg_loc_node *ca_loc
= ggc_cleared_alloc<call_arg_loc_node> ();
- rtx_insn *prev = prev_real_insn (loc_note);
- rtx x;
+ rtx_insn *prev
+ = loc_note != NULL_RTX ? prev_real_insn (loc_note) : call_insn;
+
ca_loc->call_arg_loc_note = loc_note;
ca_loc->next = NULL;
ca_loc->label = last_label;
@@ -22444,15 +22487,27 @@ dwarf2out_var_location (rtx_insn *loc_note)
if (!CALL_P (prev))
prev = as_a <rtx_sequence *> (PATTERN (prev))->insn (0);
ca_loc->tail_call_p = SIBLING_CALL_P (prev);
- x = get_call_rtx_from (PATTERN (prev));
+
+ /* Look for a SYMBOL_REF in the "prev" instruction. */
+ rtx x = get_call_rtx_from (PATTERN (prev));
if (x)
{
- x = XEXP (XEXP (x, 0), 0);
- if (GET_CODE (x) == SYMBOL_REF
- && SYMBOL_REF_DECL (x)
- && TREE_CODE (SYMBOL_REF_DECL (x)) == FUNCTION_DECL)
- ca_loc->symbol_ref = x;
+ /* Try to get the call symbol, if any. */
+ if (MEM_P (XEXP (x, 0)))
+ x = XEXP (x, 0);
+ /* First, look for a memory access to a symbol_ref. */
+ if (GET_CODE (XEXP (x, 0)) == SYMBOL_REF
+ && SYMBOL_REF_DECL (XEXP (x, 0))
+ && TREE_CODE (SYMBOL_REF_DECL (XEXP (x, 0))) == FUNCTION_DECL)
+ ca_loc->symbol_ref = XEXP (x, 0);
+ /* Otherwise, look at a compile-time known user-level function
+ declaration. */
+ else if (MEM_P (x)
+ && MEM_EXPR (x)
+ && TREE_CODE (MEM_EXPR (x)) == FUNCTION_DECL)
+ ca_loc->symbol_ref = XEXP (DECL_RTL (MEM_EXPR (x)), 0);
}
+
ca_loc->block = insn_scope (prev);
if (call_arg_locations)
call_arg_loc_last->next = ca_loc;
@@ -22460,7 +22515,7 @@ dwarf2out_var_location (rtx_insn *loc_note)
call_arg_locations = ca_loc;
call_arg_loc_last = ca_loc;
}
- else if (!NOTE_DURING_CALL_P (loc_note))
+ else if (loc_note != NULL_RTX && !NOTE_DURING_CALL_P (loc_note))
newloc->label = last_label;
else
{
diff --git a/gcc/final.c b/gcc/final.c
index 2f57b1bc3f1..8cb55332e3d 100644
--- a/gcc/final.c
+++ b/gcc/final.c
@@ -2995,7 +2995,8 @@ final_scan_insn (rtx_insn *insn, FILE *file, int optimize_p ATTRIBUTE_UNUSED,
&& targetm.asm_out.unwind_emit)
targetm.asm_out.unwind_emit (asm_out_file, insn);
- if (rtx_call_insn *call_insn = dyn_cast <rtx_call_insn *> (insn))
+ rtx_call_insn *call_insn = dyn_cast <rtx_call_insn *> (insn);
+ if (call_insn != NULL)
{
rtx x = call_from_call_insn (call_insn);
x = XEXP (x, 0);
@@ -3007,8 +3008,6 @@ final_scan_insn (rtx_insn *insn, FILE *file, int optimize_p ATTRIBUTE_UNUSED,
if (t)
assemble_external (t);
}
- if (!DECL_IGNORED_P (current_function_decl))
- debug_hooks->var_location (insn);
}
/* Output assembler code from the template. */
@@ -3024,6 +3023,12 @@ final_scan_insn (rtx_insn *insn, FILE *file, int optimize_p ATTRIBUTE_UNUSED,
&& targetm.asm_out.unwind_emit)
targetm.asm_out.unwind_emit (asm_out_file, insn);
+ /* Let the debug info back-end know about this call. We do this only
+ after the instruction has been emitted because labels that may be
+ created to reference the call instruction must appear after it. */
+ if (call_insn != NULL && !DECL_IGNORED_P (current_function_decl))
+ debug_hooks->var_location (insn);
+
current_output_insn = debug_insn = 0;
}
}
diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog
index 52dcc826538..7617a1adf7c 100644
--- a/gcc/fortran/ChangeLog
+++ b/gcc/fortran/ChangeLog
@@ -1,3 +1,89 @@
+2015-12-02 Tobias Burnus <burnus@net-b.de>
+ Alessandro Fanfarillo <fanfarillo.gcc@gmail.com>
+
+ * check.c (gfc_check_event_query): New function.
+ * dump-parse-tree.c (show_code_node): Handle EXEC_EVENT_POST,
+ EXEC_EVENT_WAIT.
+ * expr.c (gfc_check_vardef_context): New check for event variables
+ definition.
+ * gfortran.h (gfc_statement): Add ST_EVENT_POST, ST_EVENT_WAIT.
+ (gfc_isym_id): GFC_ISYM_EVENT_QUERY.
+ (struct symbol_attribute): New field.
+ (gfc_exec_op): Add EXEC_EVENT_POST and EXEC_EVENT_WAIT.
+ * gfortran.texi: Document about new events functions and minor
+ changes.
+ * interface.c (compare_parameter): New check.
+ (gfc_procedure_use): New check for explicit procedure interface.
+ (add_subroutines): Add event_query.
+ * intrinsic.h (gfc_check_event_query,gfc_resolve_event_query):
+ New prototypes.
+ * iresolve.c (gfc_resolve_event_query): New function.
+ * iso-fortran-env.def (event_type): New type.
+ * match.c (event_statement,gfc_match_event_post,gfc_match_event_wait):
+ New functions.
+ (gfc_match_name): New event post and event wait.
+ * match.h (gfc_match_event_post,gfc_match_event_wait):
+ New prototypes.
+ * module.c (ab_attribute): Add AB_EVENT_COMP.
+ (attr_bits): Likewise.
+ (mio_symbol_attribute): Handle event_comp attribute.
+ * parse.c (decode_statement): Add ST_EVENT_POST, ST_EVENT_WAIT.
+ (next_statement): Add ST_EVENT_POST, ST_EVENT_WAIT.
+ (gfc_ascii_statement): Add ST_EVENT_POST, ST_EVENT_WAIT.
+ (parse_derived): Check for event_type components.
+ * resolve.c (resolve_allocate_expr): Check for event variable def.
+ (resolve_lock_unlock): Renamed to resolve_lock_unlock_event. It
+ includes logic for locks and events.
+ (gfc_resolve_code): Call it.
+ (gfc_resolve_symbol): New check for event variable to be a corray.
+ * st.c (gfc_free_statement): Handle new EXEC_EVENT_POST and
+ EXEC_EVENT_WAIT.
+ * trans-decl.c (gfor_fndecl_caf_event_post,gfor_fndecl_caf_event_wait,
+ gfor_fndecl_caf_event_query): New global variables.
+ (generate_coarray_sym_init): Checking for event_type.
+ (gfc_conv_procedure_call): Check for C bind attribute.
+ * trans-intrinsic.c (conv_intrinsic_event_query): New function.
+ (conv_intrinsic_move_alloc): Call it.
+ * trans-stmt.c (gfc_trans_lock_unlock): Passing address
+ of actual argument.
+ (gfc_trans_sync): Likewise.
+ (gfc_trans_event_post_wait): New function.
+ * trans-stmt.h (gfc_trans_event_post_wait): New prototype.
+ * trans-types.c (gfc_get_derived_type): Integer_kind as event_type.
+ * trans.c (gfc_allocate_using_lib): New argument and logic for events.
+ (gfc_allocate_allocatable): Passing new argument.
+ (trans_code): Handle EXEC_EVENT_POST, EXEC_EVENT_WAIT.
+ * trans.h (gfc_coarray_type): New elements.
+ (gfor_fndecl_caf_event_post,gfor_fndecl_caf_event_wait,
+ gfor_fndecl_caf_event_query): Declare them.
+
+2015-12-02 Cesar Philippidis <cesar@codesourcery.com>
+
+ PR fortran/63861
+ * openmp.c (gfc_match_omp_clauses): Allow subarrays for acc reductions.
+ (resolve_omp_clauses): Error on any acc reductions on arrays.
+
+2015-12-01 Cesar Philippidis <cesar@codesourcery.com>
+
+ * dump-parse-tree.c (show_omp_clauses): Handle optional num and static
+ arguments for the gang clause.
+ * gfortran.h (gfc_omp_clauses): Rename gang_expr as gang_num_expr.
+ Add gang_static_expr.
+ * openmp.c (gfc_free_omp_clauses): Update to free gang_num_expr and
+ gang_static_expr.
+ (match_oacc_clause_gang): Update to support both num and static in
+ the same clause.
+ (resolve_omp_clauses): Formatting. Also handle gang_num_expr and
+ gang_static_expr.
+ (resolve_oacc_params_in_parallel): New const char arg argument.
+ Use it to report more accurate gang, worker and vector clause errors.
+ (resolve_oacc_loop_blocks): Update calls to
+ resolve_oacc_params_in_parallel.
+ * trans-openmp.c (gfc_trans_omp_clauses): Update the gimplification of
+ the gang clause.
+ (gfc_trans_oacc_combined_directive): Make use of gang_num_expr and
+ gang_static_expr. Remove OMP_LIST_REDUCTION from construct_clauses.
+
2015-11-30 Cesar Philippidis <cesar@codesourcery.com>
James Norris <jnorris@codesourcery.com>
Nathan Sidwell <nathan@codesourcery.com>
diff --git a/gcc/fortran/check.c b/gcc/fortran/check.c
index 038ee218d94..6dc7f3e264b 100644
--- a/gcc/fortran/check.c
+++ b/gcc/fortran/check.c
@@ -1157,6 +1157,59 @@ gfc_check_atomic_cas (gfc_expr *atom, gfc_expr *old, gfc_expr *compare,
return true;
}
+bool
+gfc_check_event_query (gfc_expr *event, gfc_expr *count, gfc_expr *stat)
+{
+ if (event->ts.type != BT_DERIVED
+ || event->ts.u.derived->from_intmod != INTMOD_ISO_FORTRAN_ENV
+ || event->ts.u.derived->intmod_sym_id != ISOFORTRAN_EVENT_TYPE)
+ {
+ gfc_error ("EVENT argument at %L to the intrinsic EVENT_QUERY "
+ "shall be of type EVENT_TYPE", &event->where);
+ return false;
+ }
+
+ if (!scalar_check (event, 0))
+ return false;
+
+ if (!gfc_check_vardef_context (count, false, false, false, NULL))
+ {
+ gfc_error ("COUNT argument of the EVENT_QUERY intrinsic function at %L "
+ "shall be definable", &count->where);
+ return false;
+ }
+
+ if (!type_check (count, 1, BT_INTEGER))
+ return false;
+
+ int i = gfc_validate_kind (BT_INTEGER, count->ts.kind, false);
+ int j = gfc_validate_kind (BT_INTEGER, gfc_default_integer_kind, false);
+
+ if (gfc_integer_kinds[i].range < gfc_integer_kinds[j].range)
+ {
+ gfc_error ("COUNT argument of the EVENT_QUERY intrinsic function at %L "
+ "shall have at least the range of the default integer",
+ &count->where);
+ return false;
+ }
+
+ if (stat != NULL)
+ {
+ if (!type_check (stat, 2, BT_INTEGER))
+ return false;
+ if (!scalar_check (stat, 2))
+ return false;
+ if (!variable_check (stat, 2, false))
+ return false;
+
+ if (!gfc_notify_std (GFC_STD_F2008_TS, "STAT= argument to %s at %L",
+ gfc_current_intrinsic, &stat->where))
+ return false;
+ }
+
+ return true;
+}
+
bool
gfc_check_atomic_fetch_op (gfc_expr *atom, gfc_expr *value, gfc_expr *old,
diff --git a/gcc/fortran/dump-parse-tree.c b/gcc/fortran/dump-parse-tree.c
index 48476af56d3..dad5c18439a 100644
--- a/gcc/fortran/dump-parse-tree.c
+++ b/gcc/fortran/dump-parse-tree.c
@@ -1146,10 +1146,24 @@ show_omp_clauses (gfc_omp_clauses *omp_clauses)
if (omp_clauses->gang)
{
fputs (" GANG", dumpfile);
- if (omp_clauses->gang_expr)
+ if (omp_clauses->gang_num_expr || omp_clauses->gang_static_expr)
{
fputc ('(', dumpfile);
- show_expr (omp_clauses->gang_expr);
+ if (omp_clauses->gang_num_expr)
+ {
+ fprintf (dumpfile, "num:");
+ show_expr (omp_clauses->gang_num_expr);
+ }
+ if (omp_clauses->gang_num_expr && omp_clauses->gang_static)
+ fputc (',', dumpfile);
+ if (omp_clauses->gang_static)
+ {
+ fprintf (dumpfile, "static:");
+ if (omp_clauses->gang_static_expr)
+ show_expr (omp_clauses->gang_static_expr);
+ else
+ fputc ('*', dumpfile);
+ }
fputc (')', dumpfile);
}
}
@@ -1659,6 +1673,33 @@ show_code_node (int level, gfc_code *c)
}
break;
+ case EXEC_EVENT_POST:
+ case EXEC_EVENT_WAIT:
+ if (c->op == EXEC_EVENT_POST)
+ fputs ("EVENT POST ", dumpfile);
+ else
+ fputs ("EVENT WAIT ", dumpfile);
+
+ fputs ("event-variable=", dumpfile);
+ if (c->expr1 != NULL)
+ show_expr (c->expr1);
+ if (c->expr4 != NULL)
+ {
+ fputs (" until_count=", dumpfile);
+ show_expr (c->expr4);
+ }
+ if (c->expr2 != NULL)
+ {
+ fputs (" stat=", dumpfile);
+ show_expr (c->expr2);
+ }
+ if (c->expr3 != NULL)
+ {
+ fputs (" errmsg=", dumpfile);
+ show_expr (c->expr3);
+ }
+ break;
+
case EXEC_LOCK:
case EXEC_UNLOCK:
if (c->op == EXEC_LOCK)
diff --git a/gcc/fortran/expr.c b/gcc/fortran/expr.c
index 7aaf0e252a0..2aeb0b5f946 100644
--- a/gcc/fortran/expr.c
+++ b/gcc/fortran/expr.c
@@ -4860,6 +4860,19 @@ gfc_check_vardef_context (gfc_expr* e, bool pointer, bool alloc_obj,
return false;
}
+ /* TS18508, C702/C203. */
+ if (!alloc_obj
+ && (attr.lock_comp
+ || (e->ts.type == BT_DERIVED
+ && e->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && e->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)))
+ {
+ if (context)
+ gfc_error ("LOCK_EVENT in variable definition context (%s) at %L",
+ context, &e->where);
+ return false;
+ }
+
/* INTENT(IN) dummy argument. Check this, unless the object itself is the
component of sub-component of a pointer; we need to distinguish
assignment to a pointer component from pointer-assignment to a pointer
diff --git a/gcc/fortran/gfortran.h b/gcc/fortran/gfortran.h
index 0628e8628c2..9f61e4522c4 100644
--- a/gcc/fortran/gfortran.h
+++ b/gcc/fortran/gfortran.h
@@ -241,7 +241,8 @@ enum gfc_statement
ST_OMP_TARGET_TEAMS_DISTRIBUTE_PARALLEL_DO_SIMD,
ST_OMP_END_TARGET_TEAMS_DISTRIBUTE_PARALLEL_DO_SIMD,
ST_PROCEDURE, ST_GENERIC, ST_CRITICAL, ST_END_CRITICAL,
- ST_GET_FCN_CHARACTERISTICS, ST_LOCK, ST_UNLOCK, ST_NONE
+ ST_GET_FCN_CHARACTERISTICS, ST_LOCK, ST_UNLOCK, ST_EVENT_POST,
+ ST_EVENT_WAIT,ST_NONE
};
/* Types of interfaces that we can have. Assignment interfaces are
@@ -393,6 +394,7 @@ enum gfc_isym_id
GFC_ISYM_ERFC,
GFC_ISYM_ERFC_SCALED,
GFC_ISYM_ETIME,
+ GFC_ISYM_EVENT_QUERY,
GFC_ISYM_EXECUTE_COMMAND_LINE,
GFC_ISYM_EXIT,
GFC_ISYM_EXP,
@@ -828,7 +830,7 @@ typedef struct
entities. */
unsigned alloc_comp:1, pointer_comp:1, proc_pointer_comp:1,
private_comp:1, zero_comp:1, coarray_comp:1, lock_comp:1,
- defined_assign_comp:1, unlimited_polymorphic:1;
+ event_comp:1, defined_assign_comp:1, unlimited_polymorphic:1;
/* This is a temporary selector for SELECT TYPE or an associate
variable for SELECT_TYPE or ASSOCIATE. */
@@ -1229,7 +1231,8 @@ typedef struct gfc_omp_clauses
/* OpenACC. */
struct gfc_expr *async_expr;
- struct gfc_expr *gang_expr;
+ struct gfc_expr *gang_static_expr;
+ struct gfc_expr *gang_num_expr;
struct gfc_expr *worker_expr;
struct gfc_expr *vector_expr;
struct gfc_expr *num_gangs_expr;
@@ -2365,7 +2368,7 @@ enum gfc_exec_op
EXEC_OPEN, EXEC_CLOSE, EXEC_WAIT,
EXEC_READ, EXEC_WRITE, EXEC_IOLENGTH, EXEC_TRANSFER, EXEC_DT_END,
EXEC_BACKSPACE, EXEC_ENDFILE, EXEC_INQUIRE, EXEC_REWIND, EXEC_FLUSH,
- EXEC_LOCK, EXEC_UNLOCK,
+ EXEC_LOCK, EXEC_UNLOCK, EXEC_EVENT_POST, EXEC_EVENT_WAIT,
EXEC_OACC_KERNELS_LOOP, EXEC_OACC_PARALLEL_LOOP, EXEC_OACC_ROUTINE,
EXEC_OACC_PARALLEL, EXEC_OACC_KERNELS, EXEC_OACC_DATA, EXEC_OACC_HOST_DATA,
EXEC_OACC_LOOP, EXEC_OACC_UPDATE, EXEC_OACC_WAIT, EXEC_OACC_CACHE,
diff --git a/gcc/fortran/gfortran.texi b/gcc/fortran/gfortran.texi
index 876f22663d5..d82ded61dcf 100644
--- a/gcc/fortran/gfortran.texi
+++ b/gcc/fortran/gfortran.texi
@@ -3342,7 +3342,9 @@ typedef enum caf_register_t {
CAF_REGTYPE_COARRAY_ALLOC,
CAF_REGTYPE_LOCK_STATIC,
CAF_REGTYPE_LOCK_ALLOC,
- CAF_REGTYPE_CRITICAL
+ CAF_REGTYPE_CRITICAL,
+ CAF_REGTYPE_EVENT_STATIC,
+ CAF_REGTYPE_EVENT_ALLOC
}
caf_register_t;
@end verbatim
@@ -3363,6 +3365,9 @@ caf_register_t;
* _gfortran_caf_sendget:: Sending data between remote images
* _gfortran_caf_lock:: Locking a lock variable
* _gfortran_caf_unlock:: Unlocking a lock variable
+* _gfortran_caf_event_post:: Post an event
+* _gfortran_caf_event_wait:: Wait that an event occurred
+* _gfortran_caf_event_query:: Query event count
* _gfortran_caf_sync_all:: All-image barrier
* _gfortran_caf_sync_images:: Barrier for selected images
* _gfortran_caf_sync_memory:: Wait for completion of segment-memory operations
@@ -3516,7 +3521,7 @@ int *stat, char *errmsg, int errmsg_len)}
@item @emph{Arguments}:
@multitable @columnfractions .15 .70
@item @var{size} @tab For normal coarrays, the byte size of the coarray to be
-allocated; for lock types, the number of elements.
+allocated; for lock types and event types, the number of elements.
@item @var{type} @tab one of the caf_register_t types.
@item @var{token} @tab intent(out) An opaque pointer identifying the coarray.
@item @var{stat} @tab intent(out) For allocatable coarrays, stores the STAT=;
@@ -3541,7 +3546,10 @@ image. For lock types, the value shall only used for checking the allocation
status. Note that for critical blocks, the locking is only required on one
image; in the locking statement, the processor shall always pass always an
image index of one for critical-block lock variables
-(@code{CAF_REGTYPE_CRITICAL}).
+(@code{CAF_REGTYPE_CRITICAL}). For lock types and critical-block variables,
+the initial value shall be unlocked (or, respecitively, not in critical
+section) such as the value false; for event types, the initial state should
+be no event, e.g. zero.
@end table
@@ -3561,8 +3569,7 @@ int errmsg_len)}
@item @emph{Arguments}:
@multitable @columnfractions .15 .70
-@item @var{stat} @tab intent(out) For allocatable coarrays, stores the STAT=;
-may be NULL
+@item @var{stat} @tab intent(out) Stores the STAT=; may be NULL
@item @var{errmsg} @tab intent(out) When an error occurs, this will be set
to an error message; may be NULL
@item @var{errmsg_len} @tab the buffer size of errmsg.
@@ -3769,8 +3776,7 @@ always 0.
number.
@item @var{aquired_lock} @tab intent(out) If not NULL, it returns whether lock
could be obtained
-@item @var{stat} @tab intent(out) For allocatable coarrays, stores the STAT=;
-may be NULL
+@item @var{stat} @tab intent(out) Stores the STAT=; may be NULL
@item @var{errmsg} @tab intent(out) When an error occurs, this will be set to
an error message; may be NULL
@item @var{errmsg_len} @tab the buffer size of errmsg.
@@ -3782,7 +3788,6 @@ is always zero and the image index is one. Libraries are permitted to use other
images for critical-block locking variables.
@end table
-
@node _gfortran_caf_unlock
@subsection @code{_gfortran_caf_lock} --- Unlocking a lock variable
@cindex Coarray, _gfortran_caf_unlock
@@ -3817,6 +3822,115 @@ is always zero and the image index is one. Libraries are permitted to use other
images for critical-block locking variables.
@end table
+@node _gfortran_caf_event_post
+@subsection @code{_gfortran_caf_event_post} --- Post an event
+@cindex Coarray, _gfortran_caf_event_post
+
+@table @asis
+@item @emph{Description}:
+Increment the event count of the specified event variable.
+
+@item @emph{Syntax}:
+@code{void _gfortran_caf_event_post (caf_token_t token, size_t index,
+int image_index, int *stat, char *errmsg, int errmsg_len)}
+
+@item @emph{Arguments}:
+@multitable @columnfractions .15 .70
+@item @var{token} @tab intent(in) An opaque pointer identifying the coarray.
+@item @var{index} @tab Array index; first array index is 0. For scalars, it is
+always 0.
+@item @var{image_index} @tab The ID of the remote image; must be a positive
+number; zero indicates the current image when accessed noncoindexed.
+@item @var{stat} @tab intent(out) Stores the STAT=; may be NULL
+@item @var{errmsg} @tab intent(out) When an error occurs, this will be set to
+an error message; may be NULL
+@item @var{errmsg_len} @tab the buffer size of errmsg.
+@end multitable
+
+@item @emph{NOTES}
+This acts like an atomic add of one to the remote image's event variable.
+The statement is an image-control statement but does not imply sync memory.
+Still, all preceeding push communications of this image to the specified
+remote image has to be completed before @code{event_wait} on the remote
+image returns.
+@end table
+
+
+
+@node _gfortran_caf_event_wait
+@subsection @code{_gfortran_caf_event_wait} --- Wait that an event occurred
+@cindex Coarray, _gfortran_caf_event_wait
+
+@table @asis
+@item @emph{Description}:
+Wait until the event count has reached at least the specified
+@var{until_count}; if so, atomically decrement the event variable by this
+amount and return.
+
+@item @emph{Syntax}:
+@code{void _gfortran_caf_event_wait (caf_token_t token, size_t index,
+int until_count, int *stat, char *errmsg, int errmsg_len)}
+
+@item @emph{Arguments}:
+@multitable @columnfractions .15 .70
+@item @var{token} @tab intent(in) An opaque pointer identifying the coarray.
+@item @var{index} @tab Array index; first array index is 0. For scalars, it is
+always 0.
+@item @var{until_count} @tab The number of events which have to be available
+before the function returns.
+@item @var{stat} @tab intent(out) Stores the STAT=; may be NULL
+@item @var{errmsg} @tab intent(out) When an error occurs, this will be set to
+an error message; may be NULL
+@item @var{errmsg_len} @tab the buffer size of errmsg.
+@end multitable
+
+@item @emph{NOTES}
+This function only operates on a local coarray. It acts like a loop checking
+atomically the value of the event variable, breaking if the value is greater
+or equal the requested number of counts. Before the function returns, the
+event variable has to be decremented by the requested @var{until_count} value.
+A possible implementation would be a busy loop for a certain number of spins
+(possibly depending on the number of threads relative to the number of available
+cores) followed by other waiting strategy such as a sleeping wait (possibly with
+an increasing number of sleep time) or, if possible, a futex wait.
+
+The statement is an image-control statement but does not imply sync memory.
+Still, all preceeding push communications to this image of images having
+issued a @code{event_push} have to be completed before this function returns.
+@end table
+
+
+
+@node _gfortran_caf_event_query
+@subsection @code{_gfortran_caf_event_query} --- Query event count
+@cindex Coarray, _gfortran_caf_event_query
+
+@table @asis
+@item @emph{Description}:
+Return the event count of the specified event count.
+
+@item @emph{Syntax}:
+@code{void _gfortran_caf_event_query (caf_token_t token, size_t index,
+int image_index, int *count, int *stat)}
+
+@item @emph{Arguments}:
+@multitable @columnfractions .15 .70
+@item @var{token} @tab intent(in) An opaque pointer identifying the coarray.
+@item @var{index} @tab Array index; first array index is 0. For scalars, it is
+always 0.
+@item @var{image_index} @tab The ID of the remote image; must be a positive
+number; zero indicates the current image when accessed noncoindexed.
+@item @var{count} @tab intent(out) The number of events currently posted to
+the event variable
+@item @var{stat} @tab intent(out) Stores the STAT=; may be NULL
+@end multitable
+
+@item @emph{NOTES}
+The typical use is to check the local even variable to only call
+@code{event_wait} when the data is available. However, a coindexed variable
+is permitted; there is no ordering or synchronization implied. It acts like
+an atomic fetch of the value of the event variable.
+@end table
@node _gfortran_caf_sync_all
@subsection @code{_gfortran_caf_sync_all} --- All-image barrier
@@ -3962,7 +4076,7 @@ int image_index, void *value, int *stat, int type, int kind)}
@item @var{offset} @tab By which amount of bytes the actual data is shifted
compared to the base address of the coarray.
@item @var{image_index} @tab The ID of the remote image; must be a positive
-number.
+number; zero indicates the current image when used noncoindexed.
@item @var{value} @tab intent(in) the value to be assigned, passed by reference.
@item @var{stat} @tab intent(out) Stores the status STAT= and may be NULL.
@item @var{type} @tab the data type, i.e. @code{BT_INTEGER} (1) or
@@ -3992,7 +4106,7 @@ int image_index, void *value, int *stat, int type, int kind)}
@item @var{offset} @tab By which amount of bytes the actual data is shifted
compared to the base address of the coarray.
@item @var{image_index} @tab The ID of the remote image; must be a positive
-number.
+number; zero indicates the current image when used noncoindexed.
@item @var{value} @tab intent(out) The variable assigned the atomically
referenced variable.
@item @var{stat} @tab intent(out) Stores the status STAT= and may be NULL.
@@ -4025,7 +4139,7 @@ int type, int kind)}
@item @var{offset} @tab By which amount of bytes the actual data is shifted
compared to the base address of the coarray.
@item @var{image_index} @tab The ID of the remote image; must be a positive
-number.
+number; zero indicates the current image when used noncoindexed.
@item @var{old} @tab intent(out) the value which the atomic variable had
just before the cas operation.
@item @var{compare} @tab intent(in) The value used for comparision.
@@ -4067,7 +4181,7 @@ int image_index, void *value, void *old, int *stat, int type, int kind)}
@item @var{offset} @tab By which amount of bytes the actual data is shifted
compared to the base address of the coarray.
@item @var{image_index} @tab The ID of the remote image; must be a positive
-number.
+number; zero indicates the current image when used noncoindexed.
@item @var{old} @tab intent(out) the value which the atomic variable had
just before the atomic operation.
@item @var{val} @tab intent(in) The new value for the atomic variable,
diff --git a/gcc/fortran/interface.c b/gcc/fortran/interface.c
index dcf3eae81e7..f74239d4844 100644
--- a/gcc/fortran/interface.c
+++ b/gcc/fortran/interface.c
@@ -2157,6 +2157,21 @@ compare_parameter (gfc_symbol *formal, gfc_expr *actual,
formal->name, &actual->where);
return 0;
}
+
+ /* TS18508, C702/C703. */
+ if (formal->attr.intent != INTENT_INOUT
+ && (((formal->ts.type == BT_DERIVED || formal->ts.type == BT_CLASS)
+ && formal->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && formal->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ || formal->attr.event_comp))
+
+ {
+ if (where)
+ gfc_error ("Actual argument to non-INTENT(INOUT) dummy %qs at %L, "
+ "which is EVENT_TYPE or has a EVENT_TYPE component",
+ formal->name, &actual->where);
+ return 0;
+ }
}
/* F2008, C1239/C1240. */
@@ -3385,6 +3400,19 @@ gfc_procedure_use (gfc_symbol *sym, gfc_actual_arglist **ap, locus *where)
break;
}
+ if (a->expr
+ && (a->expr->ts.type == BT_DERIVED || a->expr->ts.type == BT_CLASS)
+ && ((a->expr->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && a->expr->ts.u.derived->intmod_sym_id
+ == ISOFORTRAN_EVENT_TYPE)
+ || gfc_expr_attr (a->expr).event_comp))
+ {
+ gfc_error ("Actual argument of EVENT_TYPE or with EVENT_TYPE "
+ "component at %L requires an explicit interface for "
+ "procedure %qs", &a->expr->where, sym->name);
+ break;
+ }
+
if (a->expr && a->expr->expr_type == EXPR_NULL
&& a->expr->ts.type == BT_UNKNOWN)
{
diff --git a/gcc/fortran/intrinsic.c b/gcc/fortran/intrinsic.c
index 4e6a0d0e34a..170006adc33 100644
--- a/gcc/fortran/intrinsic.c
+++ b/gcc/fortran/intrinsic.c
@@ -3164,6 +3164,13 @@ add_subroutines (void)
GFC_STD_F95, gfc_check_cpu_time, NULL, gfc_resolve_cpu_time,
tm, BT_REAL, dr, REQUIRED, INTENT_OUT);
+ add_sym_3s ("event_query", GFC_ISYM_EVENT_QUERY, CLASS_ATOMIC,
+ BT_UNKNOWN, 0, GFC_STD_F2008_TS,
+ gfc_check_event_query, NULL, gfc_resolve_event_query,
+ "event", BT_INTEGER, di, REQUIRED, INTENT_IN,
+ c, BT_INTEGER, di, OPTIONAL, INTENT_IN,
+ stat, BT_INTEGER, di, OPTIONAL, INTENT_OUT);
+
/* More G77 compatibility garbage. */
add_sym_2s ("ctime", GFC_ISYM_CTIME, CLASS_IMPURE, BT_UNKNOWN, 0, GFC_STD_GNU,
gfc_check_ctime_sub, NULL, gfc_resolve_ctime_sub,
diff --git a/gcc/fortran/intrinsic.h b/gcc/fortran/intrinsic.h
index ca2ad306e0d..9b76542c526 100644
--- a/gcc/fortran/intrinsic.h
+++ b/gcc/fortran/intrinsic.h
@@ -70,6 +70,7 @@ bool gfc_check_dprod (gfc_expr *, gfc_expr *);
bool gfc_check_dshift (gfc_expr *, gfc_expr *, gfc_expr *);
bool gfc_check_eoshift (gfc_expr *, gfc_expr *, gfc_expr *, gfc_expr *);
bool gfc_check_dtime_etime (gfc_expr *);
+bool gfc_check_event_query (gfc_expr *, gfc_expr *, gfc_expr *);
bool gfc_check_fgetputc (gfc_expr *, gfc_expr *);
bool gfc_check_fgetput (gfc_expr *);
bool gfc_check_float (gfc_expr *);
@@ -462,6 +463,7 @@ void gfc_resolve_dtime_sub (gfc_code *);
void gfc_resolve_eoshift (gfc_expr *, gfc_expr *, gfc_expr *, gfc_expr *,
gfc_expr *);
void gfc_resolve_etime_sub (gfc_code *);
+void gfc_resolve_event_query (gfc_code *);
void gfc_resolve_exp (gfc_expr *, gfc_expr *);
void gfc_resolve_exponent (gfc_expr *, gfc_expr *);
void gfc_resolve_extends_type_of (gfc_expr *, gfc_expr *, gfc_expr *);
diff --git a/gcc/fortran/iresolve.c b/gcc/fortran/iresolve.c
index 80b429fbb36..8aa3a16af2e 100644
--- a/gcc/fortran/iresolve.c
+++ b/gcc/fortran/iresolve.c
@@ -2945,6 +2945,12 @@ gfc_resolve_atomic_ref (gfc_code *c)
c->resolved_sym = gfc_get_intrinsic_sub_symbol (name);
}
+void
+gfc_resolve_event_query (gfc_code *c)
+{
+ const char *name = "event_query";
+ c->resolved_sym = gfc_get_intrinsic_sub_symbol (name);
+}
void
gfc_resolve_mvbits (gfc_code *c)
diff --git a/gcc/fortran/iso-fortran-env.def b/gcc/fortran/iso-fortran-env.def
index eba0b4c9e2f..c5fb3ff21f0 100644
--- a/gcc/fortran/iso-fortran-env.def
+++ b/gcc/fortran/iso-fortran-env.def
@@ -123,6 +123,11 @@ NAMED_FUNCTION (ISOFORTRAN_COMPILER_VERSION, "compiler_version", \
NAMED_DERIVED_TYPE (ISOFORTRAN_LOCK_TYPE, "lock_type", \
get_int_kind_from_node (ptr_type_node), GFC_STD_F2008)
+NAMED_DERIVED_TYPE (ISOFORTRAN_EVENT_TYPE, "event_type", \
+ flag_coarray == GFC_FCOARRAY_LIB
+ ? get_int_kind_from_node (ptr_type_node)
+ : gfc_default_integer_kind, GFC_STD_F2008_TS)
+
#undef NAMED_INTCST
#undef NAMED_KINDARRAY
#undef NAMED_FUNCTION
diff --git a/gcc/fortran/match.c b/gcc/fortran/match.c
index 22b0d7d42f7..b55346497e9 100644
--- a/gcc/fortran/match.c
+++ b/gcc/fortran/match.c
@@ -1463,6 +1463,8 @@ gfc_match_if (gfc_statement *if_type)
match ("deallocate", gfc_match_deallocate, ST_DEALLOCATE)
match ("end file", gfc_match_endfile, ST_END_FILE)
match ("error stop", gfc_match_error_stop, ST_ERROR_STOP)
+ match ("event post", gfc_match_event_post, ST_EVENT_POST)
+ match ("event wait", gfc_match_event_wait, ST_EVENT_WAIT)
match ("exit", gfc_match_exit, ST_EXIT)
match ("flush", gfc_match_flush, ST_FLUSH)
match ("forall", match_simple_forall, ST_FORALL)
@@ -2747,6 +2749,202 @@ gfc_match_error_stop (void)
return gfc_match_stopcode (ST_ERROR_STOP);
}
+/* Match EVENT POST/WAIT statement. Syntax:
+ EVENT POST ( event-variable [, sync-stat-list] )
+ EVENT WAIT ( event-variable [, wait-spec-list] )
+ with
+ wait-spec-list is sync-stat-list or until-spec
+ until-spec is UNTIL_COUNT = scalar-int-expr
+ sync-stat is STAT= or ERRMSG=. */
+
+static match
+event_statement (gfc_statement st)
+{
+ match m;
+ gfc_expr *tmp, *eventvar, *until_count, *stat, *errmsg;
+ bool saw_until_count, saw_stat, saw_errmsg;
+
+ tmp = eventvar = until_count = stat = errmsg = NULL;
+ saw_until_count = saw_stat = saw_errmsg = false;
+
+ if (gfc_pure (NULL))
+ {
+ gfc_error ("Image control statement EVENT %s at %C in PURE procedure",
+ st == ST_EVENT_POST ? "POST" : "WAIT");
+ return MATCH_ERROR;
+ }
+
+ gfc_unset_implicit_pure (NULL);
+
+ if (flag_coarray == GFC_FCOARRAY_NONE)
+ {
+ gfc_fatal_error ("Coarrays disabled at %C, use %<-fcoarray=%> to enable");
+ return MATCH_ERROR;
+ }
+
+ if (gfc_find_state (COMP_CRITICAL))
+ {
+ gfc_error ("Image control statement EVENT %s at %C in CRITICAL block",
+ st == ST_EVENT_POST ? "POST" : "WAIT");
+ return MATCH_ERROR;
+ }
+
+ if (gfc_find_state (COMP_DO_CONCURRENT))
+ {
+ gfc_error ("Image control statement EVENT %s at %C in DO CONCURRENT "
+ "block", st == ST_EVENT_POST ? "POST" : "WAIT");
+ return MATCH_ERROR;
+ }
+
+ if (gfc_match_char ('(') != MATCH_YES)
+ goto syntax;
+
+ if (gfc_match ("%e", &eventvar) != MATCH_YES)
+ goto syntax;
+ m = gfc_match_char (',');
+ if (m == MATCH_ERROR)
+ goto syntax;
+ if (m == MATCH_NO)
+ {
+ m = gfc_match_char (')');
+ if (m == MATCH_YES)
+ goto done;
+ goto syntax;
+ }
+
+ for (;;)
+ {
+ m = gfc_match (" stat = %v", &tmp);
+ if (m == MATCH_ERROR)
+ goto syntax;
+ if (m == MATCH_YES)
+ {
+ if (saw_stat)
+ {
+ gfc_error ("Redundant STAT tag found at %L ", &tmp->where);
+ goto cleanup;
+ }
+ stat = tmp;
+ saw_stat = true;
+
+ m = gfc_match_char (',');
+ if (m == MATCH_YES)
+ continue;
+
+ tmp = NULL;
+ break;
+ }
+
+ m = gfc_match (" errmsg = %v", &tmp);
+ if (m == MATCH_ERROR)
+ goto syntax;
+ if (m == MATCH_YES)
+ {
+ if (saw_errmsg)
+ {
+ gfc_error ("Redundant ERRMSG tag found at %L ", &tmp->where);
+ goto cleanup;
+ }
+ errmsg = tmp;
+ saw_errmsg = true;
+
+ m = gfc_match_char (',');
+ if (m == MATCH_YES)
+ continue;
+
+ tmp = NULL;
+ break;
+ }
+
+ m = gfc_match (" until_count = %e", &tmp);
+ if (m == MATCH_ERROR || st == ST_EVENT_POST)
+ goto syntax;
+ if (m == MATCH_YES)
+ {
+ if (saw_until_count)
+ {
+ gfc_error ("Redundant UNTIL_COUNT tag found at %L ",
+ &tmp->where);
+ goto cleanup;
+ }
+ until_count = tmp;
+ saw_until_count = true;
+
+ m = gfc_match_char (',');
+ if (m == MATCH_YES)
+ continue;
+
+ tmp = NULL;
+ break;
+ }
+
+ break;
+ }
+
+ if (m == MATCH_ERROR)
+ goto syntax;
+
+ if (gfc_match (" )%t") != MATCH_YES)
+ goto syntax;
+
+done:
+ switch (st)
+ {
+ case ST_EVENT_POST:
+ new_st.op = EXEC_EVENT_POST;
+ break;
+ case ST_EVENT_WAIT:
+ new_st.op = EXEC_EVENT_WAIT;
+ break;
+ default:
+ gcc_unreachable ();
+ }
+
+ new_st.expr1 = eventvar;
+ new_st.expr2 = stat;
+ new_st.expr3 = errmsg;
+ new_st.expr4 = until_count;
+
+ return MATCH_YES;
+
+syntax:
+ gfc_syntax_error (st);
+
+cleanup:
+ if (until_count != tmp)
+ gfc_free_expr (until_count);
+ if (errmsg != tmp)
+ gfc_free_expr (errmsg);
+ if (stat != tmp)
+ gfc_free_expr (stat);
+
+ gfc_free_expr (tmp);
+ gfc_free_expr (eventvar);
+
+ return MATCH_ERROR;
+
+}
+
+
+match
+gfc_match_event_post (void)
+{
+ if (!gfc_notify_std (GFC_STD_F2008_TS, "EVENT POST statement at %C"))
+ return MATCH_ERROR;
+
+ return event_statement (ST_EVENT_POST);
+}
+
+
+match
+gfc_match_event_wait (void)
+{
+ if (!gfc_notify_std (GFC_STD_F2008_TS, "EVENT WAIT statement at %C"))
+ return MATCH_ERROR;
+
+ return event_statement (ST_EVENT_WAIT);
+}
+
/* Match LOCK/UNLOCK statement. Syntax:
LOCK ( lock-variable [ , lock-stat-list ] )
diff --git a/gcc/fortran/match.h b/gcc/fortran/match.h
index a52c189c1cf..7d383ed7357 100644
--- a/gcc/fortran/match.h
+++ b/gcc/fortran/match.h
@@ -69,6 +69,8 @@ match gfc_match_assignment (void);
match gfc_match_if (gfc_statement *);
match gfc_match_else (void);
match gfc_match_elseif (void);
+match gfc_match_event_post (void);
+match gfc_match_event_wait (void);
match gfc_match_critical (void);
match gfc_match_block (void);
match gfc_match_associate (void);
diff --git a/gcc/fortran/module.c b/gcc/fortran/module.c
index 6b544ee7596..704ff1523ef 100644
--- a/gcc/fortran/module.c
+++ b/gcc/fortran/module.c
@@ -1981,7 +1981,7 @@ enum ab_attribute
AB_ELEMENTAL, AB_PURE, AB_RECURSIVE, AB_GENERIC, AB_ALWAYS_EXPLICIT,
AB_CRAY_POINTER, AB_CRAY_POINTEE, AB_THREADPRIVATE,
AB_ALLOC_COMP, AB_POINTER_COMP, AB_PROC_POINTER_COMP, AB_PRIVATE_COMP,
- AB_VALUE, AB_VOLATILE, AB_PROTECTED, AB_LOCK_COMP,
+ AB_VALUE, AB_VOLATILE, AB_PROTECTED, AB_LOCK_COMP, AB_EVENT_COMP,
AB_IS_BIND_C, AB_IS_C_INTEROP, AB_IS_ISO_C, AB_ABSTRACT, AB_ZERO_COMP,
AB_IS_CLASS, AB_PROCEDURE, AB_PROC_POINTER, AB_ASYNCHRONOUS, AB_CODIMENSION,
AB_COARRAY_COMP, AB_VTYPE, AB_VTAB, AB_CONTIGUOUS, AB_CLASS_POINTER,
@@ -2028,6 +2028,7 @@ static const mstring attr_bits[] =
minit ("ALLOC_COMP", AB_ALLOC_COMP),
minit ("COARRAY_COMP", AB_COARRAY_COMP),
minit ("LOCK_COMP", AB_LOCK_COMP),
+ minit ("EVENT_COMP", AB_EVENT_COMP),
minit ("POINTER_COMP", AB_POINTER_COMP),
minit ("PROC_POINTER_COMP", AB_PROC_POINTER_COMP),
minit ("PRIVATE_COMP", AB_PRIVATE_COMP),
@@ -2216,6 +2217,8 @@ mio_symbol_attribute (symbol_attribute *attr)
MIO_NAME (ab_attribute) (AB_COARRAY_COMP, attr_bits);
if (attr->lock_comp)
MIO_NAME (ab_attribute) (AB_LOCK_COMP, attr_bits);
+ if (attr->event_comp)
+ MIO_NAME (ab_attribute) (AB_EVENT_COMP, attr_bits);
if (attr->zero_comp)
MIO_NAME (ab_attribute) (AB_ZERO_COMP, attr_bits);
if (attr->is_class)
@@ -2383,6 +2386,9 @@ mio_symbol_attribute (symbol_attribute *attr)
case AB_LOCK_COMP:
attr->lock_comp = 1;
break;
+ case AB_EVENT_COMP:
+ attr->event_comp = 1;
+ break;
case AB_POINTER_COMP:
attr->pointer_comp = 1;
break;
diff --git a/gcc/fortran/openmp.c b/gcc/fortran/openmp.c
index 730b7f98cd0..276f2f13fa1 100644
--- a/gcc/fortran/openmp.c
+++ b/gcc/fortran/openmp.c
@@ -77,7 +77,8 @@ gfc_free_omp_clauses (gfc_omp_clauses *c)
gfc_free_expr (c->thread_limit);
gfc_free_expr (c->dist_chunk_size);
gfc_free_expr (c->async_expr);
- gfc_free_expr (c->gang_expr);
+ gfc_free_expr (c->gang_num_expr);
+ gfc_free_expr (c->gang_static_expr);
gfc_free_expr (c->worker_expr);
gfc_free_expr (c->vector_expr);
gfc_free_expr (c->num_gangs_expr);
@@ -395,21 +396,41 @@ cleanup:
static match
match_oacc_clause_gang (gfc_omp_clauses *cp)
{
- if (gfc_match_char ('(') != MATCH_YES)
+ match ret = MATCH_YES;
+
+ if (gfc_match (" ( ") != MATCH_YES)
return MATCH_NO;
- if (gfc_match (" num :") == MATCH_YES)
- {
- cp->gang_static = false;
- return gfc_match (" %e )", &cp->gang_expr);
- }
- if (gfc_match (" static :") == MATCH_YES)
+
+ /* The gang clause accepts two optional arguments, num and static.
+ The num argument may either be explicit (num: <val>) or
+ implicit without (<val> without num:). */
+
+ while (ret == MATCH_YES)
{
- cp->gang_static = true;
- if (gfc_match (" * )") != MATCH_YES)
- return gfc_match (" %e )", &cp->gang_expr);
- return MATCH_YES;
+ if (gfc_match (" static :") == MATCH_YES)
+ {
+ if (cp->gang_static)
+ return MATCH_ERROR;
+ else
+ cp->gang_static = true;
+ if (gfc_match_char ('*') == MATCH_YES)
+ cp->gang_static_expr = NULL;
+ else if (gfc_match (" %e ", &cp->gang_static_expr) != MATCH_YES)
+ return MATCH_ERROR;
+ }
+ else
+ {
+ /* This is optional. */
+ if (cp->gang_num_expr || gfc_match (" num :") == MATCH_ERROR)
+ return MATCH_ERROR;
+ else if (gfc_match (" %e ", &cp->gang_num_expr) != MATCH_YES)
+ return MATCH_ERROR;
+ }
+
+ ret = gfc_match (" , ");
}
- return gfc_match (" %e )", &cp->gang_expr);
+
+ return gfc_match (" ) ");
}
static match
@@ -957,7 +978,8 @@ gfc_match_omp_clauses (gfc_omp_clauses **cp, uint64_t mask,
if (gfc_match_omp_variable_list (" :",
&c->lists[OMP_LIST_REDUCTION],
- false, NULL, &head) == MATCH_YES)
+ false, NULL, &head, openacc)
+ == MATCH_YES)
{
gfc_omp_namelist *n;
if (rop == OMP_REDUCTION_NONE)
@@ -3292,6 +3314,11 @@ resolve_omp_clauses (gfc_code *code, gfc_omp_clauses *omp_clauses,
n->sym->name, &n->where);
else
n->sym->mark = 1;
+
+ /* OpenACC does not support reductions on arrays. */
+ if (n->sym->as)
+ gfc_error ("Array %qs is not permitted in reduction at %L",
+ n->sym->name, &n->where);
}
}
@@ -3726,11 +3753,15 @@ resolve_omp_clauses (gfc_code *code, gfc_omp_clauses *omp_clauses,
if (omp_clauses->num_gangs_expr)
resolve_oacc_positive_int_expr (omp_clauses->num_gangs_expr, "NUM_GANGS");
if (omp_clauses->num_workers_expr)
- resolve_oacc_positive_int_expr (omp_clauses->num_workers_expr, "NUM_WORKERS");
+ resolve_oacc_positive_int_expr (omp_clauses->num_workers_expr,
+ "NUM_WORKERS");
if (omp_clauses->vector_length_expr)
- resolve_oacc_positive_int_expr (omp_clauses->vector_length_expr, "VECTOR_LENGTH");
- if (omp_clauses->gang_expr)
- resolve_oacc_positive_int_expr (omp_clauses->gang_expr, "GANG");
+ resolve_oacc_positive_int_expr (omp_clauses->vector_length_expr,
+ "VECTOR_LENGTH");
+ if (omp_clauses->gang_num_expr)
+ resolve_oacc_positive_int_expr (omp_clauses->gang_num_expr, "GANG");
+ if (omp_clauses->gang_static_expr)
+ resolve_oacc_positive_int_expr (omp_clauses->gang_static_expr, "GANG");
if (omp_clauses->worker_expr)
resolve_oacc_positive_int_expr (omp_clauses->worker_expr, "WORKER");
if (omp_clauses->vector_expr)
@@ -4705,20 +4736,21 @@ resolve_oacc_nested_loops (gfc_code *code, gfc_code* do_code, int collapse,
static void
-resolve_oacc_params_in_parallel (gfc_code *code, const char *clause)
+resolve_oacc_params_in_parallel (gfc_code *code, const char *clause,
+ const char *arg)
{
fortran_omp_context *c;
if (oacc_is_parallel (code))
gfc_error ("!$ACC LOOP %s in PARALLEL region doesn't allow "
- "non-static arguments at %L", clause, &code->loc);
+ "%s arguments at %L", clause, arg, &code->loc);
for (c = omp_current_ctx; c; c = c->previous)
{
if (oacc_is_loop (c->code))
break;
if (oacc_is_parallel (c->code))
gfc_error ("!$ACC LOOP %s in PARALLEL region doesn't allow "
- "non-static arguments at %L", clause, &code->loc);
+ "%s arguments at %L", clause, arg, &code->loc);
}
}
@@ -4801,13 +4833,16 @@ resolve_oacc_loop_blocks (gfc_code *code)
"vectors at the same time at %L", &code->loc);
if (code->ext.omp_clauses->gang
- && code->ext.omp_clauses->gang_expr
- && !code->ext.omp_clauses->gang_static)
- resolve_oacc_params_in_parallel (code, "GANG");
+ && code->ext.omp_clauses->gang_num_expr)
+ resolve_oacc_params_in_parallel (code, "GANG", "num");
if (code->ext.omp_clauses->worker
&& code->ext.omp_clauses->worker_expr)
- resolve_oacc_params_in_parallel (code, "WORKER");
+ resolve_oacc_params_in_parallel (code, "WORKER", "num");
+
+ if (code->ext.omp_clauses->vector
+ && code->ext.omp_clauses->vector_expr)
+ resolve_oacc_params_in_parallel (code, "VECTOR", "length");
if (code->ext.omp_clauses->tile_list)
{
diff --git a/gcc/fortran/parse.c b/gcc/fortran/parse.c
index b2d15a89aeb..157dea874ad 100644
--- a/gcc/fortran/parse.c
+++ b/gcc/fortran/parse.c
@@ -477,6 +477,8 @@ decode_statement (void)
match ("entry% ", gfc_match_entry, ST_ENTRY);
match ("equivalence", gfc_match_equivalence, ST_EQUIVALENCE);
match ("external", gfc_match_external, ST_ATTR_DECL);
+ match ("event post", gfc_match_event_post, ST_EVENT_POST);
+ match ("event wait", gfc_match_event_wait, ST_EVENT_WAIT);
break;
case 'f':
@@ -1348,6 +1350,7 @@ next_statement (void)
case ST_OMP_CANCEL: case ST_OMP_CANCELLATION_POINT: \
case ST_OMP_TARGET_UPDATE: case ST_ERROR_STOP: case ST_SYNC_ALL: \
case ST_SYNC_IMAGES: case ST_SYNC_MEMORY: case ST_LOCK: case ST_UNLOCK: \
+ case ST_EVENT_POST: case ST_EVENT_WAIT: \
case ST_OACC_UPDATE: case ST_OACC_WAIT: case ST_OACC_CACHE: \
case ST_OACC_ENTER_DATA: case ST_OACC_EXIT_DATA
@@ -1654,6 +1657,12 @@ gfc_ascii_statement (gfc_statement st)
case ST_ELSEWHERE:
p = "ELSEWHERE";
break;
+ case ST_EVENT_POST:
+ p = "EVENT POST";
+ break;
+ case ST_EVENT_WAIT:
+ p = "EVENT WAIT";
+ break;
case ST_END_ASSOCIATE:
p = "END ASSOCIATE";
break;
@@ -2646,7 +2655,7 @@ parse_derived (void)
gfc_statement st;
gfc_state_data s;
gfc_symbol *sym;
- gfc_component *c, *lock_comp = NULL;
+ gfc_component *c, *lock_comp = NULL, *event_comp = NULL;
accept_statement (ST_DERIVED_DECL);
push_state (&s, COMP_DERIVED, gfc_new_block);
@@ -2754,8 +2763,8 @@ endType:
sym = gfc_current_block ();
for (c = sym->components; c; c = c->next)
{
- bool coarray, lock_type, allocatable, pointer;
- coarray = lock_type = allocatable = pointer = false;
+ bool coarray, lock_type, event_type, allocatable, pointer;
+ coarray = lock_type = event_type = allocatable = pointer = false;
/* Look for allocatable components. */
if (c->attr.allocatable
@@ -2817,6 +2826,23 @@ endType:
sym->attr.lock_comp = 1;
}
+ /* Looking for event_type components. */
+ if ((c->ts.type == BT_DERIVED
+ && c->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && c->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ || (c->ts.type == BT_CLASS && c->attr.class_ok
+ && CLASS_DATA (c)->ts.u.derived->from_intmod
+ == INTMOD_ISO_FORTRAN_ENV
+ && CLASS_DATA (c)->ts.u.derived->intmod_sym_id
+ == ISOFORTRAN_EVENT_TYPE)
+ || (c->ts.type == BT_DERIVED && c->ts.u.derived->attr.event_comp
+ && !allocatable && !pointer))
+ {
+ event_type = 1;
+ event_comp = c;
+ sym->attr.event_comp = 1;
+ }
+
/* Check for F2008, C1302 - and recall that pointers may not be coarrays
(5.3.14) and that subobjects of coarray are coarray themselves (2.4.7),
unless there are nondirect [allocatable or pointer] components
@@ -2857,6 +2883,43 @@ endType:
"coarray subcomponent)", lock_comp->name, &lock_comp->loc,
sym->name, c->name, &c->loc);
+ /* Similarly for EVENT TYPE. */
+
+ if (pointer && !coarray && event_type)
+ gfc_error ("Component %s at %L of type EVENT_TYPE must have a "
+ "codimension or be a subcomponent of a coarray, "
+ "which is not possible as the component has the "
+ "pointer attribute", c->name, &c->loc);
+ else if (pointer && !coarray && c->ts.type == BT_DERIVED
+ && c->ts.u.derived->attr.event_comp)
+ gfc_error ("Pointer component %s at %L has a noncoarray subcomponent "
+ "of type EVENT_TYPE, which must have a codimension or be a "
+ "subcomponent of a coarray", c->name, &c->loc);
+
+ if (event_type && allocatable && !coarray)
+ gfc_error ("Allocatable component %s at %L of type EVENT_TYPE must have "
+ "a codimension", c->name, &c->loc);
+ else if (event_type && allocatable && c->ts.type == BT_DERIVED
+ && c->ts.u.derived->attr.event_comp)
+ gfc_error ("Allocatable component %s at %L must have a codimension as "
+ "it has a noncoarray subcomponent of type EVENT_TYPE",
+ c->name, &c->loc);
+
+ if (sym->attr.coarray_comp && !coarray && event_type)
+ gfc_error ("Noncoarray component %s at %L of type EVENT_TYPE or with "
+ "subcomponent of type EVENT_TYPE must have a codimension or "
+ "be a subcomponent of a coarray. (Variables of type %s may "
+ "not have a codimension as already a coarray "
+ "subcomponent exists)", c->name, &c->loc, sym->name);
+
+ if (sym->attr.event_comp && coarray && !event_type)
+ gfc_error ("Noncoarray component %s at %L of type EVENT_TYPE or with "
+ "subcomponent of type EVENT_TYPE must have a codimension or "
+ "be a subcomponent of a coarray. (Variables of type %s may "
+ "not have a codimension as %s at %L has a codimension or a "
+ "coarray subcomponent)", event_comp->name, &event_comp->loc,
+ sym->name, c->name, &c->loc);
+
/* Look for private components. */
if (sym->component_access == ACCESS_PRIVATE
|| c->attr.access == ACCESS_PRIVATE
diff --git a/gcc/fortran/resolve.c b/gcc/fortran/resolve.c
index febf0fa28d6..6598855f81a 100644
--- a/gcc/fortran/resolve.c
+++ b/gcc/fortran/resolve.c
@@ -7055,6 +7055,21 @@ resolve_allocate_expr (gfc_expr *e, gfc_code *code, bool *array_alloc_wo_spec)
&code->expr3->where, &e->where);
goto failure;
}
+
+ /* Check TS18508, C702/C703. */
+ if (code->expr3->ts.type == BT_DERIVED
+ && ((codimension && gfc_expr_attr (code->expr3).event_comp)
+ || (code->expr3->ts.u.derived->from_intmod
+ == INTMOD_ISO_FORTRAN_ENV
+ && code->expr3->ts.u.derived->intmod_sym_id
+ == ISOFORTRAN_EVENT_TYPE)))
+ {
+ gfc_error ("The source-expr at %L shall neither be of type "
+ "EVENT_TYPE nor have a EVENT_TYPE component if "
+ "allocate-object at %L is a coarray",
+ &code->expr3->where, &e->where);
+ goto failure;
+ }
}
/* Check F08:C629. */
@@ -7106,6 +7121,13 @@ resolve_allocate_expr (gfc_expr *e, gfc_code *code, bool *array_alloc_wo_spec)
no SOURCE exists by setting expr3. */
code->expr3 = gfc_default_initializer (&code->ext.alloc.ts);
}
+ else if (flag_coarray != GFC_FCOARRAY_LIB && e->ts.type == BT_DERIVED
+ && e->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && e->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ {
+ /* We have to zero initialize the integer variable. */
+ code->expr3 = gfc_get_int_expr (gfc_default_integer_kind, &e->where, 0);
+ }
else if (!code->expr3)
{
/* Set up default initializer if needed. */
@@ -8706,21 +8728,40 @@ find_reachable_labels (gfc_code *block)
static void
-resolve_lock_unlock (gfc_code *code)
+resolve_lock_unlock_event (gfc_code *code)
{
if (code->expr1->expr_type == EXPR_FUNCTION
&& code->expr1->value.function.isym
&& code->expr1->value.function.isym->id == GFC_ISYM_CAF_GET)
remove_caf_get_intrinsic (code->expr1);
- if (code->expr1->ts.type != BT_DERIVED
- || code->expr1->expr_type != EXPR_VARIABLE
- || code->expr1->ts.u.derived->from_intmod != INTMOD_ISO_FORTRAN_ENV
- || code->expr1->ts.u.derived->intmod_sym_id != ISOFORTRAN_LOCK_TYPE
- || code->expr1->rank != 0
- || (!gfc_is_coarray (code->expr1) && !gfc_is_coindexed (code->expr1)))
+ if ((code->op == EXEC_LOCK || code->op == EXEC_UNLOCK)
+ && (code->expr1->ts.type != BT_DERIVED
+ || code->expr1->expr_type != EXPR_VARIABLE
+ || code->expr1->ts.u.derived->from_intmod != INTMOD_ISO_FORTRAN_ENV
+ || code->expr1->ts.u.derived->intmod_sym_id != ISOFORTRAN_LOCK_TYPE
+ || code->expr1->rank != 0
+ || (!gfc_is_coarray (code->expr1) &&
+ !gfc_is_coindexed (code->expr1))))
gfc_error ("Lock variable at %L must be a scalar of type LOCK_TYPE",
&code->expr1->where);
+ else if ((code->op == EXEC_EVENT_POST && code->op == EXEC_EVENT_WAIT)
+ && (code->expr1->ts.type != BT_DERIVED
+ || code->expr1->expr_type != EXPR_VARIABLE
+ || code->expr1->ts.u.derived->from_intmod
+ != INTMOD_ISO_FORTRAN_ENV
+ || code->expr1->ts.u.derived->intmod_sym_id
+ != ISOFORTRAN_EVENT_TYPE
+ || code->expr1->rank != 0))
+ gfc_error ("Event variable at %L must be a scalar of type EVENT_TYPE",
+ &code->expr1->where);
+ else if (code->op == EXEC_EVENT_POST && !gfc_is_coarray (code->expr1)
+ && !gfc_is_coindexed (code->expr1))
+ gfc_error ("Event variable argument at %L must be a coarray or coindexed",
+ &code->expr1->where);
+ else if (code->op == EXEC_EVENT_WAIT && !gfc_is_coarray (code->expr1))
+ gfc_error ("Event variable argument at %L must be a coarray but not "
+ "coindexed", &code->expr1->where);
/* Check STAT. */
if (code->expr2
@@ -8746,17 +8787,23 @@ resolve_lock_unlock (gfc_code *code)
_("ERRMSG variable")))
return;
- /* Check ACQUIRED_LOCK. */
- if (code->expr4
+ /* Check for LOCK the ACQUIRED_LOCK. */
+ if (code->op != EXEC_EVENT_WAIT && code->expr4
&& (code->expr4->ts.type != BT_LOGICAL || code->expr4->rank != 0
|| code->expr4->expr_type != EXPR_VARIABLE))
gfc_error ("ACQUIRED_LOCK= argument at %L must be a scalar LOGICAL "
"variable", &code->expr4->where);
- if (code->expr4
+ if (code->op != EXEC_EVENT_WAIT && code->expr4
&& !gfc_check_vardef_context (code->expr4, false, false, false,
_("ACQUIRED_LOCK variable")))
return;
+
+ /* Check for EVENT WAIT the UNTIL_COUNT. */
+ if (code->op == EXEC_EVENT_WAIT && code->expr4
+ && (code->expr4->ts.type != BT_INTEGER || code->expr4->rank != 0))
+ gfc_error ("UNTIL_COUNT= argument at %L must be a scalar INTEGER "
+ "expression", &code->expr4->where);
}
@@ -10403,7 +10450,9 @@ start:
case EXEC_LOCK:
case EXEC_UNLOCK:
- resolve_lock_unlock (code);
+ case EXEC_EVENT_POST:
+ case EXEC_EVENT_WAIT:
+ resolve_lock_unlock_event (code);
break;
case EXEC_ENTRY:
@@ -14001,6 +14050,19 @@ resolve_symbol (gfc_symbol *sym)
return;
}
+ /* TS18508, C702/C703. */
+ if (sym->ts.type == BT_DERIVED
+ && ((sym->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && sym->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ || sym->ts.u.derived->attr.event_comp)
+ && !sym->attr.codimension && !sym->ts.u.derived->attr.coarray_comp)
+ {
+ gfc_error ("Variable %s at %L of type EVENT_TYPE or with subcomponent of "
+ "type LOCK_TYPE must be a coarray", sym->name,
+ &sym->declared_at);
+ return;
+ }
+
/* An assumed-size array with INTENT(OUT) shall not be of a type for which
default initialization is defined (5.1.2.4.4). */
if (sym->ts.type == BT_DERIVED
@@ -14030,6 +14092,15 @@ resolve_symbol (gfc_symbol *sym)
return;
}
+ /* TS18508. */
+ if (sym->ts.type == BT_DERIVED && sym->attr.dummy
+ && sym->attr.intent == INTENT_OUT && sym->attr.event_comp)
+ {
+ gfc_error ("Dummy argument %qs at %L of EVENT_TYPE shall not be "
+ "INTENT(OUT)", sym->name, &sym->declared_at);
+ return;
+ }
+
/* F2008, C525. */
if ((((sym->ts.type == BT_DERIVED && sym->ts.u.derived->attr.coarray_comp)
|| (sym->ts.type == BT_CLASS && sym->attr.class_ok
diff --git a/gcc/fortran/st.c b/gcc/fortran/st.c
index 566150b1cc2..573385f5238 100644
--- a/gcc/fortran/st.c
+++ b/gcc/fortran/st.c
@@ -118,6 +118,8 @@ gfc_free_statement (gfc_code *p)
case EXEC_SYNC_MEMORY:
case EXEC_LOCK:
case EXEC_UNLOCK:
+ case EXEC_EVENT_POST:
+ case EXEC_EVENT_WAIT:
break;
case EXEC_BLOCK:
diff --git a/gcc/fortran/trans-decl.c b/gcc/fortran/trans-decl.c
index 331b43da413..8c4fa03629b 100644
--- a/gcc/fortran/trans-decl.c
+++ b/gcc/fortran/trans-decl.c
@@ -145,6 +145,9 @@ tree gfor_fndecl_caf_atomic_cas;
tree gfor_fndecl_caf_atomic_op;
tree gfor_fndecl_caf_lock;
tree gfor_fndecl_caf_unlock;
+tree gfor_fndecl_caf_event_post;
+tree gfor_fndecl_caf_event_wait;
+tree gfor_fndecl_caf_event_query;
tree gfor_fndecl_co_broadcast;
tree gfor_fndecl_co_max;
tree gfor_fndecl_co_min;
@@ -3559,6 +3562,21 @@ gfc_build_builtin_function_decls (void)
void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
pint_type, pchar_type_node, integer_type_node);
+ gfor_fndecl_caf_event_post = gfc_build_library_function_decl_with_spec (
+ get_identifier (PREFIX("caf_event_post")), "R..WW",
+ void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
+ pint_type, pchar_type_node, integer_type_node);
+
+ gfor_fndecl_caf_event_wait = gfc_build_library_function_decl_with_spec (
+ get_identifier (PREFIX("caf_event_wait")), "R..WW",
+ void_type_node, 6, pvoid_type_node, size_type_node, integer_type_node,
+ pint_type, pchar_type_node, integer_type_node);
+
+ gfor_fndecl_caf_event_query = gfc_build_library_function_decl_with_spec (
+ get_identifier (PREFIX("caf_event_query")), "R..WW",
+ void_type_node, 5, pvoid_type_node, size_type_node, integer_type_node,
+ pint_type, pint_type);
+
gfor_fndecl_co_broadcast = gfc_build_library_function_decl_with_spec (
get_identifier (PREFIX("caf_co_broadcast")), "W.WW",
void_type_node, 5, pvoid_type_node, integer_type_node,
@@ -4854,7 +4872,7 @@ static void
generate_coarray_sym_init (gfc_symbol *sym)
{
tree tmp, size, decl, token;
- bool is_lock_type;
+ bool is_lock_type, is_event_type;
int reg_type;
if (sym->attr.dummy || sym->attr.allocatable || !sym->attr.codimension
@@ -4870,13 +4888,17 @@ generate_coarray_sym_init (gfc_symbol *sym)
&& sym->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
&& sym->ts.u.derived->intmod_sym_id == ISOFORTRAN_LOCK_TYPE;
+ is_event_type = sym->ts.type == BT_DERIVED
+ && sym->ts.u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && sym->ts.u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE;
+
/* FIXME: Workaround for PR middle-end/49106, cf. also PR middle-end/49108
to make sure the variable is not optimized away. */
DECL_PRESERVE_P (DECL_CONTEXT (decl)) = 1;
/* For lock types, we pass the array size as only the library knows the
size of the variable. */
- if (is_lock_type)
+ if (is_lock_type || is_event_type)
size = gfc_index_one_node;
else
size = TYPE_SIZE_UNIT (gfc_get_element_type (TREE_TYPE (decl)));
@@ -4898,6 +4920,8 @@ generate_coarray_sym_init (gfc_symbol *sym)
GFC_TYPE_ARRAY_CAF_TOKEN (TREE_TYPE(decl)));
if (is_lock_type)
reg_type = sym->attr.artificial ? GFC_CAF_CRITICAL : GFC_CAF_LOCK_STATIC;
+ else if (is_event_type)
+ reg_type = GFC_CAF_EVENT_STATIC;
else
reg_type = GFC_CAF_COARRAY_STATIC;
tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_register, 6, size,
diff --git a/gcc/fortran/trans-expr.c b/gcc/fortran/trans-expr.c
index 6647a4ec404..22195e09887 100644
--- a/gcc/fortran/trans-expr.c
+++ b/gcc/fortran/trans-expr.c
@@ -5784,8 +5784,9 @@ gfc_conv_procedure_call (gfc_se * se, gfc_symbol * sym,
len = cl.backend_decl;
}
- byref = (comp && (comp->attr.dimension || comp->ts.type == BT_CHARACTER))
- || (!comp && gfc_return_by_reference (sym));
+ byref = (comp && (comp->attr.dimension
+ || (comp->ts.type == BT_CHARACTER && !sym->attr.is_bind_c)))
+ || (!comp && gfc_return_by_reference (sym));
if (byref)
{
if (se->direct_byref)
@@ -6611,6 +6612,11 @@ gfc_conv_initializer (gfc_expr * expr, gfc_typespec * ts, tree type,
{
gfc_se se;
+ if (flag_coarray != GFC_FCOARRAY_LIB && ts->type == BT_DERIVED
+ && ts->u.derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && ts->u.derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ return build_constructor (type, NULL);
+
if (!(expr || pointer || procptr))
return NULL_TREE;
diff --git a/gcc/fortran/trans-intrinsic.c b/gcc/fortran/trans-intrinsic.c
index 1dabc26b010..21efe4412bd 100644
--- a/gcc/fortran/trans-intrinsic.c
+++ b/gcc/fortran/trans-intrinsic.c
@@ -9291,6 +9291,154 @@ conv_intrinsic_atomic_cas (gfc_code *code)
return gfc_finish_block (&block);
}
+static tree
+conv_intrinsic_event_query (gfc_code *code)
+{
+ gfc_se se, argse;
+ tree stat = NULL_TREE, stat2 = NULL_TREE;
+ tree count = NULL_TREE, count2 = NULL_TREE;
+
+ gfc_expr *event_expr = code->ext.actual->expr;
+
+ if (code->ext.actual->next->next->expr)
+ {
+ gcc_assert (code->ext.actual->next->next->expr->expr_type
+ == EXPR_VARIABLE);
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->ext.actual->next->next->expr);
+ stat = argse.expr;
+ }
+ else if (flag_coarray == GFC_FCOARRAY_LIB)
+ stat = null_pointer_node;
+
+ if (code->ext.actual->next->expr)
+ {
+ gcc_assert (code->ext.actual->next->expr->expr_type == EXPR_VARIABLE);
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->ext.actual->next->expr);
+ count = argse.expr;
+ }
+
+ gfc_start_block (&se.pre);
+ if (flag_coarray == GFC_FCOARRAY_LIB)
+ {
+ tree tmp, token, image_index;
+ tree index = size_zero_node;
+
+ if (event_expr->expr_type == EXPR_FUNCTION
+ && event_expr->value.function.isym
+ && event_expr->value.function.isym->id == GFC_ISYM_CAF_GET)
+ event_expr = event_expr->value.function.actual->expr;
+
+ tree caf_decl = gfc_get_tree_for_caf_expr (event_expr);
+
+ if (event_expr->symtree->n.sym->ts.type != BT_DERIVED
+ || event_expr->symtree->n.sym->ts.u.derived->from_intmod
+ != INTMOD_ISO_FORTRAN_ENV
+ || event_expr->symtree->n.sym->ts.u.derived->intmod_sym_id
+ != ISOFORTRAN_EVENT_TYPE)
+ {
+ gfc_error ("Sorry, the event component of derived type at %L is not "
+ "yet supported", &event_expr->where);
+ return NULL_TREE;
+ }
+
+ if (gfc_is_coindexed (event_expr))
+ {
+ gfc_error ("The event variable at %L shall not be coindexed ",
+ &event_expr->where);
+ return NULL_TREE;
+ }
+
+ image_index = integer_zero_node;
+
+ gfc_get_caf_token_offset (&token, NULL, caf_decl, NULL_TREE, event_expr);
+
+ /* For arrays, obtain the array index. */
+ if (gfc_expr_attr (event_expr).dimension)
+ {
+ tree desc, tmp, extent, lbound, ubound;
+ gfc_array_ref *ar, ar2;
+ int i;
+
+ /* TODO: Extend this, once DT components are supported. */
+ ar = &event_expr->ref->u.ar;
+ ar2 = *ar;
+ memset (ar, '\0', sizeof (*ar));
+ ar->as = ar2.as;
+ ar->type = AR_FULL;
+
+ gfc_init_se (&argse, NULL);
+ argse.descriptor_only = 1;
+ gfc_conv_expr_descriptor (&argse, event_expr);
+ gfc_add_block_to_block (&se.pre, &argse.pre);
+ desc = argse.expr;
+ *ar = ar2;
+
+ extent = integer_one_node;
+ for (i = 0; i < ar->dimen; i++)
+ {
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_type (&argse, ar->start[i], integer_type_node);
+ gfc_add_block_to_block (&argse.pre, &argse.pre);
+ lbound = gfc_conv_descriptor_lbound_get (desc, gfc_rank_cst[i]);
+ tmp = fold_build2_loc (input_location, MINUS_EXPR,
+ integer_type_node, argse.expr,
+ fold_convert(integer_type_node, lbound));
+ tmp = fold_build2_loc (input_location, MULT_EXPR,
+ integer_type_node, extent, tmp);
+ index = fold_build2_loc (input_location, PLUS_EXPR,
+ integer_type_node, index, tmp);
+ if (i < ar->dimen - 1)
+ {
+ ubound = gfc_conv_descriptor_ubound_get (desc, gfc_rank_cst[i]);
+ tmp = gfc_conv_array_extent_dim (lbound, ubound, NULL);
+ tmp = fold_convert (integer_type_node, tmp);
+ extent = fold_build2_loc (input_location, MULT_EXPR,
+ integer_type_node, extent, tmp);
+ }
+ }
+ }
+
+ if (count != null_pointer_node && TREE_TYPE (count) != integer_type_node)
+ {
+ count2 = count;
+ count = gfc_create_var (integer_type_node, "count");
+ }
+
+ if (stat != null_pointer_node && TREE_TYPE (stat) != integer_type_node)
+ {
+ stat2 = stat;
+ stat = gfc_create_var (integer_type_node, "stat");
+ }
+
+ tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_event_query, 5,
+ token, index, image_index, count
+ ? gfc_build_addr_expr (NULL, count) : count,
+ stat != null_pointer_node
+ ? gfc_build_addr_expr (NULL, stat) : stat);
+ gfc_add_expr_to_block (&se.pre, tmp);
+
+ if (count2 != NULL_TREE)
+ gfc_add_modify (&se.pre, count2,
+ fold_convert (TREE_TYPE (count2), count));
+
+ if (stat2 != NULL_TREE)
+ gfc_add_modify (&se.pre, stat2,
+ fold_convert (TREE_TYPE (stat2), stat));
+
+ return gfc_finish_block (&se.pre);
+ }
+
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->ext.actual->expr);
+ gfc_add_modify (&se.pre, count, fold_convert (TREE_TYPE (count), argse.expr));
+
+ if (stat != NULL_TREE)
+ gfc_add_modify (&se.pre, stat, build_int_cst (TREE_TYPE (stat), 0));
+
+ return gfc_finish_block (&se.pre);
+}
static tree
conv_intrinsic_move_alloc (gfc_code *code)
@@ -9587,6 +9735,10 @@ gfc_conv_intrinsic_subroutine (gfc_code *code)
res = conv_intrinsic_atomic_ref (code);
break;
+ case GFC_ISYM_EVENT_QUERY:
+ res = conv_intrinsic_event_query (code);
+ break;
+
case GFC_ISYM_C_F_POINTER:
case GFC_ISYM_C_F_PROCPOINTER:
res = conv_isocbinding_subroutine (code);
diff --git a/gcc/fortran/trans-openmp.c b/gcc/fortran/trans-openmp.c
index 261291c8ef5..227964cb2f6 100644
--- a/gcc/fortran/trans-openmp.c
+++ b/gcc/fortran/trans-openmp.c
@@ -2630,28 +2630,20 @@ gfc_trans_omp_clauses (stmtblock_t *block, gfc_omp_clauses *clauses,
}
if (clauses->gang)
{
- if (clauses->gang_expr)
- {
- tree gang_var
- = gfc_convert_expr_to_tree (block, clauses->gang_expr);
- c = build_omp_clause (where.lb->location, OMP_CLAUSE_GANG);
- if (clauses->gang_static)
- OMP_CLAUSE_GANG_STATIC_EXPR (c) = gang_var;
- else
- OMP_CLAUSE_GANG_EXPR (c) = gang_var;
- omp_clauses = gfc_trans_add_clause (c, omp_clauses);
- }
- else if (clauses->gang_static)
+ tree arg;
+ c = build_omp_clause (where.lb->location, OMP_CLAUSE_GANG);
+ omp_clauses = gfc_trans_add_clause (c, omp_clauses);
+ if (clauses->gang_num_expr)
{
- /* This corresponds to gang (static: *). */
- c = build_omp_clause (where.lb->location, OMP_CLAUSE_GANG);
- OMP_CLAUSE_GANG_STATIC_EXPR (c) = integer_minus_one_node;
- omp_clauses = gfc_trans_add_clause (c, omp_clauses);
+ arg = gfc_convert_expr_to_tree (block, clauses->gang_num_expr);
+ OMP_CLAUSE_GANG_EXPR (c) = arg;
}
- else
+ if (clauses->gang_static)
{
- c = build_omp_clause (where.lb->location, OMP_CLAUSE_GANG);
- omp_clauses = gfc_trans_add_clause (c, omp_clauses);
+ arg = clauses->gang_static_expr
+ ? gfc_convert_expr_to_tree (block, clauses->gang_static_expr)
+ : integer_minus_one_node;
+ OMP_CLAUSE_GANG_STATIC_EXPR (c) = arg;
}
}
@@ -3476,8 +3468,9 @@ gfc_trans_oacc_combined_directive (gfc_code *code)
sizeof (construct_clauses));
loop_clauses.collapse = construct_clauses.collapse;
loop_clauses.gang = construct_clauses.gang;
- loop_clauses.gang_expr = construct_clauses.gang_expr;
loop_clauses.gang_static = construct_clauses.gang_static;
+ loop_clauses.gang_num_expr = construct_clauses.gang_num_expr;
+ loop_clauses.gang_static_expr = construct_clauses.gang_static_expr;
loop_clauses.vector = construct_clauses.vector;
loop_clauses.vector_expr = construct_clauses.vector_expr;
loop_clauses.worker = construct_clauses.worker;
@@ -3491,8 +3484,9 @@ gfc_trans_oacc_combined_directive (gfc_code *code)
loop_clauses.lists[OMP_LIST_REDUCTION]
= construct_clauses.lists[OMP_LIST_REDUCTION];
construct_clauses.gang = false;
- construct_clauses.gang_expr = NULL;
construct_clauses.gang_static = false;
+ construct_clauses.gang_num_expr = NULL;
+ construct_clauses.gang_static_expr = NULL;
construct_clauses.vector = false;
construct_clauses.vector_expr = NULL;
construct_clauses.worker = false;
@@ -3503,6 +3497,7 @@ gfc_trans_oacc_combined_directive (gfc_code *code)
construct_clauses.independent = false;
construct_clauses.tile_list = NULL;
construct_clauses.lists[OMP_LIST_PRIVATE] = NULL;
+ construct_clauses.lists[OMP_LIST_REDUCTION] = NULL;
oacc_clauses = gfc_trans_omp_clauses (&block, &construct_clauses,
code->loc);
}
diff --git a/gcc/fortran/trans-stmt.c b/gcc/fortran/trans-stmt.c
index 47ffd78eee6..3df483a2918 100644
--- a/gcc/fortran/trans-stmt.c
+++ b/gcc/fortran/trans-stmt.c
@@ -776,6 +776,7 @@ gfc_trans_lock_unlock (gfc_code *code, gfc_exec_op op)
if (code->expr3)
{
gfc_init_se (&argse, NULL);
+ argse.want_pointer = 1;
gfc_conv_expr (&argse, code->expr3);
gfc_add_block_to_block (&se.pre, &argse.pre);
errmsg = argse.expr;
@@ -840,6 +841,165 @@ gfc_trans_lock_unlock (gfc_code *code, gfc_exec_op op)
return gfc_finish_block (&se.pre);
}
+tree
+gfc_trans_event_post_wait (gfc_code *code, gfc_exec_op op)
+{
+ gfc_se se, argse;
+ tree stat = NULL_TREE, stat2 = NULL_TREE;
+ tree until_count = NULL_TREE;
+
+ if (code->expr2)
+ {
+ gcc_assert (code->expr2->expr_type == EXPR_VARIABLE);
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->expr2);
+ stat = argse.expr;
+ }
+ else if (flag_coarray == GFC_FCOARRAY_LIB)
+ stat = null_pointer_node;
+
+ if (code->expr4)
+ {
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->expr4);
+ until_count = fold_convert (integer_type_node, argse.expr);
+ }
+ else
+ until_count = integer_one_node;
+
+ if (flag_coarray != GFC_FCOARRAY_LIB)
+ {
+ gfc_start_block (&se.pre);
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_val (&argse, code->expr1);
+
+ if (op == EXEC_EVENT_POST)
+ gfc_add_modify (&se.pre, argse.expr,
+ fold_build2_loc (input_location, PLUS_EXPR,
+ TREE_TYPE (argse.expr), argse.expr,
+ build_int_cst (TREE_TYPE (argse.expr), 1)));
+ else
+ gfc_add_modify (&se.pre, argse.expr,
+ fold_build2_loc (input_location, MINUS_EXPR,
+ TREE_TYPE (argse.expr), argse.expr,
+ fold_convert (TREE_TYPE (argse.expr),
+ until_count)));
+ if (stat != NULL_TREE)
+ gfc_add_modify (&se.pre, stat, build_int_cst (TREE_TYPE (stat), 0));
+
+ return gfc_finish_block (&se.pre);
+ }
+
+ gfc_start_block (&se.pre);
+ tree tmp, token, image_index, errmsg, errmsg_len;
+ tree index = size_zero_node;
+ tree caf_decl = gfc_get_tree_for_caf_expr (code->expr1);
+
+ if (code->expr1->symtree->n.sym->ts.type != BT_DERIVED
+ || code->expr1->symtree->n.sym->ts.u.derived->from_intmod
+ != INTMOD_ISO_FORTRAN_ENV
+ || code->expr1->symtree->n.sym->ts.u.derived->intmod_sym_id
+ != ISOFORTRAN_EVENT_TYPE)
+ {
+ gfc_error ("Sorry, the event component of derived type at %L is not "
+ "yet supported", &code->expr1->where);
+ return NULL_TREE;
+ }
+
+ gfc_get_caf_token_offset (&token, NULL, caf_decl, NULL_TREE, code->expr1);
+
+ if (gfc_is_coindexed (code->expr1))
+ image_index = gfc_caf_get_image_index (&se.pre, code->expr1, caf_decl);
+ else
+ image_index = integer_zero_node;
+
+ /* For arrays, obtain the array index. */
+ if (gfc_expr_attr (code->expr1).dimension)
+ {
+ tree desc, tmp, extent, lbound, ubound;
+ gfc_array_ref *ar, ar2;
+ int i;
+
+ /* TODO: Extend this, once DT components are supported. */
+ ar = &code->expr1->ref->u.ar;
+ ar2 = *ar;
+ memset (ar, '\0', sizeof (*ar));
+ ar->as = ar2.as;
+ ar->type = AR_FULL;
+
+ gfc_init_se (&argse, NULL);
+ argse.descriptor_only = 1;
+ gfc_conv_expr_descriptor (&argse, code->expr1);
+ gfc_add_block_to_block (&se.pre, &argse.pre);
+ desc = argse.expr;
+ *ar = ar2;
+
+ extent = integer_one_node;
+ for (i = 0; i < ar->dimen; i++)
+ {
+ gfc_init_se (&argse, NULL);
+ gfc_conv_expr_type (&argse, ar->start[i], integer_type_node);
+ gfc_add_block_to_block (&argse.pre, &argse.pre);
+ lbound = gfc_conv_descriptor_lbound_get (desc, gfc_rank_cst[i]);
+ tmp = fold_build2_loc (input_location, MINUS_EXPR,
+ integer_type_node, argse.expr,
+ fold_convert(integer_type_node, lbound));
+ tmp = fold_build2_loc (input_location, MULT_EXPR,
+ integer_type_node, extent, tmp);
+ index = fold_build2_loc (input_location, PLUS_EXPR,
+ integer_type_node, index, tmp);
+ if (i < ar->dimen - 1)
+ {
+ ubound = gfc_conv_descriptor_ubound_get (desc, gfc_rank_cst[i]);
+ tmp = gfc_conv_array_extent_dim (lbound, ubound, NULL);
+ tmp = fold_convert (integer_type_node, tmp);
+ extent = fold_build2_loc (input_location, MULT_EXPR,
+ integer_type_node, extent, tmp);
+ }
+ }
+ }
+
+ /* errmsg. */
+ if (code->expr3)
+ {
+ gfc_init_se (&argse, NULL);
+ argse.want_pointer = 1;
+ gfc_conv_expr (&argse, code->expr3);
+ gfc_add_block_to_block (&se.pre, &argse.pre);
+ errmsg = argse.expr;
+ errmsg_len = fold_convert (integer_type_node, argse.string_length);
+ }
+ else
+ {
+ errmsg = null_pointer_node;
+ errmsg_len = integer_zero_node;
+ }
+
+ if (stat != null_pointer_node && TREE_TYPE (stat) != integer_type_node)
+ {
+ stat2 = stat;
+ stat = gfc_create_var (integer_type_node, "stat");
+ }
+
+ if (op == EXEC_EVENT_POST)
+ tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_event_post, 6,
+ token, index, image_index,
+ stat != null_pointer_node
+ ? gfc_build_addr_expr (NULL, stat) : stat,
+ errmsg, errmsg_len);
+ else
+ tmp = build_call_expr_loc (input_location, gfor_fndecl_caf_event_wait, 6,
+ token, index, until_count,
+ stat != null_pointer_node
+ ? gfc_build_addr_expr (NULL, stat) : stat,
+ errmsg, errmsg_len);
+ gfc_add_expr_to_block (&se.pre, tmp);
+
+ if (stat2 != NULL_TREE)
+ gfc_add_modify (&se.pre, stat2, fold_convert (TREE_TYPE (stat2), stat));
+
+ return gfc_finish_block (&se.pre);
+}
tree
gfc_trans_sync (gfc_code *code, gfc_exec_op type)
@@ -879,6 +1039,7 @@ gfc_trans_sync (gfc_code *code, gfc_exec_op type)
{
gcc_assert (code->expr3->expr_type == EXPR_VARIABLE);
gfc_init_se (&argse, NULL);
+ argse.want_pointer = 1;
gfc_conv_expr (&argse, code->expr3);
gfc_conv_string_parameter (&argse);
errmsg = gfc_build_addr_expr (NULL, argse.expr);
diff --git a/gcc/fortran/trans-stmt.h b/gcc/fortran/trans-stmt.h
index 0ff93c49033..76f1f28f27c 100644
--- a/gcc/fortran/trans-stmt.h
+++ b/gcc/fortran/trans-stmt.h
@@ -55,6 +55,7 @@ tree gfc_trans_do_while (gfc_code *);
tree gfc_trans_select (gfc_code *);
tree gfc_trans_sync (gfc_code *, gfc_exec_op);
tree gfc_trans_lock_unlock (gfc_code *, gfc_exec_op);
+tree gfc_trans_event_post_wait (gfc_code *, gfc_exec_op);
tree gfc_trans_forall (gfc_code *);
tree gfc_trans_where (gfc_code *);
tree gfc_trans_allocate (gfc_code *);
diff --git a/gcc/fortran/trans-types.c b/gcc/fortran/trans-types.c
index 6e2b3f1a615..60bd8e1b982 100644
--- a/gcc/fortran/trans-types.c
+++ b/gcc/fortran/trans-types.c
@@ -2371,6 +2371,11 @@ gfc_get_derived_type (gfc_symbol * derived)
&& derived->intmod_sym_id == ISOFORTRAN_LOCK_TYPE))
return ptr_type_node;
+ if (flag_coarray != GFC_FCOARRAY_LIB
+ && derived->from_intmod == INTMOD_ISO_FORTRAN_ENV
+ && derived->intmod_sym_id == ISOFORTRAN_EVENT_TYPE)
+ return gfc_get_int_type (gfc_default_integer_kind);
+
if (derived && derived->attr.flavor == FL_PROCEDURE
&& derived->attr.generic)
derived = gfc_find_dt_in_generic (derived);
diff --git a/gcc/fortran/trans.c b/gcc/fortran/trans.c
index 2a91c3521b6..001db41ca83 100644
--- a/gcc/fortran/trans.c
+++ b/gcc/fortran/trans.c
@@ -711,7 +711,7 @@ gfc_allocate_using_malloc (stmtblock_t * block, tree pointer,
static void
gfc_allocate_using_lib (stmtblock_t * block, tree pointer, tree size,
tree token, tree status, tree errmsg, tree errlen,
- bool lock_var)
+ bool lock_var, bool event_var)
{
tree tmp, pstat;
@@ -738,7 +738,8 @@ gfc_allocate_using_lib (stmtblock_t * block, tree pointer, tree size,
build_int_cst (size_type_node, 1)),
build_int_cst (integer_type_node,
lock_var ? GFC_CAF_LOCK_ALLOC
- : GFC_CAF_COARRAY_ALLOC),
+ : event_var ? GFC_CAF_EVENT_ALLOC
+ : GFC_CAF_COARRAY_ALLOC),
token, pstat, errmsg, errlen);
tmp = fold_build2_loc (input_location, MODIFY_EXPR,
@@ -798,6 +799,11 @@ gfc_allocate_allocatable (stmtblock_t * block, tree mem, tree size, tree token,
== INTMOD_ISO_FORTRAN_ENV
&& expr->ts.u.derived->intmod_sym_id
== ISOFORTRAN_LOCK_TYPE;
+ bool event_var = expr->ts.type == BT_DERIVED
+ && expr->ts.u.derived->from_intmod
+ == INTMOD_ISO_FORTRAN_ENV
+ && expr->ts.u.derived->intmod_sym_id
+ == ISOFORTRAN_EVENT_TYPE;
/* In the front end, we represent the lock variable as pointer. However,
the FE only passes the pointer around and leaves the actual
representation to the library. Hence, we have to convert back to the
@@ -807,7 +813,7 @@ gfc_allocate_allocatable (stmtblock_t * block, tree mem, tree size, tree token,
size, TYPE_SIZE_UNIT (ptr_type_node));
gfc_allocate_using_lib (&alloc_block, mem, size, token, status,
- errmsg, errlen, lock_var);
+ errmsg, errlen, lock_var, event_var);
if (status != NULL_TREE)
{
@@ -1797,6 +1803,11 @@ trans_code (gfc_code * code, tree cond)
res = gfc_trans_lock_unlock (code, code->op);
break;
+ case EXEC_EVENT_POST:
+ case EXEC_EVENT_WAIT:
+ res = gfc_trans_event_post_wait (code, code->op);
+ break;
+
case EXEC_FORALL:
res = gfc_trans_forall (code);
break;
diff --git a/gcc/fortran/trans.h b/gcc/fortran/trans.h
index 3a23a3cc259..088eca376b5 100644
--- a/gcc/fortran/trans.h
+++ b/gcc/fortran/trans.h
@@ -113,7 +113,9 @@ enum gfc_coarray_type
GFC_CAF_COARRAY_ALLOC,
GFC_CAF_LOCK_STATIC,
GFC_CAF_LOCK_ALLOC,
- GFC_CAF_CRITICAL
+ GFC_CAF_CRITICAL,
+ GFC_CAF_EVENT_STATIC,
+ GFC_CAF_EVENT_ALLOC
};
@@ -763,6 +765,9 @@ extern GTY(()) tree gfor_fndecl_caf_atomic_cas;
extern GTY(()) tree gfor_fndecl_caf_atomic_op;
extern GTY(()) tree gfor_fndecl_caf_lock;
extern GTY(()) tree gfor_fndecl_caf_unlock;
+extern GTY(()) tree gfor_fndecl_caf_event_post;
+extern GTY(()) tree gfor_fndecl_caf_event_wait;
+extern GTY(()) tree gfor_fndecl_caf_event_query;
extern GTY(()) tree gfor_fndecl_co_broadcast;
extern GTY(()) tree gfor_fndecl_co_max;
extern GTY(()) tree gfor_fndecl_co_min;
diff --git a/gcc/function.c b/gcc/function.c
index 515d7c04220..e4528655917 100644
--- a/gcc/function.c
+++ b/gcc/function.c
@@ -75,6 +75,7 @@ along with GCC; see the file COPYING3. If not see
#include "tree-chkp.h"
#include "rtl-chkp.h"
#include "tree-dfa.h"
+#include "tree-ssa.h"
/* So we can assign to cfun in this file. */
#undef cfun
@@ -4798,6 +4799,7 @@ set_cfun (struct function *new_cfun)
{
cfun = new_cfun;
invoke_set_current_function_hook (new_cfun ? new_cfun->decl : NULL_TREE);
+ redirect_edge_var_map_empty ();
}
}
diff --git a/gcc/genemit.c b/gcc/genemit.c
index e92f75750ec..cd85a809ae1 100644
--- a/gcc/genemit.c
+++ b/gcc/genemit.c
@@ -51,6 +51,8 @@ struct clobber_ent
static void output_peephole2_scratches (rtx);
+/* True for <X>_optab if that optab isn't allowed to fail. */
+static bool nofail_optabs[NUM_OPTABS];
static void
print_code (RTX_CODE code)
@@ -285,6 +287,28 @@ gen_emit_seq (rtvec vec, char *used)
}
}
+/* Emit the given C code to the output file. The code is allowed to
+ fail if CAN_FAIL_P. NAME describes what we're generating,
+ for use in error messages. */
+
+static void
+emit_c_code (const char *code, bool can_fail_p, const char *name)
+{
+ if (can_fail_p)
+ printf ("#define FAIL return (end_sequence (), _val)\n");
+ else
+ printf ("#define FAIL _Pragma (\"GCC error \\\"%s cannot FAIL\\\"\")"
+ " (void)0\n", name);
+ printf ("#define DONE return (_val = get_insns (),"
+ "end_sequence (), _val)\n");
+
+ print_md_ptr_loc (code);
+ printf ("%s\n", code);
+
+ printf ("#undef DONE\n");
+ printf ("#undef FAIL\n");
+}
+
/* Generate the `gen_...' function for a DEFINE_INSN. */
static void
@@ -478,8 +502,15 @@ gen_expand (md_rtx_info *info)
/* Output the special code to be executed before the sequence
is generated. */
- print_md_ptr_loc (XSTR (expand, 3));
- printf ("%s\n", XSTR (expand, 3));
+ optab_pattern p;
+ bool can_fail_p = true;
+ if (find_optab (&p, XSTR (expand, 0)))
+ {
+ gcc_assert (p.op < NUM_OPTABS);
+ if (nofail_optabs[p.op])
+ can_fail_p = false;
+ }
+ emit_c_code (XSTR (expand, 3), can_fail_p, XSTR (expand, 0));
/* Output code to copy the arguments back out of `operands'
(unless we aren't going to use them at all). */
@@ -569,10 +600,7 @@ gen_split (md_rtx_info *info)
before the actual construction. */
if (XSTR (split, 3))
- {
- print_md_ptr_loc (XSTR (split, 3));
- printf ("%s\n", XSTR (split, 3));
- }
+ emit_c_code (XSTR (split, 3), true, name);
/* Output code to copy the arguments back out of `operands' */
for (i = 0; i < stats.num_operand_vars; i++)
@@ -724,6 +752,10 @@ main (int argc, char **argv)
if (!init_rtx_reader_args (argc, argv))
return (FATAL_EXIT_CODE);
+#define DEF_INTERNAL_OPTAB_FN(NAME, FLAGS, OPTAB, TYPE) \
+ nofail_optabs[OPTAB##_optab] = true;
+#include "internal-fn.def"
+
/* Assign sequential codes to all entries in the machine description
in parallel with the tables in insn-output.c. */
@@ -764,8 +796,6 @@ from the machine description file `md'. */\n\n");
printf ("#include \"ggc.h\"\n");
printf ("#include \"dumpfile.h\"\n");
printf ("#include \"target.h\"\n\n");
- printf ("#define FAIL return (end_sequence (), _val)\n");
- printf ("#define DONE return (_val = get_insns (), end_sequence (), _val)\n\n");
/* Read the machine description. */
diff --git a/gcc/genmatch.c b/gcc/genmatch.c
index 67d1c66a61f..ef39cb0f32b 100644
--- a/gcc/genmatch.c
+++ b/gcc/genmatch.c
@@ -1851,7 +1851,8 @@ struct capture_info
bool force_single_use;
bool cond_expr_cond_p;
unsigned long toplevel_msk;
- int result_use_count;
+ unsigned match_use_count;
+ unsigned result_use_count;
unsigned same_as;
capture *c;
};
@@ -1901,6 +1902,7 @@ capture_info::walk_match (operand *o, unsigned toplevel_arg,
if (capture *c = dyn_cast <capture *> (o))
{
unsigned where = c->where;
+ info[where].match_use_count++;
info[where].toplevel_msk |= 1 << toplevel_arg;
info[where].force_no_side_effects_p |= conditional_p;
info[where].cond_expr_cond_p |= cond_expr_cond_p;
@@ -3106,16 +3108,19 @@ dt_simplify::gen_1 (FILE *f, int indent, bool gimple, operand *result)
else if (is_a <predicate_id *> (opr))
is_predicate = true;
/* Search for captures used multiple times in the result expression
- and dependent on TREE_SIDE_EFFECTS emit a SAVE_EXPR. */
+ and wrap them in a SAVE_EXPR. Allow as many uses as in the
+ original expression. */
if (!is_predicate)
for (int i = 0; i < s->capture_max + 1; ++i)
{
- if (cinfo.info[i].same_as != (unsigned)i)
+ if (cinfo.info[i].same_as != (unsigned)i
+ || cinfo.info[i].cse_p)
continue;
- if (cinfo.info[i].result_use_count > 1)
+ if (cinfo.info[i].result_use_count
+ > cinfo.info[i].match_use_count)
fprintf_indent (f, indent,
- "captures[%d] = save_expr (captures[%d]);\n",
- i, i);
+ "if (! tree_invariant_p (captures[%d])) "
+ "return NULL_TREE;\n", i);
}
for (unsigned j = 0; j < e->ops.length (); ++j)
{
diff --git a/gcc/genopinit.c b/gcc/genopinit.c
index 167815d561d..3b91112e9ec 100644
--- a/gcc/genopinit.c
+++ b/gcc/genopinit.c
@@ -35,246 +35,22 @@ static const char * const rtx_upname[] = {
#undef DEF_RTL_EXPR
-
-/* The entries in optabs.def are categorized:
- C: A "conversion" optab, which uses two modes; has libcall data.
- N: A "normal" optab, which uses one mode; has libcall data.
- D: A "direct" optab, which uses one mode; does not have libcall data.
- V: An "oVerflow" optab. Like N, but does not record its code in
- code_to_optab.
-
- CX, NX, VX: An extra pattern entry for a conversion or normal optab.
-
- These patterns may be present in the MD file with names that contain
- the mode(s) used and the name of the operation. This array contains
- a list of optabs that need to be initialized. Within each name,
- $a and $b are used to match a short mode name (the part of the mode
- name not including `mode' and converted to lower-case).
-
- $I means that only full integer modes should be considered for the
- next mode, and $F means that only float modes should be considered.
- $P means that both full and partial integer modes should be considered.
- $Q means that only fixed-point modes should be considered.
-
- The pattern may be NULL if the optab exists only for the libcalls
- that we plan to attach to it, and there are no named patterns in
- the md files. */
-
-#define OPTAB_CL(name, pat, c, b, l) name,
-#define OPTAB_CX(name, pat)
-#define OPTAB_CD(name, pat) name,
-#define OPTAB_NL(name, pat, c, b, s, l) name,
-#define OPTAB_NC(name, pat, c) name,
-#define OPTAB_NX(name, pat)
-#define OPTAB_VL(name, pat, c, b, s, l) name,
-#define OPTAB_VC(name, pat, c) name,
-#define OPTAB_VX(name, pat)
-#define OPTAB_DC(name, pat, c) name,
-#define OPTAB_D(name, pat) name,
-
-typedef enum optab_tag {
- unknown_optab,
-#include "optabs.def"
- NUM_OPTABS
-} optab;
-
-#undef OPTAB_CL
-#undef OPTAB_CX
-#undef OPTAB_CD
-#undef OPTAB_NL
-#undef OPTAB_NC
-#undef OPTAB_NX
-#undef OPTAB_VL
-#undef OPTAB_VC
-#undef OPTAB_VX
-#undef OPTAB_DC
-#undef OPTAB_D
-
-#define NS "NULL"
-#define ZS "'\\0'"
-#define OPTAB_CL(o, p, c, b, l) { #o, p, #b, ZS, #l, o, c, UNKNOWN, 1 },
-#define OPTAB_CX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 1 },
-#define OPTAB_CD(o, p) { #o, p, NS, ZS, NS, o, UNKNOWN, UNKNOWN, 2 },
-#define OPTAB_NL(o, p, c, b, s, l) { #o, p, #b, #s, #l, o, c, c, 3 },
-#define OPTAB_NC(o, p, c) { #o, p, NS, ZS, NS, o, c, c, 3 },
-#define OPTAB_NX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 3 },
-#define OPTAB_VL(o, p, c, b, s, l) { #o, p, #b, #s, #l, o, c, UNKNOWN, 3 },
-#define OPTAB_VC(o, p, c) { #o, p, NS, ZS, NS, o, c, UNKNOWN, 3 },
-#define OPTAB_VX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 3 },
-#define OPTAB_DC(o, p, c) { #o, p, NS, ZS, NS, o, c, c, 4 },
-#define OPTAB_D(o, p) { #o, p, NS, ZS, NS, o, UNKNOWN, UNKNOWN, 4 },
-
-struct optab_def
-{
- const char *name;
- const char *pattern;
- const char *base;
- const char *suffix;
- const char *libcall;
- unsigned int op;
- enum rtx_code fcode;
- enum rtx_code rcode;
- unsigned int kind;
-};
-
-static optab_def optabs[] = {
- { "unknown_optab", NULL, NS, ZS, NS, unknown_optab, UNKNOWN, UNKNOWN, 0 },
-#include "optabs.def"
-};
-
-#undef OPTAB_CL
-#undef OPTAB_CX
-#undef OPTAB_CD
-#undef OPTAB_NL
-#undef OPTAB_NC
-#undef OPTAB_NX
-#undef OPTAB_VL
-#undef OPTAB_VC
-#undef OPTAB_VX
-#undef OPTAB_DC
-#undef OPTAB_D
-
/* Vector in which to collect insns that match. */
-
-struct pattern
-{
- const char *name;
- unsigned int op;
- unsigned int m1, m2;
- unsigned int sort_num;
-};
-
-
-static vec<pattern> patterns;
-
-static bool
-match_pattern (pattern *p, const char *name, const char *pat)
-{
- bool force_float = false;
- bool force_int = false;
- bool force_partial_int = false;
- bool force_fixed = false;
-
- if (pat == NULL)
- return false;
- for (; ; ++pat)
- {
- if (*pat != '$')
- {
- if (*pat != *name++)
- return false;
- if (*pat == '\0')
- return true;
- continue;
- }
- switch (*++pat)
- {
- case 'I':
- force_int = 1;
- break;
- case 'P':
- force_partial_int = 1;
- break;
- case 'F':
- force_float = 1;
- break;
- case 'Q':
- force_fixed = 1;
- break;
-
- case 'a':
- case 'b':
- {
- int i;
-
- /* This loop will stop at the first prefix match, so
- look through the modes in reverse order, in case
- there are extra CC modes and CC is a prefix of the
- CC modes (as it should be). */
- for (i = (MAX_MACHINE_MODE) - 1; i >= 0; i--)
- {
- const char *p, *q;
- for (p = GET_MODE_NAME (i), q = name; *p; p++, q++)
- if (TOLOWER (*p) != *q)
- break;
- if (*p == 0
- && (! force_int || mode_class[i] == MODE_INT
- || mode_class[i] == MODE_VECTOR_INT)
- && (! force_partial_int
- || mode_class[i] == MODE_INT
- || mode_class[i] == MODE_PARTIAL_INT
- || mode_class[i] == MODE_VECTOR_INT)
- && (! force_float
- || mode_class[i] == MODE_FLOAT
- || mode_class[i] == MODE_DECIMAL_FLOAT
- || mode_class[i] == MODE_COMPLEX_FLOAT
- || mode_class[i] == MODE_VECTOR_FLOAT)
- && (! force_fixed
- || mode_class[i] == MODE_FRACT
- || mode_class[i] == MODE_UFRACT
- || mode_class[i] == MODE_ACCUM
- || mode_class[i] == MODE_UACCUM
- || mode_class[i] == MODE_VECTOR_FRACT
- || mode_class[i] == MODE_VECTOR_UFRACT
- || mode_class[i] == MODE_VECTOR_ACCUM
- || mode_class[i] == MODE_VECTOR_UACCUM))
- break;
- }
-
- if (i < 0)
- return false;
- name += strlen (GET_MODE_NAME (i));
- if (*pat == 'a')
- p->m1 = i;
- else
- p->m2 = i;
-
- force_int = false;
- force_partial_int = false;
- force_float = false;
- force_fixed = false;
- }
- break;
-
- default:
- gcc_unreachable ();
- }
- }
-}
+static vec<optab_pattern> patterns;
static void
gen_insn (md_rtx_info *info)
{
- rtx insn = info->def;
- const char *name = XSTR (insn, 0);
- pattern p;
- unsigned pindex;
-
- /* Don't mention "unnamed" instructions. */
- if (*name == 0 || *name == '*')
- return;
- p.name = name;
-
- /* See if NAME matches one of the patterns we have for the optabs
- we know about. */
- for (pindex = 0; pindex < ARRAY_SIZE (optabs); pindex++)
- {
- p.m1 = p.m2 = 0;
- if (match_pattern (&p, name, optabs[pindex].pattern))
- {
- p.op = optabs[pindex].op;
- p.sort_num = (p.op << 16) | (p.m2 << 8) | p.m1;
- patterns.safe_push (p);
- return;
- }
- }
+ optab_pattern p;
+ if (find_optab (&p, XSTR (info->def, 0)))
+ patterns.safe_push (p);
}
static int
pattern_cmp (const void *va, const void *vb)
{
- const pattern *a = (const pattern *)va;
- const pattern *b = (const pattern *)vb;
+ const optab_pattern *a = (const optab_pattern *)va;
+ const optab_pattern *b = (const optab_pattern *)vb;
return a->sort_num - b->sort_num;
}
@@ -333,7 +109,7 @@ main (int argc, char **argv)
{
FILE *h_file, *s_file;
unsigned int i, j, n, last_kind[5];
- pattern *p;
+ optab_pattern *p;
progname = "genopinit";
@@ -365,7 +141,7 @@ main (int argc, char **argv)
/* Now that we've handled the "extra" patterns, eliminate them from
the optabs array. That way they don't get in the way below. */
- n = ARRAY_SIZE (optabs);
+ n = num_optabs;
for (i = 0; i < n; )
if (optabs[i].base == NULL)
optabs[i] = optabs[--n];
diff --git a/gcc/gensupport.c b/gcc/gensupport.c
index 484ead2f3e7..7969060c117 100644
--- a/gcc/gensupport.c
+++ b/gcc/gensupport.c
@@ -3061,3 +3061,161 @@ needs_barrier_p (rtx x)
&& GET_CODE (SET_DEST (x)) == PC
&& GET_CODE (SET_SRC (x)) == LABEL_REF);
}
+
+#define NS "NULL"
+#define ZS "'\\0'"
+#define OPTAB_CL(o, p, c, b, l) { #o, p, #b, ZS, #l, o, c, UNKNOWN, 1 },
+#define OPTAB_CX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 1 },
+#define OPTAB_CD(o, p) { #o, p, NS, ZS, NS, o, UNKNOWN, UNKNOWN, 2 },
+#define OPTAB_NL(o, p, c, b, s, l) { #o, p, #b, #s, #l, o, c, c, 3 },
+#define OPTAB_NC(o, p, c) { #o, p, NS, ZS, NS, o, c, c, 3 },
+#define OPTAB_NX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 3 },
+#define OPTAB_VL(o, p, c, b, s, l) { #o, p, #b, #s, #l, o, c, UNKNOWN, 3 },
+#define OPTAB_VC(o, p, c) { #o, p, NS, ZS, NS, o, c, UNKNOWN, 3 },
+#define OPTAB_VX(o, p) { #o, p, NULL, NULL, NULL, o, UNKNOWN, UNKNOWN, 3 },
+#define OPTAB_DC(o, p, c) { #o, p, NS, ZS, NS, o, c, c, 4 },
+#define OPTAB_D(o, p) { #o, p, NS, ZS, NS, o, UNKNOWN, UNKNOWN, 4 },
+
+/* An array of all optabs. Note that the same optab can appear more
+ than once, with a different pattern. */
+optab_def optabs[] = {
+ { "unknown_optab", NULL, NS, ZS, NS, unknown_optab, UNKNOWN, UNKNOWN, 0 },
+#include "optabs.def"
+};
+
+/* The number of entries in optabs[]. */
+unsigned int num_optabs = ARRAY_SIZE (optabs);
+
+#undef OPTAB_CL
+#undef OPTAB_CX
+#undef OPTAB_CD
+#undef OPTAB_NL
+#undef OPTAB_NC
+#undef OPTAB_NX
+#undef OPTAB_VL
+#undef OPTAB_VC
+#undef OPTAB_VX
+#undef OPTAB_DC
+#undef OPTAB_D
+
+/* Return true if instruction NAME matches pattern PAT, storing information
+ about the match in P if so. */
+
+static bool
+match_pattern (optab_pattern *p, const char *name, const char *pat)
+{
+ bool force_float = false;
+ bool force_int = false;
+ bool force_partial_int = false;
+ bool force_fixed = false;
+
+ if (pat == NULL)
+ return false;
+ for (; ; ++pat)
+ {
+ if (*pat != '$')
+ {
+ if (*pat != *name++)
+ return false;
+ if (*pat == '\0')
+ return true;
+ continue;
+ }
+ switch (*++pat)
+ {
+ case 'I':
+ force_int = 1;
+ break;
+ case 'P':
+ force_partial_int = 1;
+ break;
+ case 'F':
+ force_float = 1;
+ break;
+ case 'Q':
+ force_fixed = 1;
+ break;
+
+ case 'a':
+ case 'b':
+ {
+ int i;
+
+ /* This loop will stop at the first prefix match, so
+ look through the modes in reverse order, in case
+ there are extra CC modes and CC is a prefix of the
+ CC modes (as it should be). */
+ for (i = (MAX_MACHINE_MODE) - 1; i >= 0; i--)
+ {
+ const char *p, *q;
+ for (p = GET_MODE_NAME (i), q = name; *p; p++, q++)
+ if (TOLOWER (*p) != *q)
+ break;
+ if (*p == 0
+ && (! force_int || mode_class[i] == MODE_INT
+ || mode_class[i] == MODE_VECTOR_INT)
+ && (! force_partial_int
+ || mode_class[i] == MODE_INT
+ || mode_class[i] == MODE_PARTIAL_INT
+ || mode_class[i] == MODE_VECTOR_INT)
+ && (! force_float
+ || mode_class[i] == MODE_FLOAT
+ || mode_class[i] == MODE_DECIMAL_FLOAT
+ || mode_class[i] == MODE_COMPLEX_FLOAT
+ || mode_class[i] == MODE_VECTOR_FLOAT)
+ && (! force_fixed
+ || mode_class[i] == MODE_FRACT
+ || mode_class[i] == MODE_UFRACT
+ || mode_class[i] == MODE_ACCUM
+ || mode_class[i] == MODE_UACCUM
+ || mode_class[i] == MODE_VECTOR_FRACT
+ || mode_class[i] == MODE_VECTOR_UFRACT
+ || mode_class[i] == MODE_VECTOR_ACCUM
+ || mode_class[i] == MODE_VECTOR_UACCUM))
+ break;
+ }
+
+ if (i < 0)
+ return false;
+ name += strlen (GET_MODE_NAME (i));
+ if (*pat == 'a')
+ p->m1 = i;
+ else
+ p->m2 = i;
+
+ force_int = false;
+ force_partial_int = false;
+ force_float = false;
+ force_fixed = false;
+ }
+ break;
+
+ default:
+ gcc_unreachable ();
+ }
+ }
+}
+
+/* Return true if NAME is the name of an optab, describing it in P if so. */
+
+bool
+find_optab (optab_pattern *p, const char *name)
+{
+ if (*name == 0 || *name == '*')
+ return false;
+
+ /* See if NAME matches one of the patterns we have for the optabs
+ we know about. */
+ for (unsigned int pindex = 0; pindex < ARRAY_SIZE (optabs); pindex++)
+ {
+ p->m1 = p->m2 = 0;
+ if (match_pattern (p, name, optabs[pindex].pattern))
+ {
+ p->name = name;
+ p->op = optabs[pindex].op;
+ p->sort_num = (p->op << 16) | (p->m2 << 8) | p->m1;
+ return true;
+ }
+ }
+ return false;
+}
diff --git a/gcc/gensupport.h b/gcc/gensupport.h
index 0199e398034..456efa0c7d1 100644
--- a/gcc/gensupport.h
+++ b/gcc/gensupport.h
@@ -39,6 +39,91 @@ struct md_rtx_info {
int index;
};
+#define OPTAB_CL(name, pat, c, b, l) name,
+#define OPTAB_CX(name, pat)
+#define OPTAB_CD(name, pat) name,
+#define OPTAB_NL(name, pat, c, b, s, l) name,
+#define OPTAB_NC(name, pat, c) name,
+#define OPTAB_NX(name, pat)
+#define OPTAB_VL(name, pat, c, b, s, l) name,
+#define OPTAB_VC(name, pat, c) name,
+#define OPTAB_VX(name, pat)
+#define OPTAB_DC(name, pat, c) name,
+#define OPTAB_D(name, pat) name,
+
+/* Enumerates all optabs. */
+typedef enum optab_tag {
+ unknown_optab,
+#include "optabs.def"
+ NUM_OPTABS
+} optab;
+
+#undef OPTAB_CL
+#undef OPTAB_CX
+#undef OPTAB_CD
+#undef OPTAB_NL
+#undef OPTAB_NC
+#undef OPTAB_NX
+#undef OPTAB_VL
+#undef OPTAB_VC
+#undef OPTAB_VX
+#undef OPTAB_DC
+#undef OPTAB_D
+
+/* Describes one entry in optabs.def. */
+struct optab_def
+{
+ /* The name of the optab (e.g. "add_optab"). */
+ const char *name;
+
+ /* The pattern that matching define_expands and define_insns have.
+ See the comment at the head of optabs.def for details. */
+ const char *pattern;
+
+ /* The initializers (in the form of C code) for the libcall_basename,
+ libcall_suffix and libcall_gen fields of (convert_)optab_libcall_d. */
+ const char *base;
+ const char *suffix;
+ const char *libcall;
+
+ /* The optab's enum value. */
+ unsigned int op;
+
+ /* The value returned by optab_to_code (OP). */
+ enum rtx_code fcode;
+
+ /* CODE if code_to_optab (CODE) should return OP, otherwise UNKNOWN. */
+ enum rtx_code rcode;
+
+ /* 1: conversion optabs with libcall data,
+ 2: conversion optabs without libcall data,
+ 3: non-conversion optabs with libcall data ("normal" and "overflow"
+ optabs in the optabs.def comment)
+ 4: non-conversion optabs without libcall data ("direct" optabs). */
+ unsigned int kind;
+};
+
+extern optab_def optabs[];
+extern unsigned int num_optabs;
+
+/* Information about an instruction name that matches an optab pattern. */
+struct optab_pattern
+{
+ /* The name of the instruction. */
+ const char *name;
+
+ /* The matching optab. */
+ unsigned int op;
+
+ /* The optab modes. M2 is only significant for conversion optabs;
+ it is zero otherwise. */
+ unsigned int m1, m2;
+
+ /* An index that provides a lexicographical sort of (OP, M2, M1).
+ Used by genopinit.c. */
+ unsigned int sort_num;
+};
+
extern rtx add_implicit_parallel (rtvec);
extern bool init_rtx_reader_args_cb (int, char **, bool (*)(const char *));
extern bool init_rtx_reader_args (int, char **);
@@ -135,5 +220,6 @@ extern void compute_test_codes (rtx, file_location, char *);
extern file_location get_file_location (rtx);
extern const char *get_emit_function (rtx);
extern bool needs_barrier_p (rtx);
+extern bool find_optab (optab_pattern *, const char *);
#endif /* GCC_GENSUPPORT_H */
diff --git a/gcc/gimple-match-head.c b/gcc/gimple-match-head.c
index bdc1f982864..049ebab3f47 100644
--- a/gcc/gimple-match-head.c
+++ b/gcc/gimple-match-head.c
@@ -261,7 +261,7 @@ build_call_internal (internal_fn fn, tree type, unsigned int nargs, tree *ops)
if (direct_internal_fn_p (fn))
{
tree_pair types = direct_internal_fn_types (fn, type, ops);
- if (!direct_internal_fn_supported_p (fn, types))
+ if (!direct_internal_fn_supported_p (fn, types, OPTIMIZE_FOR_BOTH))
return NULL;
}
return gimple_build_call_internal (fn, nargs, ops[0], ops[1], ops[2]);
diff --git a/gcc/gimple-pretty-print.c b/gcc/gimple-pretty-print.c
index 7764201ea98..f1abf5c4aea 100644
--- a/gcc/gimple-pretty-print.c
+++ b/gcc/gimple-pretty-print.c
@@ -1356,6 +1356,9 @@ dump_gimple_omp_target (pretty_printer *buffer, gomp_target *gs,
case GF_OMP_TARGET_KIND_OACC_DECLARE:
kind = " oacc_declare";
break;
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
+ kind = " oacc_host_data";
+ break;
default:
gcc_unreachable ();
}
diff --git a/gcc/gimple.h b/gcc/gimple.h
index 0b04804ce46..dc61043fafc 100644
--- a/gcc/gimple.h
+++ b/gcc/gimple.h
@@ -171,6 +171,7 @@ enum gf_mask {
GF_OMP_TARGET_KIND_OACC_UPDATE = 8,
GF_OMP_TARGET_KIND_OACC_ENTER_EXIT_DATA = 9,
GF_OMP_TARGET_KIND_OACC_DECLARE = 10,
+ GF_OMP_TARGET_KIND_OACC_HOST_DATA = 11,
/* True on an GIMPLE_OMP_RETURN statement if the return does not require
a thread synchronization via some sort of barrier. The exact barrier
@@ -6004,6 +6005,7 @@ is_gimple_omp_oacc (const gimple *stmt)
case GF_OMP_TARGET_KIND_OACC_UPDATE:
case GF_OMP_TARGET_KIND_OACC_ENTER_EXIT_DATA:
case GF_OMP_TARGET_KIND_OACC_DECLARE:
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
return true;
default:
return false;
diff --git a/gcc/gimplify.c b/gcc/gimplify.c
index 7fff12f13ee..7146a01a5af 100644
--- a/gcc/gimplify.c
+++ b/gcc/gimplify.c
@@ -90,6 +90,9 @@ enum gimplify_omp_var_data
/* Flag for shared vars that are or might be stored to in the region. */
GOVD_WRITTEN = 131072,
+ /* Flag for GOVD_MAP, if it is a forced mapping. */
+ GOVD_MAP_FORCE = 262144,
+
GOVD_DATA_SHARE_CLASS = (GOVD_SHARED | GOVD_PRIVATE | GOVD_FIRSTPRIVATE
| GOVD_LASTPRIVATE | GOVD_REDUCTION | GOVD_LINEAR
| GOVD_LOCAL)
@@ -122,6 +125,7 @@ enum omp_region_type
ORT_ACC_DATA = ORT_ACC | ORT_TARGET_DATA, /* Data construct. */
ORT_ACC_PARALLEL = ORT_ACC | ORT_TARGET, /* Parallel construct */
ORT_ACC_KERNELS = ORT_ACC | ORT_TARGET | 0x80, /* Kernels construct. */
+ ORT_ACC_HOST_DATA = ORT_ACC | ORT_TARGET_DATA | 0x80, /* Host data. */
/* Dummy OpenMP region, used to disable expansion of
DECL_VALUE_EXPRs in taskloop pre body. */
@@ -5979,8 +5983,12 @@ oacc_default_clause (struct gimplify_omp_ctx *ctx, tree decl, unsigned flags)
gcc_unreachable ();
case ORT_ACC_KERNELS:
- /* Everything under kernels are default 'present_or_copy'. */
+ /* Scalars are default 'copy' under kernels, non-scalars are default
+ 'present_or_copy'. */
flags |= GOVD_MAP;
+ if (!AGGREGATE_TYPE_P (TREE_TYPE (decl)))
+ flags |= GOVD_MAP_FORCE;
+
rkind = "kernels";
break;
@@ -6120,6 +6128,9 @@ omp_notice_variable (struct gimplify_omp_ctx *ctx, tree decl, bool in_code)
(splay_tree_key) decl);
if (n2)
{
+ if (octx->region_type == ORT_ACC_HOST_DATA)
+ error ("variable %qE declared in enclosing "
+ "%<host_data%> region", DECL_NAME (decl));
nflags |= GOVD_MAP;
goto found_outer;
}
@@ -6418,6 +6429,7 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
case OMP_TARGET_DATA:
case OMP_TARGET_ENTER_DATA:
case OMP_TARGET_EXIT_DATA:
+ case OACC_HOST_DATA:
ctx->target_firstprivatize_array_bases = true;
default:
break;
@@ -6683,6 +6695,7 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
case OMP_TARGET_DATA:
case OMP_TARGET_ENTER_DATA:
case OMP_TARGET_EXIT_DATA:
+ case OACC_HOST_DATA:
if (OMP_CLAUSE_MAP_KIND (c) == GOMP_MAP_FIRSTPRIVATE_POINTER
|| (OMP_CLAUSE_MAP_KIND (c)
== GOMP_MAP_FIRSTPRIVATE_REFERENCE))
@@ -6695,6 +6708,22 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
}
if (remove)
break;
+ if (DECL_P (decl) && outer_ctx && (region_type & ORT_ACC))
+ {
+ struct gimplify_omp_ctx *octx;
+ for (octx = outer_ctx; octx; octx = octx->outer_context)
+ {
+ if (octx->region_type != ORT_ACC_HOST_DATA)
+ break;
+ splay_tree_node n2
+ = splay_tree_lookup (octx->variables,
+ (splay_tree_key) decl);
+ if (n2)
+ error_at (OMP_CLAUSE_LOCATION (c), "variable %qE "
+ "declared in enclosing %<host_data%> region",
+ DECL_NAME (decl));
+ }
+ }
if (OMP_CLAUSE_SIZE (c) == NULL_TREE)
OMP_CLAUSE_SIZE (c) = DECL_P (decl) ? DECL_SIZE_UNIT (decl)
: TYPE_SIZE_UNIT (TREE_TYPE (decl));
@@ -7092,6 +7121,7 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
}
goto do_notice;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
flags = GOVD_FIRSTPRIVATE | GOVD_EXPLICIT;
goto do_add;
@@ -7327,7 +7357,6 @@ gimplify_scan_omp_clauses (tree *list_p, gimple_seq *pre_p,
break;
case OMP_CLAUSE_DEVICE_RESIDENT:
- case OMP_CLAUSE_USE_DEVICE:
remove = true;
break;
@@ -7618,10 +7647,12 @@ gimplify_adjust_omp_clauses_1 (splay_tree_node n, void *data)
}
else if (code == OMP_CLAUSE_MAP)
{
- OMP_CLAUSE_SET_MAP_KIND (clause,
- flags & GOVD_MAP_TO_ONLY
- ? GOMP_MAP_TO
- : GOMP_MAP_TOFROM);
+ int kind = (flags & GOVD_MAP_TO_ONLY
+ ? GOMP_MAP_TO
+ : GOMP_MAP_TOFROM);
+ if (flags & GOVD_MAP_FORCE)
+ kind |= GOMP_MAP_FLAG_FORCE;
+ OMP_CLAUSE_SET_MAP_KIND (clause, kind);
if (DECL_SIZE (decl)
&& TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST)
{
@@ -9365,6 +9396,9 @@ gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
case OMP_TEAMS:
ort = OMP_TEAMS_COMBINED (expr) ? ORT_COMBINED_TEAMS : ORT_TEAMS;
break;
+ case OACC_HOST_DATA:
+ ort = ORT_ACC_HOST_DATA;
+ break;
default:
gcc_unreachable ();
}
@@ -9386,6 +9420,7 @@ gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
switch (TREE_CODE (expr))
{
case OACC_DATA:
+ case OACC_HOST_DATA:
end_ix = BUILT_IN_GOACC_DATA_END;
break;
case OMP_TARGET_DATA:
@@ -9418,6 +9453,10 @@ gimplify_omp_workshare (tree *expr_p, gimple_seq *pre_p)
stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_KERNELS,
OMP_CLAUSES (expr));
break;
+ case OACC_HOST_DATA:
+ stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_HOST_DATA,
+ OMP_CLAUSES (expr));
+ break;
case OACC_PARALLEL:
stmt = gimple_build_omp_target (body, GF_OMP_TARGET_KIND_OACC_PARALLEL,
OMP_CLAUSES (expr));
@@ -10527,16 +10566,12 @@ gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p,
ret = GS_ALL_DONE;
break;
- case OACC_HOST_DATA:
- sorry ("directive not yet implemented");
- ret = GS_ALL_DONE;
- break;
-
case OACC_DECLARE:
gimplify_oacc_declare (expr_p, pre_p);
ret = GS_ALL_DONE;
break;
+ case OACC_HOST_DATA:
case OACC_DATA:
case OACC_KERNELS:
case OACC_PARALLEL:
diff --git a/gcc/go/gofrontend/MERGE b/gcc/go/gofrontend/MERGE
index 80136abcf76..b4c90ef8892 100644
--- a/gcc/go/gofrontend/MERGE
+++ b/gcc/go/gofrontend/MERGE
@@ -1,4 +1,4 @@
-81eb6a3f425b2158c67ee32c0cc973a72ce9d6be
+c375f3bf470f94220149b486c947bb3eb57cde7d
The first line of this file holds the git revision number of the last
merge done from the gofrontend repository.
diff --git a/gcc/go/gofrontend/types.cc b/gcc/go/gofrontend/types.cc
index 64b560b45d6..802a17dc0e3 100644
--- a/gcc/go/gofrontend/types.cc
+++ b/gcc/go/gofrontend/types.cc
@@ -6398,22 +6398,21 @@ Array_type::do_reflection(Gogo* gogo, std::string* ret) const
if (this->length_ != NULL)
{
Numeric_constant nc;
- unsigned long val;
- if (!this->length_->numeric_constant_value(&nc)
- || nc.to_unsigned_long(&val) != Numeric_constant::NC_UL_VALID)
+ if (!this->length_->numeric_constant_value(&nc))
{
- if (!this->issued_length_error_)
- {
- error_at(this->length_->location(), "invalid array length");
- this->issued_length_error_ = true;
- }
+ go_assert(saw_errors());
+ return;
}
- else
+ mpz_t val;
+ if (!nc.to_int(&val))
{
- char buf[50];
- snprintf(buf, sizeof buf, "%lu", val);
- ret->append(buf);
+ go_assert(saw_errors());
+ return;
}
+ char* s = mpz_get_str(NULL, 10, val);
+ ret->append(s);
+ free(s);
+ mpz_clear(val);
}
ret->push_back(']');
@@ -6544,22 +6543,21 @@ Array_type::do_mangled_name(Gogo* gogo, std::string* ret) const
if (this->length_ != NULL)
{
Numeric_constant nc;
- unsigned long val;
- if (!this->length_->numeric_constant_value(&nc)
- || nc.to_unsigned_long(&val) != Numeric_constant::NC_UL_VALID)
+ if (!this->length_->numeric_constant_value(&nc))
{
- if (!this->issued_length_error_)
- {
- error_at(this->length_->location(), "invalid array length");
- this->issued_length_error_ = true;
- }
+ go_assert(saw_errors());
+ return;
}
- else
+ mpz_t val;
+ if (!nc.to_int(&val))
{
- char buf[50];
- snprintf(buf, sizeof buf, "%lu", val);
- ret->append(buf);
+ go_assert(saw_errors());
+ return;
}
+ char *s = mpz_get_str(NULL, 10, val);
+ ret->append(s);
+ free(s);
+ mpz_clear(val);
}
ret->push_back('e');
}
diff --git a/gcc/graphite-dependences.c b/gcc/graphite-dependences.c
index fcc771b9658..bb81ae3ebaa 100644
--- a/gcc/graphite-dependences.c
+++ b/gcc/graphite-dependences.c
@@ -87,7 +87,11 @@ scop_get_reads (scop_p scop, vec<poly_bb_p> pbbs)
{
FOR_EACH_VEC_ELT (PBB_DRS (pbb), j, pdr)
if (pdr_read_p (pdr))
- res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ {
+ if (dump_file)
+ print_pdr (dump_file, pdr);
+ res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ }
}
return res;
@@ -108,7 +112,11 @@ scop_get_must_writes (scop_p scop, vec<poly_bb_p> pbbs)
{
FOR_EACH_VEC_ELT (PBB_DRS (pbb), j, pdr)
if (pdr_write_p (pdr))
- res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ {
+ if (dump_file)
+ print_pdr (dump_file, pdr);
+ res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ }
}
return res;
@@ -129,7 +137,12 @@ scop_get_may_writes (scop_p scop, vec<poly_bb_p> pbbs)
{
FOR_EACH_VEC_ELT (PBB_DRS (pbb), j, pdr)
if (pdr_may_write_p (pdr))
- res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ {
+ if (dump_file)
+ print_pdr (dump_file, pdr);
+
+ res = isl_union_map_add_map (res, add_pdr_constraints (pdr, pbb));
+ }
}
return res;
@@ -313,6 +326,36 @@ compute_deps (scop_p scop, vec<poly_bb_p> pbbs,
isl_union_map *empty = isl_union_map_empty (space);
isl_union_map *original = scop_get_original_schedule (scop, pbbs);
+ if (dump_file)
+ {
+ fprintf (dump_file, "\n--- Documentation for datarefs dump: ---\n");
+ fprintf (dump_file, "Statements on the iteration domain are mapped to"
+ " array references.\n");
+ fprintf (dump_file, " To read the following data references:\n\n");
+ fprintf (dump_file, " S_5[i0] -> [106] : i0 >= 0 and i0 <= 3\n");
+ fprintf (dump_file, " S_8[i0] -> [1, i0] : i0 >= 0 and i0 <= 3\n\n");
+
+ fprintf (dump_file, " S_5[i0] is the dynamic instance of statement"
+ " bb_5 in a loop that accesses all iterations 0 <= i0 <= 3.\n");
+ fprintf (dump_file, " [1, i0] is a 'memref' with alias set 1"
+ " and first subscript access i0.\n");
+ fprintf (dump_file, " [106] is a 'scalar reference' which is the sum of"
+ " SSA_NAME_VERSION 6"
+ " and --param graphite-max-arrays-per-scop=100\n");
+ fprintf (dump_file, "-----------------------\n\n");
+
+ fprintf (dump_file, "data references (\n");
+ fprintf (dump_file, " reads: ");
+ print_isl_union_map (dump_file, reads);
+ fprintf (dump_file, " must_writes: ");
+ print_isl_union_map (dump_file, must_writes);
+ fprintf (dump_file, " may_writes: ");
+ print_isl_union_map (dump_file, may_writes);
+ fprintf (dump_file, " all_writes: ");
+ print_isl_union_map (dump_file, all_writes);
+ fprintf (dump_file, ")\n");
+ }
+
isl_union_map_compute_flow (isl_union_map_copy (reads),
isl_union_map_copy (must_writes),
isl_union_map_copy (may_writes),
diff --git a/gcc/graphite-isl-ast-to-gimple.c b/gcc/graphite-isl-ast-to-gimple.c
index bfce3169549..20eb80f52d4 100644
--- a/gcc/graphite-isl-ast-to-gimple.c
+++ b/gcc/graphite-isl-ast-to-gimple.c
@@ -588,6 +588,9 @@ binary_op_to_tree (tree type, __isl_take isl_ast_expr *expr, ivs_params &ip)
}
return fold_build2 (TRUNC_DIV_EXPR, type, tree_lhs_expr, tree_rhs_expr);
+#if HAVE_ISL_OPTIONS_SET_SCHEDULE_SERIALIZE_SCCS
+ case isl_ast_op_zdiv_r:
+#endif
case isl_ast_op_pdiv_r:
/* As ISL operates on arbitrary precision numbers, we may end up with
division by 2^64 that is folded to 0. */
@@ -758,6 +761,9 @@ gcc_expression_from_isl_expr_op (tree type, __isl_take isl_ast_expr *expr,
case isl_ast_op_pdiv_q:
case isl_ast_op_pdiv_r:
case isl_ast_op_fdiv_q:
+#if HAVE_ISL_OPTIONS_SET_SCHEDULE_SERIALIZE_SCCS
+ case isl_ast_op_zdiv_r:
+#endif
case isl_ast_op_and:
case isl_ast_op_or:
case isl_ast_op_eq:
@@ -2096,6 +2102,12 @@ translate_isl_ast_to_gimple::copy_loop_phi_nodes (basic_block bb,
codegen_error = !copy_loop_phi_args (phi, ibp_old_bb, new_phi,
ibp_new_bb, true);
update_stmt (new_phi);
+
+ if (dump_file)
+ {
+ fprintf (dump_file, "[codegen] creating loop-phi node: ");
+ print_gimple_stmt (dump_file, new_phi, 0, 0);
+ }
}
return true;
@@ -2894,6 +2906,26 @@ translate_isl_ast_to_gimple::copy_bb_and_scalar_dependences (basic_block bb,
return NULL;
}
+ /* In case ISL did some loop peeling, like this:
+
+ S_8(0);
+ for (int c1 = 1; c1 <= 5; c1 += 1) {
+ S_8(c1);
+ }
+ S_8(6);
+
+ there should be no loop-phi nodes in S_8(0).
+
+ FIXME: We need to reason about dynamic instances of S_8, i.e., the
+ values of all scalar variables: for the moment we instantiate only
+ SCEV analyzable expressions on the iteration domain, and we need to
+ extend that to reductions that cannot be analyzed by SCEV. */
+ if (!bb_in_sese_p (phi_bb, region->if_region->true_region->region))
+ {
+ codegen_error = true;
+ return NULL;
+ }
+
if (dump_file)
fprintf (dump_file, "[codegen] bb_%d contains loop phi nodes.\n",
bb->index);
@@ -2918,6 +2950,7 @@ translate_isl_ast_to_gimple::copy_bb_and_scalar_dependences (basic_block bb,
/* If a corresponding merge-point was not found, then abort codegen. */
if (phi_bb->loop_father != loop_father
+ || !bb_in_sese_p (phi_bb, region->if_region->true_region->region)
|| !copy_cond_phi_nodes (bb, phi_bb, iv_map))
{
codegen_error = true;
diff --git a/gcc/graphite-poly.c b/gcc/graphite-poly.c
index a51aefe574c..f4bdd401877 100644
--- a/gcc/graphite-poly.c
+++ b/gcc/graphite-poly.c
@@ -122,7 +122,7 @@ apply_poly_transforms (scop_p scop)
if (flag_loop_parallelize_all)
transform_done = true;
- if (flag_loop_optimize_isl)
+ if (flag_loop_nest_optimize)
transform_done |= optimize_isl (scop);
return transform_done;
diff --git a/gcc/graphite-sese-to-poly.c b/gcc/graphite-sese-to-poly.c
index 7ef01fbf32f..887c2125447 100644
--- a/gcc/graphite-sese-to-poly.c
+++ b/gcc/graphite-sese-to-poly.c
@@ -922,6 +922,33 @@ pdr_add_memory_accesses (isl_map *acc, dr_info &dri)
return acc;
}
+/* Return true when the LOW and HIGH bounds of an array reference REF are valid
+ to extract constraints on accessed elements of the array. Returning false is
+ the conservative answer. */
+
+static bool
+bounds_are_valid (tree ref, tree low, tree high)
+{
+ if (!high)
+ return false;
+
+ if (!tree_fits_shwi_p (low)
+ || !tree_fits_shwi_p (high))
+ return false;
+
+ /* 1-element arrays at end of structures may extend over
+ their declared size. */
+ if (array_at_struct_end_p (ref)
+ && operand_equal_p (low, high, 0))
+ return false;
+
+ /* Fortran has some arrays where high bound is -1 and low is 0. */
+ if (integer_onep (fold_build2 (LT_EXPR, boolean_type_node, high, low)))
+ return false;
+
+ return true;
+}
+
/* Add constrains representing the size of the accessed data to the
ACCESSES polyhedron. ACCESSP_NB_DIMS is the dimension of the
ACCESSES polyhedron, DOM_NB_DIMS is the dimension of the iteration
@@ -942,48 +969,35 @@ pdr_add_data_dimensions (isl_set *subscript_sizes, scop_p scop,
tree low = array_ref_low_bound (ref);
tree high = array_ref_up_bound (ref);
- /* XXX The PPL code dealt separately with
- subscript - low >= 0 and high - subscript >= 0 in case one of
- the two bounds isn't known. Do the same here? */
-
- if (tree_fits_shwi_p (low)
- && high
- && tree_fits_shwi_p (high)
- /* 1-element arrays at end of structures may extend over
- their declared size. */
- && !(array_at_struct_end_p (ref)
- && operand_equal_p (low, high, 0)))
- {
- isl_id *id;
- isl_aff *aff;
- isl_set *univ, *lbs, *ubs;
- isl_pw_aff *index;
- isl_set *valid;
- isl_space *space = isl_set_get_space (subscript_sizes);
- isl_pw_aff *lb = extract_affine_int (low, isl_space_copy (space));
- isl_pw_aff *ub = extract_affine_int (high, isl_space_copy (space));
-
- /* high >= 0 */
- valid = isl_pw_aff_nonneg_set (isl_pw_aff_copy (ub));
- valid = isl_set_project_out (valid, isl_dim_set, 0,
- isl_set_dim (valid, isl_dim_set));
- scop->param_context = isl_set_intersect (scop->param_context, valid);
-
- aff = isl_aff_zero_on_domain (isl_local_space_from_space (space));
- aff = isl_aff_add_coefficient_si (aff, isl_dim_in, i + 1, 1);
- univ = isl_set_universe (isl_space_domain (isl_aff_get_space (aff)));
- index = isl_pw_aff_alloc (univ, aff);
-
- id = isl_set_get_tuple_id (subscript_sizes);
- lb = isl_pw_aff_set_tuple_id (lb, isl_dim_in, isl_id_copy (id));
- ub = isl_pw_aff_set_tuple_id (ub, isl_dim_in, id);
-
- /* low <= sub_i <= high */
- lbs = isl_pw_aff_ge_set (isl_pw_aff_copy (index), lb);
- ubs = isl_pw_aff_le_set (index, ub);
- subscript_sizes = isl_set_intersect (subscript_sizes, lbs);
- subscript_sizes = isl_set_intersect (subscript_sizes, ubs);
- }
+ if (!bounds_are_valid (ref, low, high))
+ continue;
+
+ isl_space *space = isl_set_get_space (subscript_sizes);
+ isl_pw_aff *lb = extract_affine_int (low, isl_space_copy (space));
+ isl_pw_aff *ub = extract_affine_int (high, isl_space_copy (space));
+
+ /* high >= 0 */
+ isl_set *valid = isl_pw_aff_nonneg_set (isl_pw_aff_copy (ub));
+ valid = isl_set_project_out (valid, isl_dim_set, 0,
+ isl_set_dim (valid, isl_dim_set));
+ scop->param_context = isl_set_intersect (scop->param_context, valid);
+
+ isl_aff *aff
+ = isl_aff_zero_on_domain (isl_local_space_from_space (space));
+ aff = isl_aff_add_coefficient_si (aff, isl_dim_in, i + 1, 1);
+ isl_set *univ
+ = isl_set_universe (isl_space_domain (isl_aff_get_space (aff)));
+ isl_pw_aff *index = isl_pw_aff_alloc (univ, aff);
+
+ isl_id *id = isl_set_get_tuple_id (subscript_sizes);
+ lb = isl_pw_aff_set_tuple_id (lb, isl_dim_in, isl_id_copy (id));
+ ub = isl_pw_aff_set_tuple_id (ub, isl_dim_in, id);
+
+ /* low <= sub_i <= high */
+ isl_set *lbs = isl_pw_aff_ge_set (isl_pw_aff_copy (index), lb);
+ isl_set *ubs = isl_pw_aff_le_set (index, ub);
+ subscript_sizes = isl_set_intersect (subscript_sizes, lbs);
+ subscript_sizes = isl_set_intersect (subscript_sizes, ubs);
}
return subscript_sizes;
diff --git a/gcc/graphite.c b/gcc/graphite.c
index ee1d2117114..83aa88b3284 100644
--- a/gcc/graphite.c
+++ b/gcc/graphite.c
@@ -372,7 +372,7 @@ gate_graphite_transforms (void)
is turned on. */
if (flag_graphite_identity
|| flag_loop_parallelize_all
- || flag_loop_optimize_isl)
+ || flag_loop_nest_optimize)
flag_graphite = 1;
return flag_graphite != 0;
diff --git a/gcc/ifcvt.c b/gcc/ifcvt.c
index 8ece8734338..d474b3ba493 100644
--- a/gcc/ifcvt.c
+++ b/gcc/ifcvt.c
@@ -2172,10 +2172,6 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
}
}
- /* If insn to set up A clobbers any registers B depends on, try to
- swap insn that sets up A with the one that sets up B. If even
- that doesn't help, punt. */
-
modified_in_a = emit_a != NULL_RTX && modified_in_p (orig_b, emit_a);
if (tmp_b && then_bb)
{
@@ -2190,31 +2186,33 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
}
}
- if (emit_a || modified_in_a)
+
+ modified_in_b = emit_b != NULL_RTX && modified_in_p (orig_a, emit_b);
+ if (tmp_a && else_bb)
{
- modified_in_b = emit_b != NULL_RTX && modified_in_p (orig_a, emit_b);
- if (tmp_b && else_bb)
+ FOR_BB_INSNS (else_bb, tmp_insn)
+ /* Don't check inside insn_b. We will have changed it to emit_b
+ with a destination that doesn't conflict. */
+ if (!(insn_b && tmp_insn == insn_b)
+ && modified_in_p (orig_a, tmp_insn))
{
- FOR_BB_INSNS (else_bb, tmp_insn)
- /* Don't check inside insn_b. We will have changed it to emit_b
- with a destination that doesn't conflict. */
- if (!(insn_b && tmp_insn == insn_b)
- && modified_in_p (orig_a, tmp_insn))
- {
- modified_in_b = true;
- break;
- }
+ modified_in_b = true;
+ break;
}
- if (modified_in_b)
- goto end_seq_and_fail;
+ }
+ /* If insn to set up A clobbers any registers B depends on, try to
+ swap insn that sets up A with the one that sets up B. If even
+ that doesn't help, punt. */
+ if (modified_in_a && !modified_in_b)
+ {
if (!noce_emit_bb (emit_b, else_bb, b_simple))
goto end_seq_and_fail;
if (!noce_emit_bb (emit_a, then_bb, a_simple))
goto end_seq_and_fail;
}
- else
+ else if (!modified_in_a)
{
if (!noce_emit_bb (emit_a, then_bb, a_simple))
goto end_seq_and_fail;
@@ -2222,6 +2220,8 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
if (!noce_emit_bb (emit_b, else_bb, b_simple))
goto end_seq_and_fail;
}
+ else
+ goto end_seq_and_fail;
target = noce_emit_cmove (if_info, x, code, XEXP (if_info->cond, 0),
XEXP (if_info->cond, 1), a, b);
diff --git a/gcc/internal-fn.c b/gcc/internal-fn.c
index b15657f442b..2be2d8806f1 100644
--- a/gcc/internal-fn.c
+++ b/gcc/internal-fn.c
@@ -2214,23 +2214,30 @@ direct_internal_fn_types (internal_fn fn, gcall *call)
}
/* Return true if OPTAB is supported for TYPES (whose modes should be
- the same). Used for simple direct optabs. */
+ the same) when the optimization type is OPT_TYPE. Used for simple
+ direct optabs. */
static bool
-direct_optab_supported_p (direct_optab optab, tree_pair types)
+direct_optab_supported_p (direct_optab optab, tree_pair types,
+ optimization_type opt_type)
{
machine_mode mode = TYPE_MODE (types.first);
gcc_checking_assert (mode == TYPE_MODE (types.second));
- return direct_optab_handler (optab, mode) != CODE_FOR_nothing;
+ return direct_optab_handler (optab, mode, opt_type) != CODE_FOR_nothing;
}
/* Return true if load/store lanes optab OPTAB is supported for
- array type TYPES.first. */
+ array type TYPES.first when the optimization type is OPT_TYPE. */
static bool
-multi_vector_optab_supported_p (convert_optab optab, tree_pair types)
+multi_vector_optab_supported_p (convert_optab optab, tree_pair types,
+ optimization_type opt_type)
{
- return get_multi_vector_move (types.first, optab) != CODE_FOR_nothing;
+ gcc_assert (TREE_CODE (types.first) == ARRAY_TYPE);
+ machine_mode imode = TYPE_MODE (types.first);
+ machine_mode vmode = TYPE_MODE (TREE_TYPE (types.first));
+ return (convert_optab_handler (optab, imode, vmode, opt_type)
+ != CODE_FOR_nothing);
}
#define direct_unary_optab_supported_p direct_optab_supported_p
@@ -2240,12 +2247,14 @@ multi_vector_optab_supported_p (convert_optab optab, tree_pair types)
#define direct_mask_store_optab_supported_p direct_optab_supported_p
#define direct_store_lanes_optab_supported_p multi_vector_optab_supported_p
-/* Return true if FN is supported for the types in TYPES. The types
- are those associated with the "type0" and "type1" fields of FN's
- direct_internal_fn_info structure. */
+/* Return true if FN is supported for the types in TYPES when the
+ optimization type is OPT_TYPE. The types are those associated with
+ the "type0" and "type1" fields of FN's direct_internal_fn_info
+ structure. */
bool
-direct_internal_fn_supported_p (internal_fn fn, tree_pair types)
+direct_internal_fn_supported_p (internal_fn fn, tree_pair types,
+ optimization_type opt_type)
{
switch (fn)
{
@@ -2253,7 +2262,8 @@ direct_internal_fn_supported_p (internal_fn fn, tree_pair types)
case IFN_##CODE: break;
#define DEF_INTERNAL_OPTAB_FN(CODE, FLAGS, OPTAB, TYPE) \
case IFN_##CODE: \
- return direct_##TYPE##_optab_supported_p (OPTAB##_optab, types);
+ return direct_##TYPE##_optab_supported_p (OPTAB##_optab, types, \
+ opt_type);
#include "internal-fn.def"
case IFN_LAST:
@@ -2262,16 +2272,17 @@ direct_internal_fn_supported_p (internal_fn fn, tree_pair types)
gcc_unreachable ();
}
-/* Return true if FN is supported for type TYPE. The caller knows that
- the "type0" and "type1" fields of FN's direct_internal_fn_info
- structure are the same. */
+/* Return true if FN is supported for type TYPE when the optimization
+ type is OPT_TYPE. The caller knows that the "type0" and "type1"
+ fields of FN's direct_internal_fn_info structure are the same. */
bool
-direct_internal_fn_supported_p (internal_fn fn, tree type)
+direct_internal_fn_supported_p (internal_fn fn, tree type,
+ optimization_type opt_type)
{
const direct_internal_fn_info &info = direct_internal_fn (fn);
gcc_checking_assert (info.type0 == info.type1);
- return direct_internal_fn_supported_p (fn, tree_pair (type, type));
+ return direct_internal_fn_supported_p (fn, tree_pair (type, type), opt_type);
}
/* Return true if IFN_SET_EDOM is supported. */
diff --git a/gcc/internal-fn.def b/gcc/internal-fn.def
index dee9332c3d6..a9118b30b5a 100644
--- a/gcc/internal-fn.def
+++ b/gcc/internal-fn.def
@@ -91,6 +91,8 @@ DEF_INTERNAL_OPTAB_FN (LOAD_LANES, ECF_CONST, vec_load_lanes, load_lanes)
DEF_INTERNAL_OPTAB_FN (MASK_STORE, 0, maskstore, mask_store)
DEF_INTERNAL_OPTAB_FN (STORE_LANES, ECF_CONST, vec_store_lanes, store_lanes)
+DEF_INTERNAL_OPTAB_FN (RSQRT, ECF_CONST, rsqrt, unary)
+
/* Unary math functions. */
DEF_INTERNAL_FLT_FN (ACOS, ECF_CONST, acos, unary)
DEF_INTERNAL_FLT_FN (ASIN, ECF_CONST, asin, unary)
diff --git a/gcc/internal-fn.h b/gcc/internal-fn.h
index aea6abdaf7e..ef27f09cdc9 100644
--- a/gcc/internal-fn.h
+++ b/gcc/internal-fn.h
@@ -166,8 +166,10 @@ direct_internal_fn (internal_fn fn)
extern tree_pair direct_internal_fn_types (internal_fn, tree, tree *);
extern tree_pair direct_internal_fn_types (internal_fn, gcall *);
-extern bool direct_internal_fn_supported_p (internal_fn, tree_pair);
-extern bool direct_internal_fn_supported_p (internal_fn, tree);
+extern bool direct_internal_fn_supported_p (internal_fn, tree_pair,
+ optimization_type);
+extern bool direct_internal_fn_supported_p (internal_fn, tree,
+ optimization_type);
extern bool set_edom_supported_p (void);
extern void expand_internal_call (gcall *);
diff --git a/gcc/ipa-pure-const.c b/gcc/ipa-pure-const.c
index 840ca7ad844..4cf09183f3a 100644
--- a/gcc/ipa-pure-const.c
+++ b/gcc/ipa-pure-const.c
@@ -1124,11 +1124,18 @@ pure_const_read_summary (void)
}
}
+/* We only propagate across edges that can throw externally and their callee
+ is not interposable. */
static bool
-ignore_edge (struct cgraph_edge *e)
+ignore_edge_for_nothrow (struct cgraph_edge *e)
{
- return (!e->can_throw_external);
+ if (!e->can_throw_external || TREE_NOTHROW (e->callee->decl))
+ return true;
+
+ enum availability avail;
+ cgraph_node *n = e->callee->function_or_virtual_thunk_symbol (&avail);
+ return (avail <= AVAIL_INTERPOSABLE || TREE_NOTHROW (n->decl));
}
/* Return true if NODE is self recursive function.
@@ -1157,6 +1164,17 @@ cdtor_p (cgraph_node *n, void *)
return false;
}
+/* We only propagate across edges with non-interposable callee. */
+
+static bool
+ignore_edge_for_pure_const (struct cgraph_edge *e)
+{
+ enum availability avail;
+ e->callee->function_or_virtual_thunk_symbol (&avail);
+ return (avail <= AVAIL_INTERPOSABLE);
+}
+
+
/* Produce transitive closure over the callgraph and compute pure/const
attributes. */
@@ -1172,7 +1190,8 @@ propagate_pure_const (void)
struct ipa_dfs_info * w_info;
bool remove_p = false;
- order_pos = ipa_reduced_postorder (order, true, false, NULL);
+ order_pos = ipa_reduced_postorder (order, true, false,
+ ignore_edge_for_pure_const);
if (dump_file)
{
cgraph_node::dump_cgraph (dump_file);
@@ -1219,7 +1238,7 @@ propagate_pure_const (void)
if (pure_const_state == IPA_NEITHER)
break;
- /* For overwritable nodes we can not assume anything. */
+ /* For interposable nodes we can not assume anything. */
if (w->get_availability () == AVAIL_INTERPOSABLE)
{
worse_state (&pure_const_state, &looping,
@@ -1228,7 +1247,7 @@ propagate_pure_const (void)
if (dump_file && (dump_flags & TDF_DETAILS))
{
fprintf (dump_file,
- " Overwritable. state %s looping %i\n",
+ " Interposable. state %s looping %i\n",
pure_const_names[w_l->state_previously_known],
w_l->looping_previously_known);
}
@@ -1244,7 +1263,8 @@ propagate_pure_const (void)
looping = true;
/* Now walk the edges and merge in callee properties. */
- for (e = w->callees; e; e = e->next_callee)
+ for (e = w->callees; e && pure_const_state != IPA_NEITHER;
+ e = e->next_callee)
{
enum availability avail;
struct cgraph_node *y = e->callee->
@@ -1302,11 +1322,10 @@ propagate_pure_const (void)
if (pure_const_state == IPA_NEITHER)
break;
}
- if (pure_const_state == IPA_NEITHER)
- break;
/* Now process the indirect call. */
- for (ie = w->indirect_calls; ie; ie = ie->next_callee)
+ for (ie = w->indirect_calls;
+ ie && pure_const_state != IPA_NEITHER; ie = ie->next_callee)
{
enum pure_const_state_e edge_state = IPA_CONST;
bool edge_looping = false;
@@ -1325,11 +1344,10 @@ propagate_pure_const (void)
if (pure_const_state == IPA_NEITHER)
break;
}
- if (pure_const_state == IPA_NEITHER)
- break;
/* And finally all loads and stores. */
- for (i = 0; w->iterate_reference (i, ref); i++)
+ for (i = 0; w->iterate_reference (i, ref)
+ && pure_const_state != IPA_NEITHER; i++)
{
enum pure_const_state_e ref_state = IPA_CONST;
bool ref_looping = false;
@@ -1419,7 +1437,8 @@ propagate_pure_const (void)
&& this_state > w_l->state_previously_known)
{
this_state = w_l->state_previously_known;
- this_looping |= w_l->looping_previously_known;
+ if (this_state == IPA_NEITHER)
+ this_looping = w_l->looping_previously_known;
}
if (!this_looping && self_recursive_p (w))
this_looping = true;
@@ -1491,7 +1510,8 @@ propagate_nothrow (void)
int i;
struct ipa_dfs_info * w_info;
- order_pos = ipa_reduced_postorder (order, true, false, ignore_edge);
+ order_pos = ipa_reduced_postorder (order, true, false,
+ ignore_edge_for_nothrow);
if (dump_file)
{
cgraph_node::dump_cgraph (dump_file);
@@ -1515,32 +1535,38 @@ propagate_nothrow (void)
while (w && !can_throw)
{
struct cgraph_edge *e, *ie;
- funct_state w_l = get_function_state (w);
-
- if (w_l->can_throw
- || w->get_availability () == AVAIL_INTERPOSABLE)
- can_throw = true;
- for (e = w->callees; e && !can_throw; e = e->next_callee)
+ if (!TREE_NOTHROW (w->decl))
{
- enum availability avail;
- struct cgraph_node *y = e->callee->
- function_or_virtual_thunk_symbol (&avail);
+ funct_state w_l = get_function_state (w);
- if (avail > AVAIL_INTERPOSABLE)
+ if (w_l->can_throw
+ || w->get_availability () == AVAIL_INTERPOSABLE)
+ can_throw = true;
+
+ for (e = w->callees; e && !can_throw; e = e->next_callee)
{
- funct_state y_l = get_function_state (y);
+ enum availability avail;
+
+ if (!e->can_throw_external || TREE_NOTHROW (e->callee->decl))
+ continue;
+
+ struct cgraph_node *y = e->callee->
+ function_or_virtual_thunk_symbol (&avail);
- if (y_l->can_throw && !TREE_NOTHROW (w->decl)
- && e->can_throw_external)
+ /* We can use info about the callee only if we know it can
+ not be interposed. */
+ if (avail <= AVAIL_INTERPOSABLE
+ || (!TREE_NOTHROW (y->decl)
+ && get_function_state (y)->can_throw))
can_throw = true;
}
- else if (e->can_throw_external && !TREE_NOTHROW (y->decl))
- can_throw = true;
+ for (ie = w->indirect_calls; ie && !can_throw;
+ ie = ie->next_callee)
+ if (ie->can_throw_external
+ && !(ie->indirect_info->ecf_flags & ECF_NOTHROW))
+ can_throw = true;
}
- for (ie = w->indirect_calls; ie && !can_throw; ie = ie->next_callee)
- if (ie->can_throw_external)
- can_throw = true;
w_info = (struct ipa_dfs_info *) w->aux;
w = w_info->next_cycle;
}
@@ -1650,7 +1676,7 @@ skip_function_for_local_pure_const (struct cgraph_node *node)
if (node->get_availability () <= AVAIL_INTERPOSABLE)
{
if (dump_file)
- fprintf (dump_file, "Function is not available or overwritable; not analyzing.\n");
+ fprintf (dump_file, "Function is not available or interposable; not analyzing.\n");
return true;
}
return false;
diff --git a/gcc/ipa-split.c b/gcc/ipa-split.c
index be33ddae412..56c954b01b2 100644
--- a/gcc/ipa-split.c
+++ b/gcc/ipa-split.c
@@ -1205,7 +1205,6 @@ split_function (basic_block return_bb, struct split_point *split_point,
edge e;
edge_iterator ei;
tree retval = NULL, real_retval = NULL, retbnd = NULL;
- bool split_part_return_p = false;
bool with_bounds = chkp_function_instrumented_p (current_function_decl);
gimple *last_stmt = NULL;
unsigned int i;
@@ -1246,12 +1245,28 @@ split_function (basic_block return_bb, struct split_point *split_point,
args_to_pass.safe_push (arg);
}
- /* See if the split function will return. */
+ /* See if the split function or the main part will return. */
+ bool main_part_return_p = false;
+ bool split_part_return_p = false;
FOR_EACH_EDGE (e, ei, return_bb->preds)
- if (bitmap_bit_p (split_point->split_bbs, e->src->index))
- break;
- if (e)
- split_part_return_p = true;
+ {
+ if (bitmap_bit_p (split_point->split_bbs, e->src->index))
+ split_part_return_p = true;
+ else
+ main_part_return_p = true;
+ }
+ /* The main part also returns if we we split on a fallthru edge
+ and the split part returns. */
+ if (split_part_return_p)
+ FOR_EACH_EDGE (e, ei, split_point->entry_bb->preds)
+ {
+ if (! bitmap_bit_p (split_point->split_bbs, e->src->index)
+ && single_succ_p (e->src))
+ {
+ main_part_return_p = true;
+ break;
+ }
+ }
/* Add return block to what will become the split function.
We do not return; no return block is needed. */
@@ -1295,6 +1310,11 @@ split_function (basic_block return_bb, struct split_point *split_point,
else
bitmap_set_bit (split_point->split_bbs, return_bb->index);
+ /* If the main part doesn't return pretend the return block wasn't
+ found for all of the following. */
+ if (! main_part_return_p)
+ return_bb = EXIT_BLOCK_PTR_FOR_FN (cfun);
+
/* If RETURN_BB has virtual operand PHIs, they must be removed and the
virtual operand marked for renaming as we change the CFG in a way that
tree-inline is not able to compensate for.
diff --git a/gcc/loop-init.c b/gcc/loop-init.c
index e32c94ab1c0..120316d6562 100644
--- a/gcc/loop-init.c
+++ b/gcc/loop-init.c
@@ -395,7 +395,7 @@ rtl_loop_init (void)
dump_flow_info (dump_file, dump_flags);
}
- loop_optimizer_init (LOOPS_NORMAL);
+ loop_optimizer_init (LOOPS_NORMAL | LOOPS_HAVE_RECORDED_EXITS);
return 0;
}
diff --git a/gcc/loop-iv.c b/gcc/loop-iv.c
index c7d51643e92..dfa3ca38204 100644
--- a/gcc/loop-iv.c
+++ b/gcc/loop-iv.c
@@ -3054,7 +3054,7 @@ get_simple_loop_desc (struct loop *loop)
}
}
- if (flag_unsafe_loop_optimizations)
+ if (flag_unsafe_loop_optimizations && single_exit (loop))
{
desc->assumptions = NULL_RTX;
desc->infinite = NULL_RTX;
diff --git a/gcc/lto-streamer-out.c b/gcc/lto-streamer-out.c
index 0d610f166bc..8928873bcc2 100644
--- a/gcc/lto-streamer-out.c
+++ b/gcc/lto-streamer-out.c
@@ -1109,10 +1109,6 @@ hash_tree (struct streamer_tree_cache_d *cache, hash_map<tree, hashval_t> *map,
hstate.commit_flag ();
hstate.add_int (TYPE_PRECISION (t));
hstate.add_int (TYPE_ALIGN (t));
- hstate.add_int ((TYPE_ALIAS_SET (t) == 0
- || (!in_lto_p
- && get_alias_set (t) == 0))
- ? 0 : -1);
}
if (CODE_CONTAINS_STRUCT (code, TS_TRANSLATION_UNIT_DECL))
diff --git a/gcc/lto/ChangeLog b/gcc/lto/ChangeLog
index 1ddacfa158f..a508999e0f6 100644
--- a/gcc/lto/ChangeLog
+++ b/gcc/lto/ChangeLog
@@ -1,3 +1,7 @@
+2015-12-01 Jan Hubicka <hubicka@ucw.cz>
+
+ * lto.c (compare_tree_sccs_1): Do not compare TYPE_ALIAS_SET.
+
2015-11-25 Jan Hubicka <jh@suse.cz>
* lto-lang.c (lto_post_options): Process flag_lto_linker_output.
diff --git a/gcc/lto/lto.c b/gcc/lto/lto.c
index b1e2d6e8090..dcfa3c868f3 100644
--- a/gcc/lto/lto.c
+++ b/gcc/lto/lto.c
@@ -1166,7 +1166,9 @@ compare_tree_sccs_1 (tree t1, tree t2, tree **map)
compare_values (TYPE_READONLY);
compare_values (TYPE_PRECISION);
compare_values (TYPE_ALIGN);
- compare_values (TYPE_ALIAS_SET);
+ /* Do not compare TYPE_ALIAS_SET. Doing so introduce ordering issues
+ with calls to get_alias_set which may initialize it for streamed
+ in types. */
}
/* We don't want to compare locations, so there is nothing do compare
diff --git a/gcc/match.pd b/gcc/match.pd
index ea512fb20b9..5ac30eb078f 100644
--- a/gcc/match.pd
+++ b/gcc/match.pd
@@ -1855,15 +1855,17 @@ DEFINE_INT_AND_FLOAT_ROUND_FN (RINT)
/* Fold ~X op ~Y as Y op X. */
(for cmp (simple_comparison)
(simplify
- (cmp (bit_not @0) (bit_not @1))
- (cmp @1 @0)))
+ (cmp (bit_not@2 @0) (bit_not@3 @1))
+ (if (single_use (@2) && single_use (@3))
+ (cmp @1 @0))))
/* Fold ~X op C as X op' ~C, where op' is the swapped comparison. */
(for cmp (simple_comparison)
scmp (swapped_simple_comparison)
(simplify
- (cmp (bit_not @0) CONSTANT_CLASS_P@1)
- (if (TREE_CODE (@1) == INTEGER_CST || TREE_CODE (@1) == VECTOR_CST)
+ (cmp (bit_not@2 @0) CONSTANT_CLASS_P@1)
+ (if (single_use (@2)
+ && (TREE_CODE (@1) == INTEGER_CST || TREE_CODE (@1) == VECTOR_CST))
(scmp @0 (bit_not @1)))))
(for cmp (simple_comparison)
diff --git a/gcc/omp-builtins.def b/gcc/omp-builtins.def
index d540dab7969..35f5014a62b 100644
--- a/gcc/omp-builtins.def
+++ b/gcc/omp-builtins.def
@@ -47,6 +47,8 @@ DEF_GOACC_BUILTIN (BUILT_IN_GOACC_UPDATE, "GOACC_update",
DEF_GOACC_BUILTIN (BUILT_IN_GOACC_WAIT, "GOACC_wait",
BT_FN_VOID_INT_INT_VAR,
ATTR_NOTHROW_LIST)
+DEF_GOACC_BUILTIN (BUILT_IN_GOACC_HOST_DATA, "GOACC_host_data",
+ BT_FN_VOID_INT_SIZE_PTR_PTR_PTR, ATTR_NOTHROW_LIST)
DEF_GOACC_BUILTIN_COMPILER (BUILT_IN_ACC_ON_DEVICE, "acc_on_device",
BT_FN_INT_INT, ATTR_CONST_NOTHROW_LEAF_LIST)
diff --git a/gcc/omp-low.c b/gcc/omp-low.c
index f17a828330a..d1d1e3cd67a 100644
--- a/gcc/omp-low.c
+++ b/gcc/omp-low.c
@@ -1366,10 +1366,12 @@ build_sender_ref (tree var, omp_context *ctx)
return build_sender_ref ((splay_tree_key) var, ctx);
}
-/* Add a new field for VAR inside the structure CTX->SENDER_DECL. */
+/* Add a new field for VAR inside the structure CTX->SENDER_DECL. If
+ BASE_POINTERS_RESTRICT, declare the field with restrict. */
static void
-install_var_field (tree var, bool by_ref, int mask, omp_context *ctx)
+install_var_field (tree var, bool by_ref, int mask, omp_context *ctx,
+ bool base_pointers_restrict = false)
{
tree field, type, sfield = NULL_TREE;
splay_tree_key key = (splay_tree_key) var;
@@ -1393,7 +1395,11 @@ install_var_field (tree var, bool by_ref, int mask, omp_context *ctx)
type = build_pointer_type (build_pointer_type (type));
}
else if (by_ref)
- type = build_pointer_type (type);
+ {
+ type = build_pointer_type (type);
+ if (base_pointers_restrict)
+ type = build_qualified_type (type, TYPE_QUAL_RESTRICT);
+ }
else if ((mask & 3) == 1 && is_reference (var))
type = TREE_TYPE (type);
@@ -1810,10 +1816,12 @@ fixup_child_record_type (omp_context *ctx)
}
/* Instantiate decls as necessary in CTX to satisfy the data sharing
- specified by CLAUSES. */
+ specified by CLAUSES. If BASE_POINTERS_RESTRICT, install var field with
+ restrict. */
static void
-scan_sharing_clauses (tree clauses, omp_context *ctx)
+scan_sharing_clauses (tree clauses, omp_context *ctx,
+ bool base_pointers_restrict = false)
{
tree c, decl;
bool scan_array_reductions = false;
@@ -1942,6 +1950,7 @@ scan_sharing_clauses (tree clauses, omp_context *ctx)
install_var_local (decl, ctx);
break;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
decl = OMP_CLAUSE_DECL (c);
if (TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
@@ -2074,7 +2083,8 @@ scan_sharing_clauses (tree clauses, omp_context *ctx)
&& TREE_CODE (TREE_TYPE (decl)) == ARRAY_TYPE)
install_var_field (decl, true, 7, ctx);
else
- install_var_field (decl, true, 3, ctx);
+ install_var_field (decl, true, 3, ctx,
+ base_pointers_restrict);
if (is_gimple_omp_offloaded (ctx->stmt))
install_var_local (decl, ctx);
}
@@ -2144,7 +2154,6 @@ scan_sharing_clauses (tree clauses, omp_context *ctx)
break;
case OMP_CLAUSE_DEVICE_RESIDENT:
- case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE__CACHE_:
sorry ("Clause not supported yet");
break;
@@ -2295,6 +2304,7 @@ scan_sharing_clauses (tree clauses, omp_context *ctx)
case OMP_CLAUSE_SIMD:
case OMP_CLAUSE_NOGROUP:
case OMP_CLAUSE_DEFAULTMAP:
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE__CILK_FOR_COUNT_:
case OMP_CLAUSE_ASYNC:
@@ -2312,7 +2322,6 @@ scan_sharing_clauses (tree clauses, omp_context *ctx)
break;
case OMP_CLAUSE_DEVICE_RESIDENT:
- case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE__CACHE_:
sorry ("Clause not supported yet");
break;
@@ -3036,6 +3045,68 @@ scan_omp_single (gomp_single *stmt, omp_context *outer_ctx)
layout_type (ctx->record_type);
}
+/* Return true if the CLAUSES of an omp target guarantee that the base pointers
+ used in the corresponding offloaded function are restrict. */
+
+static bool
+omp_target_base_pointers_restrict_p (tree clauses)
+{
+ /* The analysis relies on the GOMP_MAP_FORCE_* mapping kinds, which are only
+ used by OpenACC. */
+ if (flag_openacc == 0)
+ return false;
+
+ /* I. Basic example:
+
+ void foo (void)
+ {
+ unsigned int a[2], b[2];
+
+ #pragma acc kernels \
+ copyout (a) \
+ copyout (b)
+ {
+ a[0] = 0;
+ b[0] = 1;
+ }
+ }
+
+ After gimplification, we have:
+
+ #pragma omp target oacc_kernels \
+ map(force_from:a [len: 8]) \
+ map(force_from:b [len: 8])
+ {
+ a[0] = 0;
+ b[0] = 1;
+ }
+
+ Because both mappings have the force prefix, we know that they will be
+ allocated when calling the corresponding offloaded function, which means we
+ can mark the base pointers for a and b in the offloaded function as
+ restrict. */
+
+ tree c;
+ for (c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
+ {
+ if (OMP_CLAUSE_CODE (c) != OMP_CLAUSE_MAP)
+ return false;
+
+ switch (OMP_CLAUSE_MAP_KIND (c))
+ {
+ case GOMP_MAP_FORCE_ALLOC:
+ case GOMP_MAP_FORCE_TO:
+ case GOMP_MAP_FORCE_FROM:
+ case GOMP_MAP_FORCE_TOFROM:
+ break;
+ default:
+ return false;
+ }
+ }
+
+ return true;
+}
+
/* Scan a GIMPLE_OMP_TARGET. */
static void
@@ -3057,13 +3128,21 @@ scan_omp_target (gomp_target *stmt, omp_context *outer_ctx)
DECL_NAMELESS (name) = 1;
TYPE_NAME (ctx->record_type) = name;
TYPE_ARTIFICIAL (ctx->record_type) = 1;
+
+ bool base_pointers_restrict = false;
if (offloaded)
{
create_omp_child_function (ctx, false);
gimple_omp_target_set_child_fn (stmt, ctx->cb.dst_fn);
+
+ base_pointers_restrict = omp_target_base_pointers_restrict_p (clauses);
+ if (base_pointers_restrict
+ && dump_file && (dump_flags & TDF_DETAILS))
+ fprintf (dump_file,
+ "Base pointers in offloaded function are restrict\n");
}
- scan_sharing_clauses (clauses, ctx);
+ scan_sharing_clauses (clauses, ctx, base_pointers_restrict);
scan_omp (gimple_omp_body_ptr (stmt), ctx);
if (TYPE_FIELDS (ctx->record_type) == NULL)
@@ -3615,6 +3694,8 @@ check_omp_nesting_restrictions (gimple *stmt, omp_context *ctx)
case GF_OMP_TARGET_KIND_OACC_UPDATE: stmt_name = "update"; break;
case GF_OMP_TARGET_KIND_OACC_ENTER_EXIT_DATA:
stmt_name = "enter/exit data"; break;
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA: stmt_name = "host_data";
+ break;
default: gcc_unreachable ();
}
switch (gimple_omp_target_kind (ctx->stmt))
@@ -3626,6 +3707,8 @@ check_omp_nesting_restrictions (gimple *stmt, omp_context *ctx)
case GF_OMP_TARGET_KIND_OACC_KERNELS:
ctx_stmt_name = "kernels"; break;
case GF_OMP_TARGET_KIND_OACC_DATA: ctx_stmt_name = "data"; break;
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
+ ctx_stmt_name = "host_data"; break;
default: gcc_unreachable ();
}
@@ -12508,6 +12591,7 @@ expand_omp_target (struct omp_region *region)
break;
case GF_OMP_TARGET_KIND_DATA:
case GF_OMP_TARGET_KIND_OACC_DATA:
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
data_region = true;
break;
default:
@@ -12751,6 +12835,9 @@ expand_omp_target (struct omp_region *region)
case GF_OMP_TARGET_KIND_OACC_DECLARE:
start_ix = BUILT_IN_GOACC_DECLARE;
break;
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
+ start_ix = BUILT_IN_GOACC_HOST_DATA;
+ break;
default:
gcc_unreachable ();
}
@@ -12875,6 +12962,7 @@ expand_omp_target (struct omp_region *region)
case BUILT_IN_GOACC_DATA_START:
case BUILT_IN_GOACC_DECLARE:
case BUILT_IN_GOMP_TARGET_DATA:
+ case BUILT_IN_GOACC_HOST_DATA:
break;
case BUILT_IN_GOMP_TARGET:
case BUILT_IN_GOMP_TARGET_UPDATE:
@@ -13182,6 +13270,7 @@ build_omp_regions_1 (basic_block bb, struct omp_region *parent,
case GF_OMP_TARGET_KIND_OACC_PARALLEL:
case GF_OMP_TARGET_KIND_OACC_KERNELS:
case GF_OMP_TARGET_KIND_OACC_DATA:
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
break;
case GF_OMP_TARGET_KIND_UPDATE:
case GF_OMP_TARGET_KIND_ENTER_DATA:
@@ -14982,6 +15071,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx)
break;
case GF_OMP_TARGET_KIND_DATA:
case GF_OMP_TARGET_KIND_OACC_DATA:
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
data_region = true;
break;
default:
@@ -15188,6 +15278,7 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx)
}
break;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
var = OMP_CLAUSE_DECL (c);
@@ -15573,12 +15664,14 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx)
build_int_cstu (tkind_type, tkind));
break;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
ovar = OMP_CLAUSE_DECL (c);
var = lookup_decl_in_outer_ctx (ovar, ctx);
x = build_sender_ref (ovar, ctx);
- if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR)
+ if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR
+ || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE)
tkind = GOMP_MAP_USE_DEVICE_PTR;
else
tkind = GOMP_MAP_FIRSTPRIVATE_INT;
@@ -15781,10 +15874,12 @@ lower_omp_target (gimple_stmt_iterator *gsi_p, omp_context *ctx)
gimple_build_assign (new_var, x));
}
break;
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
var = OMP_CLAUSE_DECL (c);
- if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR)
+ if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE_PTR
+ || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_USE_DEVICE)
x = build_sender_ref (var, ctx);
else
x = build_receiver_ref (var, false, ctx);
@@ -16771,6 +16866,7 @@ make_gimple_omp_edges (basic_block bb, struct omp_region **region,
case GF_OMP_TARGET_KIND_OACC_PARALLEL:
case GF_OMP_TARGET_KIND_OACC_KERNELS:
case GF_OMP_TARGET_KIND_OACC_DATA:
+ case GF_OMP_TARGET_KIND_OACC_HOST_DATA:
break;
case GF_OMP_TARGET_KIND_UPDATE:
case GF_OMP_TARGET_KIND_ENTER_DATA:
diff --git a/gcc/optabs-query.c b/gcc/optabs-query.c
index c20597c7bcb..2f9c7cde278 100644
--- a/gcc/optabs-query.c
+++ b/gcc/optabs-query.c
@@ -35,6 +35,36 @@ struct target_optabs *this_fn_optabs = &default_target_optabs;
struct target_optabs *this_target_optabs = &default_target_optabs;
#endif
+/* Return the insn used to perform conversion OP from mode FROM_MODE
+ to mode TO_MODE; return CODE_FOR_nothing if the target does not have
+ such an insn, or if it is unsuitable for optimization type OPT_TYPE. */
+
+insn_code
+convert_optab_handler (convert_optab optab, machine_mode to_mode,
+ machine_mode from_mode, optimization_type opt_type)
+{
+ insn_code icode = convert_optab_handler (optab, to_mode, from_mode);
+ if (icode == CODE_FOR_nothing
+ || !targetm.optab_supported_p (optab, to_mode, from_mode, opt_type))
+ return CODE_FOR_nothing;
+ return icode;
+}
+
+/* Return the insn used to implement mode MODE of OP; return
+ CODE_FOR_nothing if the target does not have such an insn,
+ or if it is unsuitable for optimization type OPT_TYPE. */
+
+insn_code
+direct_optab_handler (convert_optab optab, machine_mode mode,
+ optimization_type opt_type)
+{
+ insn_code icode = direct_optab_handler (optab, mode);
+ if (icode == CODE_FOR_nothing
+ || !targetm.optab_supported_p (optab, mode, mode, opt_type))
+ return CODE_FOR_nothing;
+ return icode;
+}
+
/* Enumerates the possible types of structure operand to an
extraction_insn. */
enum extraction_type { ET_unaligned_mem, ET_reg };
diff --git a/gcc/optabs-query.h b/gcc/optabs-query.h
index 48bcf7c71d2..8a5f042b461 100644
--- a/gcc/optabs-query.h
+++ b/gcc/optabs-query.h
@@ -46,6 +46,9 @@ convert_optab_handler (convert_optab op, machine_mode to_mode,
return raw_optab_handler (scode);
}
+enum insn_code convert_optab_handler (convert_optab, machine_mode,
+ machine_mode, optimization_type);
+
/* Return the insn used to implement mode MODE of OP, or CODE_FOR_nothing
if the target does not have such an insn. */
@@ -55,6 +58,9 @@ direct_optab_handler (direct_optab op, machine_mode mode)
return optab_handler (op, mode);
}
+enum insn_code direct_optab_handler (convert_optab, machine_mode,
+ optimization_type);
+
/* Return true if UNOPTAB is for a trapping-on-overflow operation. */
inline bool
diff --git a/gcc/optabs.c b/gcc/optabs.c
index 550764293b9..8cc4802f339 100644
--- a/gcc/optabs.c
+++ b/gcc/optabs.c
@@ -2223,6 +2223,58 @@ expand_doubleword_clz (machine_mode mode, rtx op0, rtx target)
return 0;
}
+/* Try calculating popcount of a double-word quantity as two popcount's of
+ word-sized quantities and summing up the results. */
+static rtx
+expand_doubleword_popcount (machine_mode mode, rtx op0, rtx target)
+{
+ rtx t0, t1, t;
+ rtx_insn *seq;
+
+ start_sequence ();
+
+ t0 = expand_unop_direct (word_mode, popcount_optab,
+ operand_subword_force (op0, 0, mode), NULL_RTX,
+ true);
+ t1 = expand_unop_direct (word_mode, popcount_optab,
+ operand_subword_force (op0, 1, mode), NULL_RTX,
+ true);
+ if (!t0 || !t1)
+ {
+ end_sequence ();
+ return NULL_RTX;
+ }
+
+ /* If we were not given a target, use a word_mode register, not a
+ 'mode' register. The result will fit, and nobody is expecting
+ anything bigger (the return type of __builtin_popcount* is int). */
+ if (!target)
+ target = gen_reg_rtx (word_mode);
+
+ t = expand_binop (word_mode, add_optab, t0, t1, target, 0, OPTAB_DIRECT);
+
+ seq = get_insns ();
+ end_sequence ();
+
+ add_equal_note (seq, t, POPCOUNT, op0, 0);
+ emit_insn (seq);
+ return t;
+}
+
+/* Try calculating
+ (parity:wide x)
+ as
+ (parity:narrow (low (x) ^ high (x))) */
+static rtx
+expand_doubleword_parity (machine_mode mode, rtx op0, rtx target)
+{
+ rtx t = expand_binop (word_mode, xor_optab,
+ operand_subword_force (op0, 0, mode),
+ operand_subword_force (op0, 1, mode),
+ NULL_RTX, 0, OPTAB_DIRECT);
+ return expand_unop (word_mode, parity_optab, t, target, true);
+}
+
/* Try calculating
(bswap:narrow x)
as
@@ -2582,7 +2634,7 @@ expand_absneg_bit (enum rtx_code code, machine_mode mode,
different mode or with a libcall. */
static rtx
expand_unop_direct (machine_mode mode, optab unoptab, rtx op0, rtx target,
- int unsignedp)
+ int unsignedp)
{
if (optab_handler (unoptab, mode) != CODE_FOR_nothing)
{
@@ -2665,6 +2717,27 @@ expand_unop (machine_mode mode, optab unoptab, rtx op0, rtx target,
goto try_libcall;
}
+ if (unoptab == popcount_optab
+ && GET_MODE_SIZE (mode) == 2 * UNITS_PER_WORD
+ && optab_handler (unoptab, word_mode) != CODE_FOR_nothing
+ && optimize_insn_for_speed_p ())
+ {
+ temp = expand_doubleword_popcount (mode, op0, target);
+ if (temp)
+ return temp;
+ }
+
+ if (unoptab == parity_optab
+ && GET_MODE_SIZE (mode) == 2 * UNITS_PER_WORD
+ && (optab_handler (unoptab, word_mode) != CODE_FOR_nothing
+ || optab_handler (popcount_optab, word_mode) != CODE_FOR_nothing)
+ && optimize_insn_for_speed_p ())
+ {
+ temp = expand_doubleword_parity (mode, op0, target);
+ if (temp)
+ return temp;
+ }
+
/* Widening (or narrowing) bswap needs special treatment. */
if (unoptab == bswap_optab)
{
diff --git a/gcc/optabs.def b/gcc/optabs.def
index 20e4225d733..a19466e3611 100644
--- a/gcc/optabs.def
+++ b/gcc/optabs.def
@@ -17,8 +17,29 @@ You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
-/* Entries here are categorized C, D, N, V. See genopinit.c for details
- on the meaning of the categories and for the pattern dollar codes. */
+/* The entries in optabs.def are categorized:
+ C: A "conversion" optab, which uses two modes; has libcall data.
+ N: A "normal" optab, which uses one mode; has libcall data.
+ D: A "direct" optab, which uses one mode; does not have libcall data.
+ V: An "oVerflow" optab. Like N, but does not record its code in
+ code_to_optab.
+
+ CX, NX, VX: An extra pattern entry for a conversion or normal optab.
+
+ These patterns may be present in the MD file with names that contain
+ the mode(s) used and the name of the operation. This array contains
+ a list of optabs that need to be initialized. Within each name,
+ $a and $b are used to match a short mode name (the part of the mode
+ name not including `mode' and converted to lower-case).
+
+ $I means that only full integer modes should be considered for the
+ next mode, and $F means that only float modes should be considered.
+ $P means that both full and partial integer modes should be considered.
+ $Q means that only fixed-point modes should be considered.
+
+ The pattern may be NULL if the optab exists only for the libcalls
+ that we plan to attach to it, and there are no named patterns in
+ the md files. */
/* The extension libcalls are used for float extension. */
OPTAB_CL(sext_optab, "extend$b$a2", SIGN_EXTEND, "extend", gen_extend_conv_libfunc)
@@ -246,6 +267,7 @@ OPTAB_D (log_optab, "log$a2")
OPTAB_D (logb_optab, "logb$a2")
OPTAB_D (pow_optab, "pow$a3")
OPTAB_D (remainder_optab, "remainder$a3")
+OPTAB_D (rsqrt_optab, "rsqrt$a2")
OPTAB_D (scalb_optab, "scalb$a3")
OPTAB_D (signbit_optab, "signbit$F$a2")
OPTAB_D (significand_optab, "significand$a2")
diff --git a/gcc/opts-common.c b/gcc/opts-common.c
index d9bf4d4b897..24967cc4a25 100644
--- a/gcc/opts-common.c
+++ b/gcc/opts-common.c
@@ -885,7 +885,7 @@ keep:
}
}
- if (fdiagnostics_color_idx > 1)
+ if (fdiagnostics_color_idx >= 1)
{
/* We put the last -fdiagnostics-color= at the first position
after argv[0] so it can take effect immediately. */
diff --git a/gcc/passes.c b/gcc/passes.c
index 0e23dcbec78..ba9bfc276b1 100644
--- a/gcc/passes.c
+++ b/gcc/passes.c
@@ -2218,6 +2218,7 @@ execute_one_ipa_transform_pass (struct cgraph_node *node,
pass_fini_dump_file (pass);
current_pass = NULL;
+ redirect_edge_var_map_empty ();
/* Signal this is a suitable GC collection point. */
if (!(todo_after & TODO_do_not_ggc_collect))
@@ -2370,6 +2371,7 @@ execute_one_pass (opt_pass *pass)
|| pass->type != RTL_PASS);
current_pass = NULL;
+ redirect_edge_var_map_empty ();
if (todo_after & TODO_discard_function)
{
diff --git a/gcc/predict.c b/gcc/predict.c
index 7e0f848f177..d5c40def863 100644
--- a/gcc/predict.c
+++ b/gcc/predict.c
@@ -269,6 +269,16 @@ optimize_function_for_speed_p (struct function *fun)
return !optimize_function_for_size_p (fun);
}
+/* Return the optimization type that should be used for the function FUN. */
+
+optimization_type
+function_optimization_type (struct function *fun)
+{
+ return (optimize_function_for_speed_p (fun)
+ ? OPTIMIZE_FOR_SPEED
+ : OPTIMIZE_FOR_SIZE);
+}
+
/* Return TRUE when BB should be optimized for size. */
bool
@@ -286,6 +296,16 @@ optimize_bb_for_speed_p (const_basic_block bb)
return !optimize_bb_for_size_p (bb);
}
+/* Return the optimization type that should be used for block BB. */
+
+optimization_type
+bb_optimization_type (const_basic_block bb)
+{
+ return (optimize_bb_for_speed_p (bb)
+ ? OPTIMIZE_FOR_SPEED
+ : OPTIMIZE_FOR_SIZE);
+}
+
/* Return TRUE when BB should be optimized for size. */
bool
diff --git a/gcc/predict.h b/gcc/predict.h
index 85150fe8b6f..486ce171f87 100644
--- a/gcc/predict.h
+++ b/gcc/predict.h
@@ -54,8 +54,10 @@ extern bool probably_never_executed_bb_p (struct function *, const_basic_block);
extern bool probably_never_executed_edge_p (struct function *, edge);
extern bool optimize_function_for_size_p (struct function *);
extern bool optimize_function_for_speed_p (struct function *);
+extern optimization_type function_optimization_type (struct function *);
extern bool optimize_bb_for_size_p (const_basic_block);
extern bool optimize_bb_for_speed_p (const_basic_block);
+extern optimization_type bb_optimization_type (const_basic_block);
extern bool optimize_edge_for_size_p (edge);
extern bool optimize_edge_for_speed_p (edge);
extern bool optimize_insn_for_size_p (void);
diff --git a/gcc/regrename.c b/gcc/regrename.c
index e2a1e83c7ea..701e0789955 100644
--- a/gcc/regrename.c
+++ b/gcc/regrename.c
@@ -1677,6 +1677,12 @@ build_def_use (basic_block bb)
untracked_operands |= 1 << matches;
}
}
+#ifdef STACK_REGS
+ if (regstack_completed
+ && REG_P (op)
+ && IN_RANGE (REGNO (op), FIRST_STACK_REG, LAST_STACK_REG))
+ untracked_operands |= 1 << i;
+#endif
/* If there's an in-out operand with a register that is not
being tracked at all yet, open a chain. */
if (recog_data.operand_type[i] == OP_INOUT
diff --git a/gcc/target.def b/gcc/target.def
index 1d40012c5a2..d7543378fe7 100644
--- a/gcc/target.def
+++ b/gcc/target.def
@@ -2459,13 +2459,13 @@ identical versions.",
tree, (void *decl), NULL)
/* Returns a code for a target-specific builtin that implements
- reciprocal of the function, or NULL_TREE if not available. */
+ reciprocal of a target-specific function, or NULL_TREE if not available. */
DEFHOOK
(builtin_reciprocal,
- "This hook should return the DECL of a function that implements reciprocal of\n\
-the builtin or internal function call @var{call}, or\n\
+ "This hook should return the DECL of a function that implements the\n\
+reciprocal of the machine-specific builtin function @var{fndecl}, or\n\
@code{NULL_TREE} if such a function is not available.",
- tree, (gcall *call),
+ tree, (tree fndecl),
default_builtin_reciprocal)
/* For a vendor-specific TYPE, return a pointer to a statically-allocated
@@ -3434,6 +3434,23 @@ move would be greater than that of a library call.",
enum by_pieces_operation op, bool speed_p),
default_use_by_pieces_infrastructure_p)
+DEFHOOK
+(optab_supported_p,
+ "Return true if the optimizers should use optab @var{op} with\n\
+modes @var{mode1} and @var{mode2} for optimization type @var{opt_type}.\n\
+The optab is known to have an associated @file{.md} instruction\n\
+whose C condition is true. @var{mode2} is only meaningful for conversion\n\
+optabs; for direct optabs it is a copy of @var{mode1}.\n\
+\n\
+For example, when called with @var{op} equal to @code{rint_optab} and\n\
+@var{mode1} equal to @code{DFmode}, the hook should say whether the\n\
+optimizers should use optab @code{rintdf2}.\n\
+\n\
+The default hook returns true for all inputs.",
+ bool, (int op, machine_mode mode1, machine_mode mode2,
+ optimization_type opt_type),
+ default_optab_supported_p)
+
/* True for MODE if the target expects that registers in this mode will
be allocated to registers in a small register class. The compiler is
allowed to use registers explicitly used in the rtl as spill registers
diff --git a/gcc/targhooks.c b/gcc/targhooks.c
index 3868230c662..dcf08631c40 100644
--- a/gcc/targhooks.c
+++ b/gcc/targhooks.c
@@ -600,7 +600,7 @@ default_builtin_vectorization_cost (enum vect_cost_for_stmt type_of_cost,
/* Reciprocal. */
tree
-default_builtin_reciprocal (gcall *)
+default_builtin_reciprocal (tree)
{
return NULL_TREE;
}
@@ -1953,4 +1953,12 @@ can_use_doloop_if_innermost (const widest_int &, const widest_int &,
return loop_depth == 1;
}
+/* Default implementation of TARGET_OPTAB_SUPPORTED_P. */
+
+bool
+default_optab_supported_p (int, machine_mode, machine_mode, optimization_type)
+{
+ return true;
+}
+
#include "gt-targhooks.h"
diff --git a/gcc/targhooks.h b/gcc/targhooks.h
index c8094704c09..47b5cfc3b8b 100644
--- a/gcc/targhooks.h
+++ b/gcc/targhooks.h
@@ -90,7 +90,7 @@ extern tree default_builtin_vectorized_conversion (unsigned int, tree, tree);
extern int default_builtin_vectorization_cost (enum vect_cost_for_stmt, tree, int);
-extern tree default_builtin_reciprocal (gcall *);
+extern tree default_builtin_reciprocal (tree);
extern HOST_WIDE_INT default_vector_alignment (const_tree);
@@ -250,4 +250,7 @@ extern void default_setup_incoming_vararg_bounds (cumulative_args_t ca ATTRIBUTE
tree type ATTRIBUTE_UNUSED,
int *pretend_arg_size ATTRIBUTE_UNUSED,
int second_time ATTRIBUTE_UNUSED);
+extern bool default_optab_supported_p (int, machine_mode, machine_mode,
+ optimization_type);
+
#endif /* GCC_TARGHOOKS_H */
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 6e17cc4f207..ca604d26b4c 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,319 @@
+2015-12-04 Eric Botcazou <ebotcazou@adacore.com>
+
+ * gcc.dg/sso-9.c: New test.
+
+2015-12-04 Jakub Jelinek <jakub@redhat.com>
+
+ PR target/68655
+ * gcc.dg/torture/vshuf-4.inc (TESTS): Add one extra test.
+ * gcc.dg/torture/vshuf-4.inc (TESTS): Add two extra tests.
+
+2015-12-03 Bernd Schmidt <bschmidt@redhat.com>
+
+ PR target/68472
+ * gcc.target/i386/rop1.c: New test.
+
+2015-12-03 Nathan Sidwell <nathan@acm.org>
+
+ * gcc.target/nvptx/decl.c: New.
+ * gcc.target/nvptx/uninit-decl.c: Robustify regexps.
+
+2015-12-03 Kyrylo Tkachov <kyrylo.tkachov@arm.com>
+
+ PR rtl-optimization/68624
+ * gcc.c-torture/execute/pr68624.c: New test.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/66051
+ * gcc.dg/vect/slp-42.c: New testcase.
+
+2015-12-02 Kirill Yukhin <kirill.yukhin@intel.com>
+
+ * gcc.target/i386/avx512vl-vextractf32x4-1.c: Fix scan pattern.
+ * gcc.target/i386/avx512vl-vextracti32x4-1.c: Fix scan pattern.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/67800
+ PR tree-optimization/68333
+ * gcc.target/i386/vect-pr67800.c: New testcase.
+
+2015-12-03 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68639
+ * gfortran.fortran-torture/compile/pr68639.f90: New testcase.
+
+2015-12-02 Jan Hubicka <hubicka@ucw.cz>
+
+ PR ipa/68184
+ * g++.dg/torture/pr68184.C: New testcase.
+
+2015-12-03 Jakub Jelinek <jakub@redhat.com>
+
+ PR preprocessor/57580
+ * c-c++-common/cpp/pr57580.c: New test.
+ * c-c++-common/gomp/pr57580.c: New test.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * gcc.dg/graphite/id-28.c: New.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * gfortran.dg/graphite/id-26.f03: New.
+
+2015-12-02 Jason Merrill <jason@redhat.com>
+
+ * lib/g++.exp: Handle --stds= option.
+ * lib/g++-dg.exp (g++-dg-runtest): Use it.
+
+2015-12-02 Tobias Burnus <burnus@net-b.de>
+ Alessandro Fanfarillo <fanfarillo.gcc@gmail.com>
+
+ * gfortran.dg/coarray/event_1.f90: New.
+ * gfortran.dg/coarray/event_2.f90: New.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ PR tree-optimization/68550
+ * gfortran.dg/graphite/pr68550-1.f90: New.
+ * gfortran.dg/graphite/pr68550-2.f90: New.
+
+>>>>>>> .r231221
+2015-12-02 Marek Polacek <polacek@redhat.com>
+
+ PR c/68513
+ * gcc.dg/pr68513.c: New test.
+
+2015-12-02 Cesar Philippidis <cesar@codesourcery.com>
+
+ PR fortran/63861
+ * gfortran.dg/goacc/array-reduction.f90: New test.
+ * gfortran.dg/goacc/assumed.f95: Update expected diagnostics.
+ * gfortran.dg/goacc/coarray.f95: Likewise.
+ * gfortran.dg/goacc/coarray_2.f90: Likewise.
+ * gfortran.dg/goacc/reduction-2.f95: Likewise.
+ * gfortran.dg/goacc/reduction.f95: Likewise.
+
+2015-12-02 Jakub Jelinek <jakub@redhat.com>
+
+ PR target/68647
+ * gcc.target/i386/pr68647.c: New test.
+
+2015-12-02 Marek Polacek <polacek@redhat.com>
+
+ PR c++/68653
+ * g++.dg/warn/nonnull3.C: New test.
+
+2015-12-02 Joseph Myers <joseph@codesourcery.com>
+
+ PR c/68162
+ * gcc.dg/pr68162-1.c: New test.
+
+2015-12-02 Aditya Kumar <aditya.k7@samsung.com>
+ Sebastian Pop <s.pop@samsung.com>
+
+ * gfortran.dg/graphite/run-id-3.f90: New.
+
+2015-12-02 David Sherwood <david.sherwood@arm.com>
+
+ * gcc.target/aarch64/fmaxmin.c: New test.
+
+2015-12-02 Thomas Schwinge <thomas@codesourcery.com>
+
+ * gfortran.dg/goacc/coarray.f95: XFAIL.
+ * gfortran.dg/goacc/coarray_2.f90: Adjust dg-excess-errors
+ directive.
+ * gfortran.dg/goacc/host_data-tree.f95: Remove dg-prune-output
+ directive.
+
+2015-12-02 Thomas Schwinge <thomas@codesourcery.com>
+ Julian Brown <julian@codesourcery.com>
+ James Norris <James_Norris@mentor.com>
+
+ * c-c++-common/goacc/host_data-5.c: New file.
+ * c-c++-common/goacc/host_data-6.c: Likewise.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * c-c++-common/goacc/kernels-default-2.c: New test.
+ * c-c++-common/goacc/kernels-default.c: New test.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * c-c++-common/goacc/kernels-alias-2.c: New test.
+ * c-c++-common/goacc/kernels-alias-3.c: New test.
+ * c-c++-common/goacc/kernels-alias-4.c: New test.
+ * c-c++-common/goacc/kernels-alias-5.c: New test.
+ * c-c++-common/goacc/kernels-alias-6.c: New test.
+ * c-c++-common/goacc/kernels-alias-7.c: New test.
+ * c-c++-common/goacc/kernels-alias-8.c: New test.
+ * c-c++-common/goacc/kernels-alias.c: New test.
+
+2015-12-02 Tom de Vries <tom@codesourcery.com>
+
+ * c-c++-common/goacc/kernels-alias-ipa-pta-2.c: New test.
+ * c-c++-common/goacc/kernels-alias-ipa-pta-3.c: New test.
+ * c-c++-common/goacc/kernels-alias-ipa-pta.c: New test.
+
+2015-12-02 Richard Biener <rguenther@suse.de>
+
+ * gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c: Fix uninitialized
+ y guarding a call to abort ().
+ * gcc.dg/vect/vect-strided-a-u8-i8-gap7.c: Likewise.
+ * gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c: Likewise.
+
+2015-12-02 Marek Polacek <polacek@redhat.com>
+
+ PR middle-end/68570
+ * gcc.dg/torture/pr68570.c: New test.
+
+2015-12-02 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68625
+ * gcc.dg/torture/pr68625.c: New testcase.
+
+2015-12-02 Richard Sandiford <richard.sandiford@arm.com>
+
+ * gcc.target/i386/pr68432-1.c: New test.
+ * gcc.target/i386/pr68432-2.c: Likewise.
+ * gcc.target/i386/pr68432-3.c: Likewise.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.target/s390/zvector/vec-splat-2.c: New test.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.target/s390/vector/vec-vrepi-1.c: New test.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.target/s390/zvector/vec-splat-1.c: New test.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.target/s390/bswap-1.c (foo64c, foo32a, foo32c): New functions.
+ * gcc.target/s390/bswaphi-1.c: New test.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * lib/target-supports.exp: Add s390 and s390x to the list of long
+ long atomic targets.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.dg/optimize-bswapdi-1.c: Force using -mzarch on s390 and
+ s390x to enable 64 bit bswap patterns.
+ * gcc.dg/optimize-bswapdi-2.c: Likewise.
+ * gcc.dg/optimize-bswapdi-3.c: Likewise.
+ * lib/target-supports.exp: Add a comment for s390.
+
+2015-12-02 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
+
+ * gcc.dg/builtin-bswap-6a.c: Add -march=z900 for s390 and s390x in
+ order to make -m31 work.
+ * gcc.dg/optimize-bswapsi-1.c: Likewise.
+ * gcc.dg/optimize-bswapsi-2.c: Likewise.
+
+2015-12-02 Jakub Jelinek <jakub@redhat.com>
+
+ PR c/68533
+ * gcc.dg/pr68533.c: New test.
+
+2015-12-01 Richard Sandiford <richard.sandiford@arm.com>
+
+ PR tree-optimization/68577
+ * gcc.dg/vect/pr68577.c: New test.
+
+2015-12-01 Nathan Sidwell <nathan@acm.org>
+
+ * gcc.target/nvptx/uninit-decl.c: New.
+
+2015-12-01 Jan Hubicka <hubicka@ucw.cz>
+
+ * gcc.c-torture/execute/alias-1.c: New testcase.
+
+2015-12-01 Marek Polacek <polacek@redhat.com>
+
+ PR tree-optimization/64769
+ * c-c++-common/gomp/pr64769.c: New test.
+
+2015-12-01 Bill Schmidt <wschmidt@linux.vnet.ibm.com>
+
+ * gcc.target/powerpc/swaps-p8-22.c: New.
+
+2015-12-01 Marek Polacek <polacek@redhat.com>
+
+ PR tree-optimization/67916
+ * gcc.dg/torture/pr67916.c: New test.
+
+2015-12-01 Marek Polacek <polacek@redhat.com>
+
+ PR middle-end/68582
+ * c-c++-common/pr68582.c: New test.
+
+2015-12-01 Richard Sandiford <richard.sandiford@arm.com>
+
+ PR tree-optimization/68474
+ * gcc.dg/pr68474.c: New test.
+
+2015-12-01 Christian Bruel <christian.bruel@st.com>
+
+ PR target/68617
+ * gcc.target/arm/attr-unaligned-load-ice.c: New test.
+
+2015-12-01 Tom de Vries <tom@codesourcery.com>
+
+ * gcc.dg/pr46032.c: Move to ...
+ * gcc.dg/vect/pr46032.c: here. Add dg-require-effective-target
+ vect_int.
+ * gcc.dg/pr46032-2.c: Move to ...
+ * gcc.dg/gomp/pr46032-2.c: ... here. Drop dg-require-effective-target fopenmp.
+ * gcc.dg/pr46032-3.c: Move to ...
+ * gcc.dg/gomp/pr46032-3.c: ... here. Drop dg-require-effective-target fopenmp.
+
+2015-12-01 Cesar Philippidis <cesar@codesourcery.com>
+
+ * gfortran.dg/goacc/gang-static.f95: Add tests for gang num arguments.
+ * gfortran.dg/goacc/loop-2.f95: Update expected diagnostics.
+ * gfortran.dg/goacc/loop-6.f95: Likewise.
+ * gfortran.dg/goacc/loop-7.f95: New test.
+ * gfortran.dg/goacc/reduction-2.f95: New test.
+
+2015-12-01 Richard Biener <rguenther@suse.de>
+
+ PR tree-optimization/68379
+ * gcc.dg/torture/pr68379.c: New testcase.
+ * gfortran.dg/pr68379-1.f90: Likewise.
+ * gfortran.dg/pr68379-2.f: Likewise.
+
+2015-12-01 Christophe Lyon <christophe.lyon@linaro.org>
+
+ * gcc.dg/pr46032.c: Add dg-require-effective-target fopenmp.
+ * gcc.dg/pr46032-2.c: Likewise.
+ * gcc.dg/pr46032-3.c: Likewise.
+
+2015-12-01 Richard Biener <rguenther@suse.de>
+
+ PR ipa/68470
+ * g++.dg/torture/pr68470.C: New testcase.
+
+2015-12-01 Ilya Enkovich <enkovich.gnu@gmail.com>
+
+ PR middle-end/68595
+ * gcc.dg/pr68595.c: New test.
+
+2015-12-01 Christian Bruel <christian.bruel@st.com>
+
+ * gcc.target/arm/ftest-armv6-thumb.c: Remove NEED_ARM_FEATURE_UNALIGNED.
+ * gcc.target/arm/ftest-armv6k-thumb.c: Likewise.
+ * gcc.target/arm/ftest-armv6z-thumb.c: Likewise.
+
2015-12-01 Bin Cheng <bin.cheng@arm.com>
PR tree-optimization/68529
@@ -205,7 +521,7 @@
2015-11-30 Andreas Krebbel <krebbel@linux.vnet.ibm.com>
- * gcc.target/s390/load-relative-check.c: Add -mzarch.
+ * gcc.target/s390/load-relative-check.c: Add -mzarch.
2015-11-30 Eric Botcazou <ebotcazou@adacore.com>
diff --git a/gcc/testsuite/c-c++-common/cpp/pr57580.c b/gcc/testsuite/c-c++-common/cpp/pr57580.c
new file mode 100644
index 00000000000..1039e213e1c
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/cpp/pr57580.c
@@ -0,0 +1,9 @@
+/* PR preprocessor/57580 */
+/* { dg-do compile } */
+/* { dg-options "-save-temps" } */
+
+#define MSG \
+ _Pragma("message(\"message0\")") \
+ _Pragma("message(\"message1\")")
+MSG /* { dg-message "message0" } */
+/* { dg-message "message1" "" { target *-*-* } 8 } */
diff --git a/gcc/testsuite/c-c++-common/goacc/host_data-5.c b/gcc/testsuite/c-c++-common/goacc/host_data-5.c
new file mode 100644
index 00000000000..f372fbdc437
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/host_data-5.c
@@ -0,0 +1,23 @@
+/* { dg-do compile } */
+
+#define N 1024
+
+int main (int argc, char* argv[])
+{
+ int x[N];
+
+#pragma acc data copyin (x[0:N])
+ {
+ int *xp;
+#pragma acc host_data use_device (x)
+ {
+ /* This use of the present clause is undefined behaviour for OpenACC. */
+#pragma acc parallel present (x) copyout (xp) /* { dg-error "variable 'x' declared in enclosing 'host_data' region" } */
+ {
+ xp = x;
+ }
+ }
+ }
+
+ return 0;
+}
diff --git a/gcc/testsuite/c-c++-common/goacc/host_data-6.c b/gcc/testsuite/c-c++-common/goacc/host_data-6.c
new file mode 100644
index 00000000000..8be7912e280
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/host_data-6.c
@@ -0,0 +1,25 @@
+/* { dg-do compile } */
+
+#define N 1024
+
+int main (int argc, char* argv[])
+{
+ int x[N];
+
+#pragma acc data copyin (x[0:N])
+ {
+ int *xp;
+#pragma acc host_data use_device (x)
+ {
+ /* Here 'x' being implicitly firstprivate for the parallel region
+ conflicts with it being declared as use_device in the enclosing
+ host_data region. */
+#pragma acc parallel copyout (xp)
+ {
+ xp = x; /* { dg-error "variable 'x' declared in enclosing 'host_data' region" } */
+ }
+ }
+ }
+
+ return 0;
+}
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-2.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-2.c
new file mode 100644
index 00000000000..d437c47779d
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-2.c
@@ -0,0 +1,27 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+void
+foo (void)
+{
+ unsigned int a;
+ unsigned int b;
+ unsigned int c;
+ unsigned int d;
+
+#pragma acc kernels copyin (a) create (b) copyout (c) copy (d)
+ {
+ a = 0;
+ b = 0;
+ c = 0;
+ d = 0;
+ }
+}
+
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 4 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 2" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 3" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 4" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 5" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 8 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-3.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-3.c
new file mode 100644
index 00000000000..0eda7e17c3b
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-3.c
@@ -0,0 +1,20 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+void
+foo (void)
+{
+ unsigned int a;
+ unsigned int *p = &a;
+
+#pragma acc kernels pcopyin (a, p[0:1])
+ {
+ a = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-4.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-4.c
new file mode 100644
index 00000000000..037901fcffb
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-4.c
@@ -0,0 +1,22 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int a[N];
+ unsigned int *p = &a[0];
+
+#pragma acc kernels pcopyin (a, p[0:2])
+ {
+ a[0] = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-5.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-5.c
new file mode 100644
index 00000000000..69cd3fb9449
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-5.c
@@ -0,0 +1,19 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+void
+foo (int *a)
+{
+ int *p = a;
+
+#pragma acc kernels pcopyin (a[0:1], p[0:1])
+ {
+ *a = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-6.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-6.c
new file mode 100644
index 00000000000..6ebce15f5e2
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-6.c
@@ -0,0 +1,23 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+typedef __SIZE_TYPE__ size_t;
+extern void *acc_copyin (void *, size_t);
+
+void
+foo (void)
+{
+ int a = 0;
+ int *p = (int *)acc_copyin (&a, sizeof (a));
+
+#pragma acc kernels deviceptr (p) pcopy(a)
+ {
+ a = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-7.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-7.c
new file mode 100644
index 00000000000..40eb235d601
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-7.c
@@ -0,0 +1,25 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+typedef __SIZE_TYPE__ size_t;
+extern void *acc_copyin (void *, size_t);
+
+#define N 2
+
+void
+foo (void)
+{
+ int a[N];
+ int *p = (int *)acc_copyin (&a[0], sizeof (a));
+
+#pragma acc kernels deviceptr (p) pcopy(a)
+ {
+ a[0] = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-8.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-8.c
new file mode 100644
index 00000000000..0b93e35909b
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-8.c
@@ -0,0 +1,22 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+typedef __SIZE_TYPE__ size_t;
+extern void *acc_copyin (void *, size_t);
+
+void
+foo (int *a, size_t n)
+{
+ int *p = (int *)acc_copyin (&a, n);
+
+#pragma acc kernels deviceptr (p) pcopy(a[0:n])
+ {
+ a = 0;
+ *p = 1;
+ }
+}
+
+/* Only the omp_data_i related loads should be annotated with cliques. */
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 2 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 2 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-2.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-2.c
new file mode 100644
index 00000000000..f16d698af0d
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-2.c
@@ -0,0 +1,37 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fipa-pta -fdump-tree-optimized" } */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+typedef __SIZE_TYPE__ size_t;
+void *malloc (size_t);
+void free (void *);
+#ifdef __cplusplus
+}
+#endif
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int *a = (unsigned int *)malloc (N * sizeof (unsigned int));
+ unsigned int *b = (unsigned int *)malloc (N * sizeof (unsigned int));
+ unsigned int *c = (unsigned int *)malloc (N * sizeof (unsigned int));
+
+#pragma acc kernels pcopyout (a[0:N], b[0:N], c[0:N])
+ {
+ a[0] = 0;
+ b[0] = 1;
+ c[0] = a[0];
+ }
+
+ free (a);
+ free (b);
+ free (c);
+}
+
+/* { dg-final { scan-tree-dump-times "(?n)= 0;$" 2 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= 1;$" 1 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= \\*a" 0 "optimized" } } */
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-3.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-3.c
new file mode 100644
index 00000000000..1eb56eb9e62
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta-3.c
@@ -0,0 +1,36 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fipa-pta -fdump-tree-optimized" } */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+typedef __SIZE_TYPE__ size_t;
+void *malloc (size_t);
+void free (void *);
+#ifdef __cplusplus
+}
+#endif
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int *a = (unsigned int *)malloc (N * sizeof (unsigned int));
+ unsigned int *b = a;
+ unsigned int *c = (unsigned int *)malloc (N * sizeof (unsigned int));
+
+#pragma acc kernels pcopyout (a[0:N], b[0:N], c[0:N])
+ {
+ a[0] = 0;
+ b[0] = 1;
+ c[0] = a[0];
+ }
+
+ free (a);
+ free (c);
+}
+
+/* { dg-final { scan-tree-dump-times "(?n)= 0;$" 1 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= 1;$" 1 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= \\*a" 1 "optimized" } } */
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta.c
new file mode 100644
index 00000000000..969b466e8a8
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias-ipa-pta.c
@@ -0,0 +1,23 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fipa-pta -fdump-tree-optimized" } */
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int a[N];
+ unsigned int b[N];
+ unsigned int c[N];
+
+#pragma acc kernels pcopyout (a, b, c)
+ {
+ a[0] = 0;
+ b[0] = 1;
+ c[0] = a[0];
+ }
+}
+
+/* { dg-final { scan-tree-dump-times "(?n)= 0;$" 2 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= 1;$" 1 "optimized" } } */
+/* { dg-final { scan-tree-dump-times "(?n)= \\*_\[0-9\]\\\[0\\\];$" 0 "optimized" } } */
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-alias.c b/gcc/testsuite/c-c++-common/goacc/kernels-alias.c
new file mode 100644
index 00000000000..25821ab2aea
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-alias.c
@@ -0,0 +1,29 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-ealias-all" } */
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int a[N];
+ unsigned int b[N];
+ unsigned int c[N];
+ unsigned int d[N];
+
+#pragma acc kernels copyin (a) create (b) copyout (c) copy (d)
+ {
+ a[0] = 0;
+ b[0] = 0;
+ c[0] = 0;
+ d[0] = 0;
+ }
+}
+
+/* { dg-final { scan-tree-dump-times "clique 1 base 1" 4 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 2" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 3" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 4" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "clique 1 base 5" 1 "ealias" } } */
+/* { dg-final { scan-tree-dump-times "(?n)clique .* base .*" 8 "ealias" } } */
+
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-default-2.c b/gcc/testsuite/c-c++-common/goacc/kernels-default-2.c
new file mode 100644
index 00000000000..232b1236f38
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-default-2.c
@@ -0,0 +1,17 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-gimple" } */
+
+#define N 2
+
+void
+foo (void)
+{
+ unsigned int a[N];
+
+#pragma acc kernels
+ {
+ a[0]++;
+ }
+}
+
+/* { dg-final { scan-tree-dump-times "map\\(tofrom" 1 "gimple" } } */
diff --git a/gcc/testsuite/c-c++-common/goacc/kernels-default.c b/gcc/testsuite/c-c++-common/goacc/kernels-default.c
new file mode 100644
index 00000000000..58cd5e10a5b
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/goacc/kernels-default.c
@@ -0,0 +1,14 @@
+/* { dg-additional-options "-O2" } */
+/* { dg-additional-options "-fdump-tree-gimple" } */
+
+void
+foo (void)
+{
+ unsigned int i;
+#pragma acc kernels
+ {
+ i++;
+ }
+}
+
+/* { dg-final { scan-tree-dump-times "map\\(force_tofrom" 1 "gimple" } } */
diff --git a/gcc/testsuite/c-c++-common/gomp/pr57580.c b/gcc/testsuite/c-c++-common/gomp/pr57580.c
new file mode 100644
index 00000000000..9bbe707ef37
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/gomp/pr57580.c
@@ -0,0 +1,36 @@
+/* PR preprocessor/57580 */
+/* { dg-do compile } */
+/* { dg-options "-fopenmp -save-temps -fdump-tree-gimple" } */
+
+#define PS \
+ _Pragma("omp parallel num_threads(2)") \
+ { \
+ _Pragma("omp single") \
+ { \
+ ret = 0; \
+ } \
+ }
+
+int
+main ()
+{
+ int ret;
+ _Pragma("omp parallel num_threads(3)")
+ {
+ _Pragma("omp single")
+ {
+ ret = 0;
+ }
+ }
+ _Pragma("omp parallel num_threads(4)") { _Pragma("omp single") { ret = 0; } }
+ { _Pragma("omp parallel num_threads(5)") { _Pragma("omp single") { ret = 0; } } }
+ PS
+ PS
+ return ret;
+}
+
+/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(2\\)" 2 "gimple" } } */
+/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(3\\)" 1 "gimple" } } */
+/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(4\\)" 1 "gimple" } } */
+/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(5\\)" 1 "gimple" } } */
+/* { dg-final { scan-tree-dump-times "#pragma omp single" 5 "gimple" } } */
diff --git a/gcc/testsuite/c-c++-common/gomp/pr64769.c b/gcc/testsuite/c-c++-common/gomp/pr64769.c
new file mode 100644
index 00000000000..3a301495f01
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/gomp/pr64769.c
@@ -0,0 +1,9 @@
+/* PR tree-optimization/64769 */
+/* { dg-do compile } */
+/* { dg-options "-fopenmp-simd" } */
+
+#pragma omp declare simd linear(i)
+void
+foo (int i)
+{
+}
diff --git a/gcc/testsuite/c-c++-common/pr68582.c b/gcc/testsuite/c-c++-common/pr68582.c
new file mode 100644
index 00000000000..95ca9a4f3b7
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/pr68582.c
@@ -0,0 +1,25 @@
+/* PR middle-end/68582 */
+/* { dg-do compile } */
+/* { dg-options "-Wunused-function" } */
+
+/* We failed to give the warning for functions with TREE_THIS_VOLATILE set. */
+
+static void
+fn1 (void) /* { dg-warning "defined but not used" } */
+{
+ __builtin_abort ();
+}
+
+__attribute__ ((noreturn))
+static void
+fn2 (void) /* { dg-warning "defined but not used" } */
+{
+ __builtin_abort ();
+}
+
+__attribute__ ((volatile))
+static void
+fn3 (void) /* { dg-warning "defined but not used" } */
+{
+ __builtin_abort ();
+}
diff --git a/gcc/testsuite/g++.dg/template/pr67337.C b/gcc/testsuite/g++.dg/template/pr67337.C
new file mode 100644
index 00000000000..df2651bc9a5
--- /dev/null
+++ b/gcc/testsuite/g++.dg/template/pr67337.C
@@ -0,0 +1,25 @@
+template <class> class A
+{
+ void m_fn1 (int *, int);
+};
+
+template <class> class B
+{
+public:
+ typedef int Type;
+};
+
+template <class> class C
+{
+public:
+ C (int);
+ template <template <class> class T> void m_fn2 (typename T<void>::Type);
+};
+
+template <>
+void
+A<int>::m_fn1 (int *, int)
+{
+ C<int> a (0);
+ a.m_fn2<B> (0);
+}
diff --git a/gcc/testsuite/g++.dg/torture/pr68184.C b/gcc/testsuite/g++.dg/torture/pr68184.C
new file mode 100644
index 00000000000..d0c7c84910c
--- /dev/null
+++ b/gcc/testsuite/g++.dg/torture/pr68184.C
@@ -0,0 +1,31 @@
+// { dg-do run }
+namespace {
+struct IFoo { virtual void foo() = 0; };
+struct IBar { virtual void bar() = 0; };
+
+struct FooBar : private IBar, private IFoo
+{
+ void call_foo()
+ {
+ try
+ {
+ static_cast<IFoo*>(this)->foo();
+ }
+ catch( ... ) {}
+ }
+ void foo() { throw 1; }
+ void bar() {}
+};
+
+void test()
+{
+ FooBar foobar;
+ foobar.call_foo();
+}
+}
+int main()
+{
+ test();
+ return 0;
+}
+
diff --git a/gcc/testsuite/g++.dg/torture/pr68470.C b/gcc/testsuite/g++.dg/torture/pr68470.C
new file mode 100644
index 00000000000..5dd558d15d2
--- /dev/null
+++ b/gcc/testsuite/g++.dg/torture/pr68470.C
@@ -0,0 +1,36 @@
+/* { dg-do compile } */
+
+void deallocate(void *);
+void *a;
+
+struct C {
+ virtual void m_fn1();
+};
+
+struct D {
+ C *m_fn2() {
+ if (a)
+ __builtin_abort();
+ }
+};
+D getd();
+
+struct vec_int {
+ int _M_start;
+ ~vec_int() {
+ if (_M_start)
+ deallocate(&_M_start);
+ }
+};
+vec_int *b;
+
+struct I {
+ virtual void m_fn3();
+};
+
+void I::m_fn3() {
+ if (a)
+ getd().m_fn2()->m_fn1();
+ b->~vec_int();
+}
+
diff --git a/gcc/testsuite/g++.dg/warn/Wnonnull1.C b/gcc/testsuite/g++.dg/warn/Wnonnull1.C
new file mode 100644
index 00000000000..0f610f449c7
--- /dev/null
+++ b/gcc/testsuite/g++.dg/warn/Wnonnull1.C
@@ -0,0 +1,7 @@
+// { dg-options -Wnonnull }
+
+void g(void *) __attribute__ ((nonnull (1)));
+void f(void *p)
+{
+ g(1 == 1 ? p : 0);
+}
diff --git a/gcc/testsuite/g++.dg/warn/nonnull3.C b/gcc/testsuite/g++.dg/warn/nonnull3.C
new file mode 100644
index 00000000000..d82fa31d957
--- /dev/null
+++ b/gcc/testsuite/g++.dg/warn/nonnull3.C
@@ -0,0 +1,19 @@
+// PR c++/68653
+// { dg-do compile { target c++11 } }
+// { dg-options "-Wall" }
+
+struct B;
+struct A {
+ template <typename T> __attribute__((nonnull)) bool foo (int T::*);
+ void bar (B *);
+};
+
+template <typename T> bool A::foo (int T::*p)
+{
+ return p;
+}
+void A::bar (B *)
+{
+ foo ((int B::*) nullptr);
+}
+// { dg-warning "nonnull argument" "" {target "*-*-*"} 0 }
diff --git a/gcc/testsuite/gcc.c-torture/execute/alias-1.c b/gcc/testsuite/gcc.c-torture/execute/alias-1.c
new file mode 100644
index 00000000000..666e96f968a
--- /dev/null
+++ b/gcc/testsuite/gcc.c-torture/execute/alias-1.c
@@ -0,0 +1,19 @@
+int val;
+
+int *ptr = &val;
+float *ptr2 = &val;
+
+__attribute__((optimize ("-fno-strict-aliasing")))
+typepun ()
+{
+ *ptr2=0;
+}
+
+main()
+{
+ *ptr=1;
+ typepun ();
+ if (*ptr)
+ __builtin_abort ();
+}
+
diff --git a/gcc/testsuite/gcc.c-torture/execute/pr68624.c b/gcc/testsuite/gcc.c-torture/execute/pr68624.c
new file mode 100644
index 00000000000..abb716b1550
--- /dev/null
+++ b/gcc/testsuite/gcc.c-torture/execute/pr68624.c
@@ -0,0 +1,30 @@
+int b, c, d, e = 1, f, g, h, j;
+
+static int
+fn1 ()
+{
+ int a = c;
+ if (h)
+ return 9;
+ g = (c || b) % e;
+ if ((g || f) && b)
+ return 9;
+ e = d;
+ for (c = 0; c > -4; c--)
+ ;
+ if (d)
+ c--;
+ j = c;
+ return d;
+}
+
+int
+main ()
+{
+ fn1 ();
+
+ if (c != -4)
+ __builtin_abort ();
+
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.dg/builtin-bswap-6a.c b/gcc/testsuite/gcc.dg/builtin-bswap-6a.c
index a8b953122b0..90dfd7d6242 100644
--- a/gcc/testsuite/gcc.dg/builtin-bswap-6a.c
+++ b/gcc/testsuite/gcc.dg/builtin-bswap-6a.c
@@ -1,7 +1,7 @@
/* { dg-do compile { target arm*-*-* alpha*-*-* i?86-*-* powerpc*-*-* rs6000-*-* x86_64-*-* s390*-*-* } } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-rtl-combine" } */
-/* { dg-additional-options "-march=z900" { target s390-*-* } } */
+/* { dg-additional-options "-march=z900" { target s390*-*-* } } */
/* The test is similiar to builtin-bswap-6.c but returns 1/2 instead
of 0/1 to prevent GCC from calculating the return value with
diff --git a/gcc/testsuite/gcc.dg/pr46032-2.c b/gcc/testsuite/gcc.dg/gomp/pr46032-2.c
index e110880bd8e..e110880bd8e 100644
--- a/gcc/testsuite/gcc.dg/pr46032-2.c
+++ b/gcc/testsuite/gcc.dg/gomp/pr46032-2.c
diff --git a/gcc/testsuite/gcc.dg/pr46032-3.c b/gcc/testsuite/gcc.dg/gomp/pr46032-3.c
index a4af7ec4a8a..a4af7ec4a8a 100644
--- a/gcc/testsuite/gcc.dg/pr46032-3.c
+++ b/gcc/testsuite/gcc.dg/gomp/pr46032-3.c
diff --git a/gcc/testsuite/gcc.dg/graphite/id-28.c b/gcc/testsuite/gcc.dg/graphite/id-28.c
new file mode 100644
index 00000000000..941a1e4f543
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/graphite/id-28.c
@@ -0,0 +1,72 @@
+/* { dg-options "-fcilkplus -floop-nest-optimize -O3" } */
+
+#if HAVE_IO
+#include <stdio.h>
+#endif
+#include <math.h>
+#define NUMBER 5
+
+int func1 (int *a1, int *a2)
+{
+ return __sec_reduce_add (a1[0:NUMBER] * a2[0:NUMBER:1]);
+}
+
+int func2 (int *a1, int *a2)
+{
+ return (__sec_reduce_add (a1[0:NUMBER] * a2[0:NUMBER]) +
+ __sec_reduce_mul (a1[0:NUMBER] + a2[0:NUMBER]));
+}
+
+int func3 (int *a1, int *a2)
+{
+ return (int) sqrt ((double)(__sec_reduce_add (a1[0:NUMBER] * a2[0:NUMBER]) +
+ a2[0] + a2[1] + a2[3]));
+}
+
+int func4 (int *a1, int *a2)
+{
+ return a1[NUMBER-1] * (__sec_reduce_add (a1[0:NUMBER] * a2[0:NUMBER]) + a2[0] + a2[1] + a2[3])/a1[NUMBER-2];
+}
+int main(void)
+{
+ int array[NUMBER], array2[NUMBER];
+ int return_value = 0;
+ int ii = 0;
+ int argc = 1;
+ __asm volatile ("" : "+r" (argc));
+ for (ii = 0; ii < NUMBER; ii++)
+ {
+ array[ii] = argc; /* This should calculate to 1. */
+ array2[ii] = argc * argc + argc; /* This should calculate to 2. */
+ }
+
+ return_value = func1 (array, array2);
+#if HAVE_IO
+ printf("Return_value = %d\n", return_value);
+#endif
+ if (return_value != (2+2+2+2+2))
+ return 1;
+
+ return_value = func2 (array2, array);
+#if HAVE_IO
+ printf("Return_value = %d\n", return_value);
+#endif
+ if (return_value != (3*3*3*3*3) + (2+2+2+2+2))
+ return 2;
+
+ return_value = func3 (array, array2);
+#if HAVE_IO
+ printf("Return_value = %d\n", return_value);
+#endif
+ if (return_value != 4)
+ return 3;
+
+ return_value = func4 (array, array2);
+#if HAVE_IO
+ printf("Return_value = %d\n", return_value);
+#endif
+ if (return_value != 16)
+ return 4;
+
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.dg/optimize-bswapdi-1.c b/gcc/testsuite/gcc.dg/optimize-bswapdi-1.c
index 0b5fe29687a..251dbc2da95 100644
--- a/gcc/testsuite/gcc.dg/optimize-bswapdi-1.c
+++ b/gcc/testsuite/gcc.dg/optimize-bswapdi-1.c
@@ -2,6 +2,7 @@
/* { dg-require-effective-target bswap64 } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-tree-bswap" } */
+/* { dg-additional-options "-mzarch" { target s390*-*-* } } */
#include <stdint.h>
#define __const_swab64(x) ((uint64_t)( \
diff --git a/gcc/testsuite/gcc.dg/optimize-bswapdi-2.c b/gcc/testsuite/gcc.dg/optimize-bswapdi-2.c
index 7ac0323825a..2c8108707dc 100644
--- a/gcc/testsuite/gcc.dg/optimize-bswapdi-2.c
+++ b/gcc/testsuite/gcc.dg/optimize-bswapdi-2.c
@@ -2,6 +2,7 @@
/* { dg-require-effective-target bswap64 } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-tree-bswap" } */
+/* { dg-additional-options "-mzarch" { target s390*-*-* } } */
#include <stdint.h>
diff --git a/gcc/testsuite/gcc.dg/optimize-bswapdi-3.c b/gcc/testsuite/gcc.dg/optimize-bswapdi-3.c
index 3c66505a64f..273b4bc622c 100644
--- a/gcc/testsuite/gcc.dg/optimize-bswapdi-3.c
+++ b/gcc/testsuite/gcc.dg/optimize-bswapdi-3.c
@@ -2,6 +2,7 @@
/* { dg-require-effective-target bswap64 } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-tree-bswap" } */
+/* { dg-additional-options "-mzarch" { target s390*-*-* } } */
#include <stdint.h>
diff --git a/gcc/testsuite/gcc.dg/optimize-bswapsi-1.c b/gcc/testsuite/gcc.dg/optimize-bswapsi-1.c
index fb1d884c0fb..77916a7a955 100644
--- a/gcc/testsuite/gcc.dg/optimize-bswapsi-1.c
+++ b/gcc/testsuite/gcc.dg/optimize-bswapsi-1.c
@@ -2,7 +2,7 @@
/* { dg-require-effective-target bswap32 } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-tree-bswap" } */
-/* { dg-additional-options "-march=z900" { target s390-*-* } } */
+/* { dg-additional-options "-march=z900" { target s390*-*-* } } */
#include <stdint.h>
diff --git a/gcc/testsuite/gcc.dg/optimize-bswapsi-2.c b/gcc/testsuite/gcc.dg/optimize-bswapsi-2.c
index dfa37634226..a1558af2cc7 100644
--- a/gcc/testsuite/gcc.dg/optimize-bswapsi-2.c
+++ b/gcc/testsuite/gcc.dg/optimize-bswapsi-2.c
@@ -2,7 +2,7 @@
/* { dg-require-effective-target bswap32 } */
/* { dg-require-effective-target stdint_types } */
/* { dg-options "-O2 -fdump-tree-bswap" } */
-/* { dg-additional-options "-march=z900" { target s390-*-* } } */
+/* { dg-additional-options "-march=z900" { target s390*-*-* } } */
#include <stdint.h>
diff --git a/gcc/testsuite/gcc.dg/pr68162-1.c b/gcc/testsuite/gcc.dg/pr68162-1.c
new file mode 100644
index 00000000000..a2c495365fe
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr68162-1.c
@@ -0,0 +1,6 @@
+/* Test handling of pointers to arrays of const elements involving a
+ typedef. PR c/68162. */
+
+typedef const double cd;
+void f (const double (*)[]);
+void g (void) { f ((cd (*)[]) 0); }
diff --git a/gcc/testsuite/gcc.dg/pr68474.c b/gcc/testsuite/gcc.dg/pr68474.c
new file mode 100644
index 00000000000..8ad7def4b74
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr68474.c
@@ -0,0 +1,7 @@
+/* { dg-options "-O -funsafe-math-optimizations" } */
+
+long double
+foo (long double d1, long double d2)
+{
+ return d1 || __builtin_significandl (d2);
+}
diff --git a/gcc/testsuite/gcc.dg/pr68513.c b/gcc/testsuite/gcc.dg/pr68513.c
new file mode 100644
index 00000000000..86f878d5d73
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr68513.c
@@ -0,0 +1,125 @@
+/* PR c/68513 */
+/* { dg-do compile } */
+/* { dg-options "-funsafe-math-optimizations -fno-math-errno -O -Wno-div-by-zero" } */
+
+int i;
+unsigned u;
+volatile int *e;
+
+#define E (i ? *e : 0)
+
+/* Can't trigger some of them because operand_equal_p will return false
+ for side-effects. */
+
+/* (x & ~m) | (y & m) -> ((x ^ y) & m) ^ x */
+int
+fn1 (void)
+{
+ int r = 0;
+ r += (short) (E & ~u | i & u);
+ r += -(short) (E & ~u | i & u);
+ r += (short) -(E & ~u | i & u);
+ return r;
+}
+
+/* sqrt(x) < y is x >= 0 && x != +Inf, when y is large. */
+double
+fn2 (void)
+{
+ double r;
+ r = __builtin_sqrt (E) < __builtin_inf ();
+ return r;
+}
+
+/* sqrt(x) < c is the same as x >= 0 && x < c*c. */
+double
+fn3 (void)
+{
+ double r;
+ r = __builtin_sqrt (E) < 1.3;
+ return r;
+}
+
+/* copysign(x,y)*copysign(x,y) -> x*x. */
+double
+fn4 (double y, double x)
+{
+ return __builtin_copysign (E, y) * __builtin_copysign (E, y);
+}
+
+/* x <= +Inf is the same as x == x, i.e. !isnan(x). */
+int
+fn5 (void)
+{
+ return E <= __builtin_inf ();
+}
+
+/* Fold (A & ~B) - (A & B) into (A ^ B) - B. */
+int
+fn6 (void)
+{
+ return (i & ~E) - (i & E);
+}
+
+/* Fold (A & B) - (A & ~B) into B - (A ^ B). */
+int
+fn7 (void)
+{
+ return (i & E) - (i & ~E);
+}
+
+/* x + (x & 1) -> (x + 1) & ~1 */
+int
+fn8 (void)
+{
+ return E + (E & 1);
+}
+
+/* Simplify comparison of something with itself. */
+int
+fn9 (void)
+{
+ return E <= E | E >= E;
+}
+
+/* Fold (A & ~B) - (A & B) into (A ^ B) - B. */
+int
+fn10 (void)
+{
+ return (i & ~E) - (i & E);
+}
+
+/* abs(x)*abs(x) -> x*x. Should be valid for all types. */
+int
+fn11 (void)
+{
+ return __builtin_abs (E) * __builtin_abs (E);
+}
+
+/* (x | CST1) & CST2 -> (x & CST2) | (CST1 & CST2) */
+int
+fn12 (void)
+{
+ return (E | 11) & 12;
+}
+
+/* fold_range_test */
+int
+fn13 (const char *s)
+{
+ return s[E] != '\0' && s[E] != '/';
+}
+
+/* fold_comparison */
+int
+fn14 (void)
+{
+ return (!!i ? : (u *= E / 0)) >= (u = E);
+}
+
+/* fold_mult_zconjz */
+_Complex int
+fn15 (_Complex volatile int *z)
+{
+ return *z * ~*z;
+}
diff --git a/gcc/testsuite/gcc.dg/pr68533.c b/gcc/testsuite/gcc.dg/pr68533.c
new file mode 100644
index 00000000000..e1a1f31f65a
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr68533.c
@@ -0,0 +1,68 @@
+/* PR c/68533 */
+/* { dg-do compile } */
+/* { dg-options "" } */
+
+struct T { int t; };
+
+void
+f1 (
+ struct S * /* { dg-warning "declared inside parameter list will not be visible outside of this definition or declaration" } */
+ x,
+ struct T *
+ y
+ )
+{
+ y->t = 4;
+}
+
+void
+f2 (
+ struct {int s;} * /* { dg-warning "anonymous struct declared inside parameter list will not be visible outside of this definition or declaration" } */
+ x,
+ struct T *
+ y
+ )
+{
+ y->t = 5;
+}
+
+void
+f3 (
+ const void
+ ) /* { dg-error "'void' as only parameter may not be qualified" } */
+{
+}
+
+void
+f4 (
+ void, /* { dg-error "'void' must be the only parameter" } */
+ ...
+ )
+{
+}
+
+void
+f5 (
+ int
+ x; /* { dg-error "parameter 'x' has just a forward declaration" } */
+ int y
+ )
+{
+}
+
+void
+f6 (
+ int
+ x,
+ void
+ ) /* { dg-error "'void' must be the only parameter" } */
+{
+}
+
+void
+f7 (
+ void, /* { dg-error "'void' must be the only parameter" } */
+ int y
+ )
+{
+}
diff --git a/gcc/testsuite/gcc.dg/pr68595.c b/gcc/testsuite/gcc.dg/pr68595.c
new file mode 100644
index 00000000000..179c6c352d3
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr68595.c
@@ -0,0 +1,13 @@
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+int a, b;
+char c;
+void fn1() {
+ b = 30;
+ for (; b <= 32; b++) {
+ c = -17;
+ for (; c <= 56; c++)
+ a -= 0 == (c || b);
+ }
+}
diff --git a/gcc/testsuite/gcc.dg/sso-9.c b/gcc/testsuite/gcc.dg/sso-9.c
new file mode 100644
index 00000000000..6e767462e4d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/sso-9.c
@@ -0,0 +1,27 @@
+/* Test support of scalar_storage_order attribute */
+
+/* { dg-do compile } */
+
+#include <stdarg.h>
+
+int x;
+
+#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
+struct __attribute__((scalar_storage_order("big-endian"))) Rec
+{
+ va_list v;
+};
+#else
+struct __attribute__((scalar_storage_order("little-endian"))) Rec
+{
+ va_list v;
+};
+#endif
+
+void foo (int i, ...)
+{
+ struct Rec a;
+ va_start (a.v, i);
+ a.v = a.v, x = va_arg (a.v, int); /* { dg-error "array type|reverse storage order" } */
+ va_end (a.v);
+}
diff --git a/gcc/testsuite/gcc.dg/torture/pr67916.c b/gcc/testsuite/gcc.dg/torture/pr67916.c
new file mode 100644
index 00000000000..88541f9acdd
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr67916.c
@@ -0,0 +1,46 @@
+/* PR tree-optimization/67916 */
+/* { dg-do run } */
+
+int a[6], b = 1, d, e;
+long long c;
+static int f = 1;
+
+void
+fn1 (int p1)
+{
+ b = (b >> 1) & (1 ^ a[(1 ^ p1) & 5]);
+}
+
+void
+fn2 ()
+{
+ b = (b >> 1) & (1 ^ a[(b ^ 1) & 1]);
+ fn1 (c >> 1 & 5);
+ fn1 (c >> 2 & 5);
+ fn1 (c >> 4 & 5);
+ fn1 (c >> 8 & 5);
+}
+
+int
+main ()
+{
+ int i, j;
+ for (; d;)
+ {
+ for (; e;)
+ fn2 ();
+ f = 0;
+ }
+ for (i = 0; i < 8; i++)
+ {
+ if (f)
+ i = 9;
+ for (j = 0; j < 7; j++)
+ fn2 ();
+ }
+
+ if (b != 0)
+ __builtin_abort ();
+
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.dg/torture/pr68379.c b/gcc/testsuite/gcc.dg/torture/pr68379.c
new file mode 100644
index 00000000000..6a3be7b5f5f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr68379.c
@@ -0,0 +1,12 @@
+/* { dg-do compile } */
+
+int a, b[3], c[3][5];
+
+void
+fn1 ()
+{
+ int e;
+ for (a = 2; a >= 0; a--)
+ for (e = 0; e < 4; e++)
+ c[a][e] = b[a];
+}
diff --git a/gcc/testsuite/gcc.dg/torture/pr68570.c b/gcc/testsuite/gcc.dg/torture/pr68570.c
new file mode 100644
index 00000000000..a8f2843ccb3
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr68570.c
@@ -0,0 +1,35 @@
+/* PR middle-end/68570 */
+/* { dg-do compile } */
+
+int a, d, e, f, h, i, k;
+
+void
+fn1 ()
+{
+ char m;
+ for (;;)
+ {
+ for (;;)
+ {
+ e = f = 1;
+ if (i)
+ d = h = 0;
+ else
+ a = 0;
+ break;
+ }
+ k = 0;
+ if (f)
+ a = 3;
+ if (d)
+ f = 0;
+ if (a > (i < 1))
+ {
+ if (e)
+ break;
+ }
+ else
+ i = m;
+ k = i ? a : i;
+ }
+}
diff --git a/gcc/testsuite/gcc.dg/torture/pr68625.c b/gcc/testsuite/gcc.dg/torture/pr68625.c
new file mode 100644
index 00000000000..47f837a2418
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/torture/pr68625.c
@@ -0,0 +1,51 @@
+/* { dg-do compile } */
+/* { dg-additional-options "-w" } */
+
+int **dp;
+int sg;
+
+void
+z9(void)
+{
+ int pz, oi, vz, yp, zi, hd, pw, gr, w9 = 0, j0 = -1, rb = &w9;
+ int *lr;
+ while (w9 < 1) {
+ lr++;
+ *lr = 1;
+ if (*lr < 1)
+ for (;;)
+ if (pz && *lr) {
+ee:
+ **dp = 0;
+ }
+ pz = zi = vz;
+ if (j0 ^ (vz > 0))
+ continue;
+ **dp = 1;
+ while (**dp)
+ if (++oi) {
+ int mq = dp;
+ j0 = 1;
+ while (pw < 1) {
+ if (++rb && mq)
+ xq:
+ hd = sg;
+ ++pw;
+ }
+ sg = 0;
+ while (!sg) {
+ goto ee;
+ while (++yp && gr++) {
+ int i9, xa;
+ while (++i9 && ++xa)
+ fb:
+ ;
+ }
+ }
+ }
+ }
+ ++vz;
+ if (zi > hd)
+ goto xq;
+ goto fb;
+}
diff --git a/gcc/testsuite/gcc.dg/torture/vshuf-4.inc b/gcc/testsuite/gcc.dg/torture/vshuf-4.inc
index d0cb7387ca3..d041b33871b 100644
--- a/gcc/testsuite/gcc.dg/torture/vshuf-4.inc
+++ b/gcc/testsuite/gcc.dg/torture/vshuf-4.inc
@@ -24,7 +24,8 @@ T (20, 0, 4, 1, 5) \
T (21, 2, 6, 3, 7) \
T (22, 1, 2, 3, 0) \
T (23, 2, 1, 0, 3) \
-T (24, 2, 5, 6, 3)
+T (24, 2, 5, 6, 3) \
+T (25, 0, 1, 4, 5)
#define EXPTESTS \
T (116, 1, 2, 4, 3) \
T (117, 7, 3, 3, 0) \
diff --git a/gcc/testsuite/gcc.dg/torture/vshuf-8.inc b/gcc/testsuite/gcc.dg/torture/vshuf-8.inc
index a39d71da6c8..d7a76108d8a 100644
--- a/gcc/testsuite/gcc.dg/torture/vshuf-8.inc
+++ b/gcc/testsuite/gcc.dg/torture/vshuf-8.inc
@@ -23,7 +23,9 @@ T (19, 7, 6, 5, 4, 3, 2, 1, 0) \
T (20, 0, 8, 1, 9, 2, 10, 3, 11) \
T (21, 4, 12, 5, 13, 6, 14, 7, 15) \
T (22, 1, 2, 3, 4, 5, 6, 7, 0) \
-T (23, 6, 5, 4, 3, 2, 1, 0, 7)
+T (23, 6, 5, 4, 3, 2, 1, 0, 7) \
+T (24, 0, 1, 2, 3, 8, 9, 10, 11) \
+T (25, 0, 1, 2, 3, 12, 13, 14, 15)
#define EXPTESTS \
T (116, 9, 3, 9, 4, 7, 0, 0, 6) \
T (117, 4, 14, 12, 8, 9, 6, 0, 10) \
diff --git a/gcc/testsuite/gcc.dg/pr46032.c b/gcc/testsuite/gcc.dg/vect/pr46032.c
index b91190e871f..8aa725a4245 100644
--- a/gcc/testsuite/gcc.dg/pr46032.c
+++ b/gcc/testsuite/gcc.dg/vect/pr46032.c
@@ -1,4 +1,6 @@
/* { dg-do compile } */
+/* { dg-require-effective-target fopenmp } */
+/* { dg-require-effective-target vect_int } */
/* { dg-options "-O2 -fopenmp -ftree-vectorize -std=c99 -fipa-pta -fdump-tree-vect-all" } */
extern void abort (void);
diff --git a/gcc/testsuite/gcc.dg/vect/pr68577.c b/gcc/testsuite/gcc.dg/vect/pr68577.c
new file mode 100644
index 00000000000..999c1c8502e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/vect/pr68577.c
@@ -0,0 +1,25 @@
+/* { dg-do compile } */
+
+int a, b;
+
+void
+__sched_cpucount (void)
+{
+ while (b)
+ {
+ long l = b++;
+ a += __builtin_popcountl(l);
+ }
+}
+
+void
+slp_test (int *x, long *y)
+{
+ for (int i = 0; i < 512; i += 4)
+ {
+ x[i] = __builtin_popcountl(y[i]);
+ x[i + 1] = __builtin_popcountl(y[i + 1]);
+ x[i + 2] = __builtin_popcountl(y[i + 2]);
+ x[i + 3] = __builtin_popcountl(y[i + 3]);
+ }
+}
diff --git a/gcc/testsuite/gcc.dg/vect/slp-42.c b/gcc/testsuite/gcc.dg/vect/slp-42.c
new file mode 100644
index 00000000000..ea5fe167cdb
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/vect/slp-42.c
@@ -0,0 +1,19 @@
+/* { dg-do compile } */
+/* { dg-require-effective-target vect_int } */
+
+int p[4096], q[4096];
+
+void foo (int n)
+{
+ int i;
+ for (i = 0; i < n; ++i)
+ {
+ p[i*4+0] = q[i*8+0] + q[i*8+4];
+ p[i*4+1] = q[i*8+1] + q[i*8+5];
+ p[i*4+2] = q[i*8+2] + q[i*8+6];
+ p[i*4+3] = q[i*8+3] + q[i*8+7];
+ }
+}
+
+/* { dg-final { scan-tree-dump "vectorizing stmts using SLP" "vect" } } */
+/* { dg-final { scan-tree-dump "vectorized 1 loops" "vect" } } */
diff --git a/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c b/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c
index 138cb3f6454..0132aaf4bc6 100644
--- a/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c
+++ b/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7-big-array.c
@@ -26,7 +26,7 @@ main1 ()
s *ptr = arr;
s check_res[N];
s res[N];
- unsigned char u, t, s, x, y, z, w;
+ unsigned char u, t, s, x, z, w;
for (i = 0; i < N; i++)
{
diff --git a/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7.c b/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7.c
index 716d7a59541..6eb04d88a51 100644
--- a/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7.c
+++ b/gcc/testsuite/gcc.dg/vect/vect-strided-a-u8-i8-gap7.c
@@ -25,7 +25,7 @@ main1 ()
s arr[N];
s *ptr = arr;
s res[N];
- unsigned char u, t, s, x, y, z, w;
+ unsigned char u, t, s, x, z, w;
for (i = 0; i < N; i++)
{
diff --git a/gcc/testsuite/gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c b/gcc/testsuite/gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c
index d16059fbc0a..ac93099372e 100644
--- a/gcc/testsuite/gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c
+++ b/gcc/testsuite/gcc.dg/vect/vect-strided-u8-i8-gap7-big-array.c
@@ -26,7 +26,7 @@ main1 (s *arr)
int i;
s *ptr = arr;
s res[N];
- unsigned char u, t, s, x, y, z, w;
+ unsigned char u, t, s, x, z, w;
for (i = 0; i < N; i++)
{
@@ -65,7 +65,7 @@ int main (void)
{
int i;
s arr[N];
- unsigned char u, t, s, x, y, z, w;
+ unsigned char u, t, s, x, z, w;
check_vect ();
diff --git a/gcc/testsuite/gcc.target/arm/attr-unaligned-load-ice.c b/gcc/testsuite/gcc.target/arm/attr-unaligned-load-ice.c
new file mode 100644
index 00000000000..e1ed1c148e0
--- /dev/null
+++ b/gcc/testsuite/gcc.target/arm/attr-unaligned-load-ice.c
@@ -0,0 +1,19 @@
+/* PR target/68617
+ Verify that unaligned_access is correctly with attribute target. */
+/* { dg-do compile } */
+/* { dg-skip-if "avoid conflicting multilib options" { *-*-* } { "-march=*" } { "-march=armv6" } } */
+/* { dg-options "-Os -mfloat-abi=softfp -mtp=soft" } */
+/* { dg-add-options arm_arch_v6 } */
+
+long __attribute__((target("thumb")))
+foo (char *s, long size, int unsigned_p)
+{
+ long x;
+ unsigned char *p = (unsigned char *) s;
+ switch (size)
+ {
+ case 4:
+ x = ((long) p[3] << 24) | ((long) p[2] << 16) | (p[1] << 8) | p[0];
+ return x;
+ }
+}
diff --git a/gcc/testsuite/gcc.target/arm/ftest-armv6-thumb.c b/gcc/testsuite/gcc.target/arm/ftest-armv6-thumb.c
index 0f42a0ca8dc..90ef9d2823a 100644
--- a/gcc/testsuite/gcc.target/arm/ftest-armv6-thumb.c
+++ b/gcc/testsuite/gcc.target/arm/ftest-armv6-thumb.c
@@ -13,7 +13,4 @@
#define NEED_ARM_ARCH_ISA_THUMB
#define VALUE_ARM_ARCH_ISA_THUMB 1
-#define NEED_ARM_FEATURE_UNALIGNED
-#define VALUE_ARM_FEATURE_UNALIGNED 1
-
#include "ftest-support.h"
diff --git a/gcc/testsuite/gcc.target/arm/ftest-armv6k-thumb.c b/gcc/testsuite/gcc.target/arm/ftest-armv6k-thumb.c
index 8e4a1880428..c2fc270d33d 100644
--- a/gcc/testsuite/gcc.target/arm/ftest-armv6k-thumb.c
+++ b/gcc/testsuite/gcc.target/arm/ftest-armv6k-thumb.c
@@ -13,7 +13,4 @@
#define NEED_ARM_ARCH_ISA_THUMB
#define VALUE_ARM_ARCH_ISA_THUMB 1
-#define NEED_ARM_FEATURE_UNALIGNED
-#define VALUE_ARM_FEATURE_UNALIGNED 1
-
#include "ftest-support.h"
diff --git a/gcc/testsuite/gcc.target/arm/ftest-armv6z-thumb.c b/gcc/testsuite/gcc.target/arm/ftest-armv6z-thumb.c
index 9761f0a96f6..e4b94efc075 100644
--- a/gcc/testsuite/gcc.target/arm/ftest-armv6z-thumb.c
+++ b/gcc/testsuite/gcc.target/arm/ftest-armv6z-thumb.c
@@ -13,7 +13,4 @@
#define NEED_ARM_ARCH_ISA_THUMB
#define VALUE_ARM_ARCH_ISA_THUMB 1
-#define NEED_ARM_FEATURE_UNALIGNED
-#define VALUE_ARM_FEATURE_UNALIGNED 1
-
#include "ftest-support.h"
diff --git a/gcc/testsuite/gcc.target/i386/avx512vl-vextractf32x4-1.c b/gcc/testsuite/gcc.target/i386/avx512vl-vextractf32x4-1.c
index c01835ce097..26313f44062 100644
--- a/gcc/testsuite/gcc.target/i386/avx512vl-vextractf32x4-1.c
+++ b/gcc/testsuite/gcc.target/i386/avx512vl-vextractf32x4-1.c
@@ -1,6 +1,6 @@
/* { dg-do compile } */
/* { dg-options "-mavx512vl -O2" } */
-/* { dg-final { scan-assembler-times "vextractf32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+(?:\n|\[ \\t\]+#)" 1 } } */
+/* { dg-final { scan-assembler-times "vextractf(?:128|32x4)\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+(?:\n|\[ \\t\]+#)" 1 } } */
/* { dg-final { scan-assembler-times "vextractf32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+\{%k\[1-7\]\}\{z\}(?:\n|\[ \\t\]+#)" 1 } } */
/* { dg-final { scan-assembler-times "vextractf32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+\{%k\[1-7\]\}(?:\n|\[ \\t\]+#)" 1 } } */
diff --git a/gcc/testsuite/gcc.target/i386/avx512vl-vextracti32x4-1.c b/gcc/testsuite/gcc.target/i386/avx512vl-vextracti32x4-1.c
index 7ee87dd82ec..0826a0b8e04 100644
--- a/gcc/testsuite/gcc.target/i386/avx512vl-vextracti32x4-1.c
+++ b/gcc/testsuite/gcc.target/i386/avx512vl-vextracti32x4-1.c
@@ -1,6 +1,6 @@
/* { dg-do compile } */
/* { dg-options "-mavx512vl -O2" } */
-/* { dg-final { scan-assembler-times "vextracti32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+(?:\n|\[ \\t\]+#)" 1 } } */
+/* { dg-final { scan-assembler-times "vextracti\(?:128|32x4\)\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+(?:\n|\[ \\t\]+#)" 1 } } */
/* { dg-final { scan-assembler-times "vextracti32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+\{%k\[1-7\]\}(?:\n|\[ \\t\]+#)" 1 } } */
/* { dg-final { scan-assembler-times "vextracti32x4\[ \\t\]+\[^\{\n\]*%xmm\[0-9\]+\{%k\[1-7\]\}\{z\}(?:\n|\[ \\t\]+#)" 1 } } */
diff --git a/gcc/testsuite/gcc.target/i386/pr68432-1.c b/gcc/testsuite/gcc.target/i386/pr68432-1.c
new file mode 100644
index 00000000000..8493652369e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68432-1.c
@@ -0,0 +1,17 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fno-math-errno -fno-trapping-math -msse2 -mfpmath=sse" } */
+
+float
+f1 (float f)
+{
+ return __builtin_rintf (f);
+}
+
+double
+f2 (double f)
+{
+ return __builtin_rint (f);
+}
+
+/* { dg-final { scan-assembler-times "\tucomiss\t" 1 } } */
+/* { dg-final { scan-assembler-times "\tucomisd\t" 1 } } */
diff --git a/gcc/testsuite/gcc.target/i386/pr68432-2.c b/gcc/testsuite/gcc.target/i386/pr68432-2.c
new file mode 100644
index 00000000000..8a0c2955895
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68432-2.c
@@ -0,0 +1,17 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fno-math-errno -fno-trapping-math -msse2 -mfpmath=sse" } */
+
+float
+f1 (float f)
+{
+ return __builtin_rintf (f);
+}
+
+double
+f2 (double f)
+{
+ return __builtin_rint (f);
+}
+
+/* { dg-final { scan-assembler-not "\tucomiss\t" } } */
+/* { dg-final { scan-assembler-not "\tucomisd\t" } } */
diff --git a/gcc/testsuite/gcc.target/i386/pr68432-3.c b/gcc/testsuite/gcc.target/i386/pr68432-3.c
new file mode 100644
index 00000000000..5f22972338e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68432-3.c
@@ -0,0 +1,17 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fno-math-errno -fno-trapping-math -msse2 -mfpmath=sse" } */
+
+float __attribute__ ((cold))
+f1 (float f)
+{
+ return __builtin_rintf (f);
+}
+
+double __attribute__ ((cold))
+f2 (double f)
+{
+ return __builtin_rint (f);
+}
+
+/* { dg-final { scan-assembler-not "\tucomiss\t" } } */
+/* { dg-final { scan-assembler-not "\tucomisd\t" } } */
diff --git a/gcc/testsuite/gcc.target/i386/pr68647.c b/gcc/testsuite/gcc.target/i386/pr68647.c
new file mode 100644
index 00000000000..70549318e87
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/pr68647.c
@@ -0,0 +1,18 @@
+/* PR target/68647 */
+/* { dg-do compile } */
+/* { dg-options "-O2 -mpopcnt" } */
+
+int
+f1 (unsigned long long a)
+{
+ return __builtin_popcountll (a);
+}
+
+int
+f2 (unsigned long long a)
+{
+ return __builtin_parityll (a);
+}
+
+/* { dg-final { scan-assembler-not "__popcountdi2" } } */
+/* { dg-final { scan-assembler-not "__paritydi2" } } */
diff --git a/gcc/testsuite/gcc.target/i386/vect-pr67800.c b/gcc/testsuite/gcc.target/i386/vect-pr67800.c
new file mode 100644
index 00000000000..324510858ff
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/vect-pr67800.c
@@ -0,0 +1,42 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -ftree-vectorize -fdump-tree-vect-details" } */
+/* { dg-additional-options "-msse4.2" } */
+
+#define ubyte unsigned char
+#define byte char
+
+#define SCALE 8
+
+#define R2Y (76)
+#define G2Y (150)
+#define B2Y (30)
+#define R2I (127)
+#define G2I (-59)
+#define B2I (-68)
+#define R2Q (51)
+#define G2Q (-127)
+#define B2Q (76)
+
+void
+convert(ubyte *in, ubyte *out, unsigned n)
+{
+ ubyte r, g, b;
+ ubyte y = 0;
+ byte i, q;
+
+ while (--n) {
+ r = *in++;
+ g = *in++;
+ b = *in++;
+
+ y = (ubyte)(((R2Y * r) + (G2Y * g) + (B2Y * b) + (1 << (SCALE - 1))) >> SCALE);
+ i = (byte)(((R2I * r) + (G2I * g) + (B2I * b) + (1 << (SCALE - 1))) >> SCALE);
+ q = (byte)(((R2Q * r) + (G2Q * g) + (B2Q * b) + (1 << (SCALE - 1))) >> SCALE);
+
+ *out++ = y;
+ *out++ = i;
+ *out++ = q;
+ }
+}
+
+/* { dg-final { scan-tree-dump "vectorized 1 loops" "vect" } } */
diff --git a/gcc/testsuite/gcc.target/nvptx/decl.c b/gcc/testsuite/gcc.target/nvptx/decl.c
new file mode 100644
index 00000000000..094cdb03fe0
--- /dev/null
+++ b/gcc/testsuite/gcc.target/nvptx/decl.c
@@ -0,0 +1,19 @@
+
+static const int __attribute__ ((used)) cst_local = 4;
+static int __attribute__ ((used)) glob_local = 5;
+const int __attribute__ ((used)) cst_export = 4;
+int __attribute__ ((used)) glob_export = 5;
+extern const int cst_import;
+extern int glob_import;
+
+int Foo ()
+{
+ return cst_import + glob_import;
+}
+
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.visible .global \[^,\r\n\]*glob_export" } } */
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.visible .const \[^,\r\n\]*cst_export" } } */
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.global \[^,\r\n\]*glob_local" } } */
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.const \[^,\r\n\]*cst_local" } } */
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.extern .global \[^,\r\n\]*glob_import" } } */
+/* { dg-final { scan-assembler "\[\r\n\]\[\t \]*.extern .const \[^,\r\n\]*cst_import" } } */
diff --git a/gcc/testsuite/gcc.target/nvptx/uninit-decl.c b/gcc/testsuite/gcc.target/nvptx/uninit-decl.c
new file mode 100644
index 00000000000..65c44f5b0f7
--- /dev/null
+++ b/gcc/testsuite/gcc.target/nvptx/uninit-decl.c
@@ -0,0 +1,7 @@
+/* { dg-do compile } */
+
+int __attribute__ ((used)) common;
+static int __attribute__ ((used)) local;
+
+/* { dg-final { scan-assembler "\[\n\r\]\[\t \]*.weak .global\[^,\n\r\]*common" } } */
+/* { dg-final { scan-assembler "\[\n\r\]\[\t \]*.global\[^,\n\r\]*local" } } */
diff --git a/gcc/testsuite/gcc.target/powerpc/swaps-p8-22.c b/gcc/testsuite/gcc.target/powerpc/swaps-p8-22.c
new file mode 100644
index 00000000000..4be217b3dd1
--- /dev/null
+++ b/gcc/testsuite/gcc.target/powerpc/swaps-p8-22.c
@@ -0,0 +1,29 @@
+/* { dg-do compile { target { powerpc64le-*-* } } } */
+/* { dg-skip-if "do not override -mcpu" { powerpc*-*-* } { "-mcpu=*" } { "-mcpu=power8" } }
+/* { dg-options "-O2 -mcpu=power8 -maltivec -mcmodel=large" } */
+
+/* The expansion for vector character multiply introduces a vperm operation.
+ This tests that changing the vperm mask allows us to remove all swaps
+ from the generated code. It is a duplicate of swaps-p8-21.c, except
+ that it applies the large code model, which requires an extra indirection
+ in the load of the constant mask. */
+
+#include <altivec.h>
+
+void abort ();
+
+vector unsigned char r;
+vector unsigned char v =
+ { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 };
+vector unsigned char i =
+ { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16 };
+
+int main ()
+{
+ int j;
+ r = v * i;
+ return 0;
+}
+
+/* { dg-final { scan-assembler-times "vperm" 1 } } */
+/* { dg-final { scan-assembler-not "xxpermdi" } } */
diff --git a/gcc/testsuite/gcc.target/s390/bswap-1.c b/gcc/testsuite/gcc.target/s390/bswap-1.c
index e1f113a4ccf..edfcdf888c0 100644
--- a/gcc/testsuite/gcc.target/s390/bswap-1.c
+++ b/gcc/testsuite/gcc.target/s390/bswap-1.c
@@ -21,16 +21,32 @@ foo64b ()
}
/* { dg-final { scan-assembler-times "lrvg\t%r2,0\\(%r\[0-9\]*\\)" 1 { target lp64 } } } */
+void
+foo64c (uint64_t a)
+{
+ u64 = __builtin_bswap64 (a);
+}
+/* { dg-final { scan-assembler-times "strvg\t%r2,0\\(%r\[0-9\]*\\)" 1 { target lp64 } } } */
+
+
+
+uint32_t
+foo32a (uint32_t a)
+{
+ return __builtin_bswap32 (a);
+}
+/* { dg-final { scan-assembler-times "lrvr\t%r2,%r2" 1 } } */
+
uint32_t
-foo32 ()
+foo32b ()
{
return __builtin_bswap32 (u32);
}
/* { dg-final { scan-assembler-times "lrv\t%r2,0\\(%r\[0-9\]*\\)" 1 } } */
-uint16_t
-foo16 ()
+void
+foo32c (uint32_t a)
{
- return __builtin_bswap16 (u16);
+ u32 = __builtin_bswap32 (a);
}
-/* { dg-final { scan-assembler-times "lrvh\t%r2,0\\(%r\[0-9\]*\\)" 1 } } */
+/* { dg-final { scan-assembler-times "strv\t%r2,0\\(%r\[0-9\]*\\)" 1 } } */
diff --git a/gcc/testsuite/gcc.target/s390/bswaphi-1.c b/gcc/testsuite/gcc.target/s390/bswaphi-1.c
new file mode 100644
index 00000000000..f6be9b42d8c
--- /dev/null
+++ b/gcc/testsuite/gcc.target/s390/bswaphi-1.c
@@ -0,0 +1,27 @@
+/* { dg-do compile } */
+/* { dg-options "-O3 -march=z900 -mzarch" } */
+
+#include <stdint.h>
+
+uint16_t u16;
+
+uint16_t
+foo16a (uint16_t a)
+{
+ return __builtin_bswap16 (a);
+}
+/* { dg-final { scan-assembler-times "lrvr\t%r2,%r\[0-9\]*" 1 } } */
+
+uint16_t
+foo16b ()
+{
+ return __builtin_bswap16 (u16);
+}
+/* { dg-final { scan-assembler-times "lrvh\t%r2,0\\(%r\[0-9\]*\\)" 1 } } */
+
+void
+foo16c (uint16_t a)
+{
+ u16 = __builtin_bswap16 (a);
+}
+/* { dg-final { scan-assembler-times "strvh\t%r2,0\\(%r\[0-9\]*\\)" 1 } } */
diff --git a/gcc/testsuite/gcc.target/s390/vector/vec-vrepi-1.c b/gcc/testsuite/gcc.target/s390/vector/vec-vrepi-1.c
new file mode 100644
index 00000000000..27bf39e0963
--- /dev/null
+++ b/gcc/testsuite/gcc.target/s390/vector/vec-vrepi-1.c
@@ -0,0 +1,58 @@
+/* { dg-do run } */
+/* { dg-options "-O3 -mzarch -march=z13 --save-temps" } */
+/* { dg-require-effective-target vector } */
+
+typedef unsigned char uv16qi __attribute__((vector_size(16)));
+typedef unsigned short uv8hi __attribute__((vector_size(16)));
+typedef unsigned int uv4si __attribute__((vector_size(16)));
+typedef unsigned long long uv2di __attribute__((vector_size(16)));
+
+uv2di __attribute__((noinline))
+foo1 ()
+{
+ return (uv2di){ 0x7f0f, 0x7f0f };
+}
+/* { dg-final { scan-assembler-times "vrepig\t%v24,32527" 1 } } */
+
+uv4si __attribute__((noinline))
+foo2 ()
+{
+ return (uv4si){ 0x7f0f, 0x7f0f, 0x7f0f, 0x7f0f };
+}
+/* { dg-final { scan-assembler-times "vrepif\t%v24,32527" 1 } } */
+
+uv8hi __attribute__((noinline))
+foo3 ()
+{
+ return (uv8hi){ 0x7f0f, 0x7f0f, 0x7f0f, 0x7f0f,
+ 0x7f0f, 0x7f0f, 0x7f0f, 0x7f0f };
+}
+/* { dg-final { scan-assembler-times "vrepih\t%v24,32527" 1 } } */
+
+uv16qi __attribute__((noinline))
+foo4 ()
+{
+ return (uv16qi){ 0x77, 0x77, 0x77, 0x77,
+ 0x77, 0x77, 0x77, 0x77,
+ 0x77, 0x77, 0x77, 0x77,
+ 0x77, 0x77, 0x77, 0x77 };
+}
+/* { dg-final { scan-assembler-times "vrepib\t%v24,119" 1 } } */
+
+int
+main ()
+{
+ if (foo1()[1] != 0x7f0f)
+ __builtin_abort ();
+
+ if (foo2()[1] != 0x7f0f)
+ __builtin_abort ();
+
+ if (foo3()[1] != 0x7f0f)
+ __builtin_abort ();
+
+ if (foo4()[1] != 0x77)
+ __builtin_abort ();
+
+ return 0;
+}
diff --git a/gcc/testsuite/gcc.target/s390/zvector/vec-splat-1.c b/gcc/testsuite/gcc.target/s390/zvector/vec-splat-1.c
new file mode 100644
index 00000000000..bab2e2d4028
--- /dev/null
+++ b/gcc/testsuite/gcc.target/s390/zvector/vec-splat-1.c
@@ -0,0 +1,42 @@
+/* { dg-do compile } */
+/* { dg-options "-O3 -mzarch -march=z13 -mzvector" } */
+
+#include <vecintrin.h>
+
+vector signed char v16qi;
+vector short v8hi;
+vector int v4si;
+vector long long v2di;
+
+vector unsigned char uv16qi;
+vector unsigned short uv8hi;
+vector unsigned int uv4si;
+vector unsigned long long uv2di;
+
+int
+foo ()
+{
+ v16qi = vec_splats ((signed char)0x77);
+ uv16qi = vec_splats ((unsigned char)0x77);
+
+ v8hi = vec_splats ((short int)0x7f0f);
+ uv8hi = vec_splats ((unsigned short int)0x7f0f);
+
+ v4si = vec_splats ((int)0x7f0f);
+ uv4si = vec_splats ((unsigned int)0x7f0f);
+
+ v2di = vec_splats ((long long)0x7f0f);
+ uv2di = vec_splats ((unsigned long long)0x7f0f);
+}
+
+/* { dg-final { scan-assembler-times "vrepib\t%v.*,119" 1 } } */
+/* { dg-final { scan-assembler-times "vrepib\t%v.*,119" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepih\t%v.*,32527" 1 } } */
+/* { dg-final { scan-assembler-times "vrepih\t%v.*,32527" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepif\t%v.*,32527" 1 } } */
+/* { dg-final { scan-assembler-times "vrepif\t%v.*,32527" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepig\t%v.*,32527" 1 } } */
+/* { dg-final { scan-assembler-times "vrepig\t%v.*,32527" 1 } } */
diff --git a/gcc/testsuite/gcc.target/s390/zvector/vec-splat-2.c b/gcc/testsuite/gcc.target/s390/zvector/vec-splat-2.c
new file mode 100644
index 00000000000..7ad090b2d5e
--- /dev/null
+++ b/gcc/testsuite/gcc.target/s390/zvector/vec-splat-2.c
@@ -0,0 +1,42 @@
+/* { dg-do compile } */
+/* { dg-options "-O3 -mzarch -march=z13 -mzvector" } */
+
+#include <vecintrin.h>
+
+vector signed char v16qi;
+vector short v8hi;
+vector int v4si;
+vector long long v2di;
+
+vector unsigned char uv16qi;
+vector unsigned short uv8hi;
+vector unsigned int uv4si;
+vector unsigned long long uv2di;
+
+int
+foo ()
+{
+ v16qi = vec_splat_s8 (-112);
+ uv16qi = vec_splat_u8 (215);
+
+ v8hi = vec_splat_s16 (-32000);
+ uv8hi = vec_splat_u16 (64000);
+
+ v4si = vec_splat_s32 (-32000);
+ uv4si = vec_splat_u32 (64000);
+
+ v2di = vec_splat_s64 (-32000);
+ uv2di = vec_splat_u64 (64000);
+}
+
+/* { dg-final { scan-assembler-times "vrepib\t%v.*,-112" 1 } } */
+/* { dg-final { scan-assembler-times "vrepib\t%v.*,-41" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepih\t%v.*,-32000" 1 } } */
+/* { dg-final { scan-assembler-times "vrepih\t%v.*,-1536" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepif\t%v.*,-32000" 1 } } */
+/* { dg-final { scan-assembler-times "vrepif\t%v.*,-1536" 1 } } */
+
+/* { dg-final { scan-assembler-times "vrepig\t%v.*,-32000" 1 } } */
+/* { dg-final { scan-assembler-times "vrepig\t%v.*,-1536" 1 } } */
diff --git a/gcc/testsuite/gfortran.dg/coarray/event_1.f90 b/gcc/testsuite/gfortran.dg/coarray/event_1.f90
new file mode 100644
index 00000000000..b4385f340ed
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/coarray/event_1.f90
@@ -0,0 +1,51 @@
+! { dg-do run }
+!
+! Run-time test for EVENT_TYPE
+!
+use iso_fortran_env, only: event_type
+implicit none
+
+type(event_type), save :: var[*]
+integer :: count, stat
+
+count = -42
+call event_query (var, count)
+if (count /= 0) call abort()
+
+stat = 99
+event post (var, stat=stat)
+if (stat /= 0) call abort()
+call event_query(var, count, stat=stat)
+if (count /= 1 .or. stat /= 0) call abort()
+
+stat = 99
+event post (var[this_image()])
+call event_query(var, count)
+if (count /= 2) call abort()
+
+stat = 99
+event wait (var)
+call event_query(var, count)
+if (count /= 1) call abort()
+
+stat = 99
+event post (var)
+call event_query(var, count)
+if (count /= 2) call abort()
+
+stat = 99
+event post (var)
+call event_query(var, count)
+if (count /= 3) call abort()
+
+stat = 99
+event wait (var, until_count=2)
+call event_query(var, count)
+if (count /= 1) call abort()
+
+stat = 99
+event wait (var, stat=stat, until_count=1)
+if (stat /= 0) call abort()
+call event_query(event=var, stat=stat, count=count)
+if (count /= 0 .or. stat /= 0) call abort()
+end
diff --git a/gcc/testsuite/gfortran.dg/coarray/event_2.f90 b/gcc/testsuite/gfortran.dg/coarray/event_2.f90
new file mode 100644
index 00000000000..2d451a557a9
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/coarray/event_2.f90
@@ -0,0 +1,89 @@
+! { dg-do run }
+!
+! Run-time test for EVENT_TYPE
+!
+use iso_fortran_env, only: event_type
+implicit none
+
+type(event_type), save, allocatable :: var(:)[:]
+integer :: count, stat
+
+allocate(var(3)[*])
+
+count = -42
+call event_query (var(1), count)
+if (count /= 0) call abort()
+call event_query (var(1), count)
+if (count /= 0) call abort()
+call event_query (var(2), count)
+if (count /= 0) call abort()
+call event_query (var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event post (var(2), stat=stat)
+if (stat /= 0) call abort()
+call event_query (var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count, stat=stat)
+if (count /= 1 .or. stat /= 0) call abort()
+call event_query (var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event post (var(2)[this_image()])
+call event_query(var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count)
+if (count /= 2) call abort()
+call event_query(var(2), count)
+if (count /= 2) call abort()
+call event_query(var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event wait (var(2))
+call event_query(var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count)
+if (count /= 1) call abort()
+call event_query(var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event post (var(2))
+call event_query(var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count)
+if (count /= 2) call abort()
+call event_query(var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event post (var(2))
+call event_query(var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count)
+if (count /= 3) call abort()
+call event_query(var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event wait (var(2), until_count=2)
+call event_query(var(1), count)
+if (count /= 0) call abort()
+call event_query(var(2), count)
+if (count /= 1) call abort()
+call event_query(var(3), count)
+if (count /= 0) call abort()
+
+stat = 99
+event wait (var(2), stat=stat, until_count=1)
+if (stat /= 0) call abort()
+call event_query(event=var(1), stat=stat, count=count)
+if (count /= 0 .or. stat /= 0) call abort()
+call event_query(event=var(2), stat=stat, count=count)
+if (count /= 0 .or. stat /= 0) call abort()
+call event_query(event=var(3), stat=stat, count=count)
+if (count /= 0 .or. stat /= 0) call abort()
+end
diff --git a/gcc/testsuite/gfortran.dg/goacc/array-reduction.f90 b/gcc/testsuite/gfortran.dg/goacc/array-reduction.f90
new file mode 100644
index 00000000000..d71c400a5bf
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/goacc/array-reduction.f90
@@ -0,0 +1,74 @@
+program test
+ implicit none
+ integer a(10), i
+
+ a(:) = 0
+
+ ! Array reductions.
+
+ !$acc parallel reduction (+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end parallel
+
+ !$acc parallel
+ !$acc loop reduction (+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end parallel
+
+ !$acc kernels
+ !$acc loop reduction (+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end kernels
+
+ ! Subarray reductions.
+
+ !$acc parallel reduction (+:a(1:5)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end parallel
+
+ !$acc parallel
+ !$acc loop reduction (+:a(1:5)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end parallel
+
+ !$acc kernels
+ !$acc loop reduction (+:a(1:5)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a = a + 1
+ end do
+ !$acc end kernels
+
+ ! Reductions on array elements.
+
+ !$acc parallel reduction (+:a(1)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a(1) = a(1) + 1
+ end do
+ !$acc end parallel
+
+ !$acc parallel
+ !$acc loop reduction (+:a(1)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a(1) = a(1) + 1
+ end do
+ !$acc end parallel
+
+ !$acc kernels
+ !$acc loop reduction (+:a(1)) ! { dg-error "Array 'a' is not permitted in reduction" }
+ do i = 1, 10
+ a(1) = a(1) + 1
+ end do
+ !$acc end kernels
+
+ print *, a
+end program test
diff --git a/gcc/testsuite/gfortran.dg/goacc/assumed.f95 b/gcc/testsuite/gfortran.dg/goacc/assumed.f95
index 328724107eb..4efe5a2b06e 100644
--- a/gcc/testsuite/gfortran.dg/goacc/assumed.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/assumed.f95
@@ -45,3 +45,6 @@ contains
!$acc update self (a) ! { dg-error "Assumed rank" }
end subroutine assumed_rank
end module test
+
+! { dg-error "Array 'a' is not permitted in reduction" "" { target "*-*-*" } 18 }
+! { dg-error "Array 'a' is not permitted in reduction" "" { target "*-*-*" } 39 }
diff --git a/gcc/testsuite/gfortran.dg/goacc/coarray.f95 b/gcc/testsuite/gfortran.dg/goacc/coarray.f95
index 130ffc3ce9d..932e1f7fd0d 100644
--- a/gcc/testsuite/gfortran.dg/goacc/coarray.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/coarray.f95
@@ -1,7 +1,7 @@
! { dg-do compile }
! { dg-additional-options "-fcoarray=single" }
-
-! TODO: These cases must fail
+!
+! PR fortran/63861
module test
contains
@@ -9,7 +9,6 @@ contains
implicit none
integer :: i
integer, codimension[*] :: a
- ! { dg-excess-errors "sorry, unimplemented: directive not yet implemented" }
!$acc declare device_resident (a)
!$acc data copy (a)
!$acc end data
@@ -17,10 +16,9 @@ contains
!$acc end data
!$acc parallel private (a)
!$acc end parallel
- ! { dg-excess-errors "sorry, unimplemented: directive not yet implemented" }
!$acc host_data use_device (a)
!$acc end host_data
- !$acc parallel loop reduction(+:a)
+ !$acc parallel loop reduction(+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
do i = 1,5
enddo
!$acc end parallel loop
diff --git a/gcc/testsuite/gfortran.dg/goacc/coarray_2.f90 b/gcc/testsuite/gfortran.dg/goacc/coarray_2.f90
index f9cf9ac6ca0..05167a18af1 100644
--- a/gcc/testsuite/gfortran.dg/goacc/coarray_2.f90
+++ b/gcc/testsuite/gfortran.dg/goacc/coarray_2.f90
@@ -2,7 +2,6 @@
! { dg-additional-options "-fcoarray=lib" }
!
! PR fortran/63861
-! { dg-xfail-if "<http://gcc.gnu.org/PR63861>" { *-*-* } }
module test
contains
@@ -19,7 +18,7 @@ contains
!$acc end parallel
!$acc host_data use_device (a)
!$acc end host_data
- !$acc parallel loop reduction(+:a)
+ !$acc parallel loop reduction(+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
do i = 1,5
enddo
!$acc end parallel loop
@@ -71,7 +70,7 @@ contains
!$acc end parallel
!$acc host_data use_device (a)
!$acc end host_data
- !$acc parallel loop reduction(+:a)
+ !$acc parallel loop reduction(+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
do i = 1,5
enddo
!$acc end parallel loop
@@ -93,7 +92,7 @@ contains
!$acc end data
!$acc parallel private (a)
!$acc end parallel
- !$acc parallel loop reduction(+:a)
+ !$acc parallel loop reduction(+:a) ! { dg-error "Array 'a' is not permitted in reduction" }
do i = 1,5
enddo
!$acc end parallel loop
@@ -106,4 +105,3 @@ contains
!$acc update self (a)
end subroutine oacc4
end module test
-! { dg-excess-errors "sorry, unimplemented: directive not yet implemented" }
diff --git a/gcc/testsuite/gfortran.dg/goacc/gang-static.f95 b/gcc/testsuite/gfortran.dg/goacc/gang-static.f95
index 4e46cf3cb41..34810852d19 100644
--- a/gcc/testsuite/gfortran.dg/goacc/gang-static.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/gang-static.f95
@@ -47,6 +47,18 @@ program main
end do
!$acc end parallel loop
+ !$acc kernels loop gang (num:5, static:*)
+ do i = 1, n
+ a(i) = b(i) + 20
+ end do
+ !$acc end kernels loop
+
+ !$acc kernels loop gang (static:20, num:30)
+ do i = 1, n
+ a(i) = b(i) + 20
+ end do
+ !$acc end kernels loop
+
call test (a, b, 20, n)
end program main
@@ -66,3 +78,5 @@ end subroutine test
! { dg-final { scan-tree-dump-times "gang\\(static:2\\)" 1 "omplower" } }
! { dg-final { scan-tree-dump-times "gang\\(static:5\\)" 1 "omplower" } }
! { dg-final { scan-tree-dump-times "gang\\(static:20\\)" 1 "omplower" } }
+! { dg-final { scan-tree-dump-times "gang\\(num: 5 static:\\\*\\)" 1 "omplower" } }
+! { dg-final { scan-tree-dump-times "gang\\(num: 30 static:20\\)" 1 "omplower" } }
diff --git a/gcc/testsuite/gfortran.dg/goacc/host_data-tree.f95 b/gcc/testsuite/gfortran.dg/goacc/host_data-tree.f95
index e4c8205a591..7a5eea6d287 100644
--- a/gcc/testsuite/gfortran.dg/goacc/host_data-tree.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/host_data-tree.f95
@@ -8,5 +8,4 @@ program test
!$acc host_data use_device(i)
!$acc end host_data
end program test
-! { dg-prune-output "unimplemented" }
! { dg-final { scan-tree-dump-times "pragma acc host_data use_device\\(i\\)" 1 "original" } }
diff --git a/gcc/testsuite/gfortran.dg/goacc/loop-2.f95 b/gcc/testsuite/gfortran.dg/goacc/loop-2.f95
index b5e6368a493..0c902b22410 100644
--- a/gcc/testsuite/gfortran.dg/goacc/loop-2.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/loop-2.f95
@@ -187,10 +187,10 @@ program test
!$acc loop gang
DO i = 1,10
ENDDO
- !$acc loop gang(5) ! { dg-error "non-static" }
+ !$acc loop gang(5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
- !$acc loop gang(num:5) ! { dg-error "non-static" }
+ !$acc loop gang(num:5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
!$acc loop gang(static:5)
@@ -218,10 +218,10 @@ program test
!$acc loop worker
DO i = 1,10
ENDDO
- !$acc loop worker(5) ! { dg-error "non-static" }
+ !$acc loop worker(5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
- !$acc loop worker(num:5) ! { dg-error "non-static" }
+ !$acc loop worker(num:5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
!$acc loop worker
@@ -246,10 +246,10 @@ program test
!$acc loop vector
DO i = 1,10
ENDDO
- !$acc loop vector(5)
+ !$acc loop vector(5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
- !$acc loop vector(length:5)
+ !$acc loop vector(length:5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
!$acc loop vector
@@ -501,10 +501,10 @@ program test
!$acc parallel loop gang
DO i = 1,10
ENDDO
- !$acc parallel loop gang(5) ! { dg-error "non-static" }
+ !$acc parallel loop gang(5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
- !$acc parallel loop gang(num:5) ! { dg-error "non-static" }
+ !$acc parallel loop gang(num:5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
!$acc parallel loop gang(static:5)
@@ -526,10 +526,10 @@ program test
!$acc parallel loop worker
DO i = 1,10
ENDDO
- !$acc parallel loop worker(5) ! { dg-error "non-static" }
+ !$acc parallel loop worker(5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
- !$acc parallel loop worker(num:5) ! { dg-error "non-static" }
+ !$acc parallel loop worker(num:5) ! { dg-error "num arguments" }
DO i = 1,10
ENDDO
!$acc parallel loop worker
@@ -551,10 +551,10 @@ program test
!$acc parallel loop vector
DO i = 1,10
ENDDO
- !$acc parallel loop vector(5)
+ !$acc parallel loop vector(5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
- !$acc parallel loop vector(length:5)
+ !$acc parallel loop vector(length:5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
!$acc parallel loop vector
diff --git a/gcc/testsuite/gfortran.dg/goacc/loop-6.f95 b/gcc/testsuite/gfortran.dg/goacc/loop-6.f95
index e13abc764c8..e8444686cb0 100644
--- a/gcc/testsuite/gfortran.dg/goacc/loop-6.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/loop-6.f95
@@ -49,10 +49,10 @@ program test
!$acc loop vector
DO i = 1,10
ENDDO
- !$acc loop vector(5) ! { dg-error "argument not permitted" }
+ !$acc loop vector(5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
- !$acc loop vector(length:5) ! { dg-error "argument not permitted" }
+ !$acc loop vector(length:5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
!$acc loop vector
@@ -73,10 +73,10 @@ program test
!$acc parallel loop vector
DO i = 1,10
ENDDO
- !$acc parallel loop vector(5) ! { dg-error "argument not permitted" }
+ !$acc parallel loop vector(5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
- !$acc parallel loop vector(length:5) ! { dg-error "argument not permitted" }
+ !$acc parallel loop vector(length:5) ! { dg-error "length arguments" }
DO i = 1,10
ENDDO
end
diff --git a/gcc/testsuite/gfortran.dg/goacc/loop-7.f95 b/gcc/testsuite/gfortran.dg/goacc/loop-7.f95
new file mode 100644
index 00000000000..9ca8297d81a
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/goacc/loop-7.f95
@@ -0,0 +1,122 @@
+! { dg-do compile }
+! { dg-additional-options "-fmax-errors=100" }
+
+program test
+ implicit none
+ integer :: i, j, static, num, length
+
+ !$acc kernels
+ !$acc loop gang(static:static)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:*)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:1)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(,static:1) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:1,) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:*, num:5)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:1, 5)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(num:num, static:1)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(static:*, num:5, static:5) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(1, num:2, static:3) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(num:num static:1) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(num)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(num:num+1, static:1+num)
+ DO i = 1,10
+ ENDDO
+ !$acc loop gang(length:num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+
+ !$acc loop worker
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (5)
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num)
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (static:num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num:,) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num:num:num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num:num*num)
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (length:num*num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num:*) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop worker (num:5)
+ DO i = 1,10
+ ENDDO
+
+ !$acc loop vector
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (32)
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length)
+ DO i = 1,10
+ ENDDO
+ !$acc loop vrctor (static:num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:,) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:num:num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:static*num)
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:length)
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:32)
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (num:num*num) ! { dg-error "Unclassifiable OpenACC directive" }
+ DO i = 1,10
+ ENDDO
+ !$acc loop vector (length:*) ! { dg-error "Invalid character" }
+ DO i = 1,10
+ ENDDO
+
+
+ !$acc loop auto
+ DO i = 1,10
+ ENDDO
+ !$acc end kernels
+end
diff --git a/gcc/testsuite/gfortran.dg/goacc/reduction-2.f95 b/gcc/testsuite/gfortran.dg/goacc/reduction-2.f95
new file mode 100644
index 00000000000..929fb0e81e9
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/goacc/reduction-2.f95
@@ -0,0 +1,22 @@
+! { dg-do compile }
+! { dg-additional-options "-fdump-tree-gimple" }
+
+subroutine foo ()
+ implicit none
+ integer :: p,k
+ integer :: a
+ !$acc parallel loop reduction(+:a)
+ do p = 1,5
+ enddo
+ !$acc end parallel loop
+ !$acc kernels loop reduction(+:a)
+ do k = 2,6
+ enddo
+ !$acc end kernels loop
+end subroutine
+
+! { dg-final { scan-tree-dump-times "target oacc_parallel firstprivate.a." 1 "gimple" } }
+! { dg-final { scan-tree-dump-times "acc loop private.p. reduction..:a." 1 "gimple" } }
+! { dg-final { scan-tree-dump-times "target oacc_kernels map.force_tofrom:a .len: 4.." 1 "gimple" } }
+! { dg-final { scan-tree-dump-times "acc loop private.k. reduction..:a." 1 "gimple" } }
+
diff --git a/gcc/testsuite/gfortran.dg/goacc/reduction.f95 b/gcc/testsuite/gfortran.dg/goacc/reduction.f95
index 833230ade80..a13574b150c 100644
--- a/gcc/testsuite/gfortran.dg/goacc/reduction.f95
+++ b/gcc/testsuite/gfortran.dg/goacc/reduction.f95
@@ -136,3 +136,26 @@ common /blk/ i1
!$acc end parallel
end subroutine
+
+! { dg-error "Array 'ia2' is not permitted in reduction" "" { target "*-*-*" } 27 }
+! { dg-error "Array 'ra1' is not permitted in reduction" "" { target "*-*-*" } 29 }
+! { dg-error "Array 'ca1' is not permitted in reduction" "" { target "*-*-*" } 31 }
+! { dg-error "Array 'da1' is not permitted in reduction" "" { target "*-*-*" } 33 }
+! { dg-error "Array 'la1' is not permitted in reduction" "" { target "*-*-*" } 35 }
+! { dg-error "Array 'aa1' is not permitted in reduction" "" { target "*-*-*" } 65 }
+! { dg-error "Array 'ia1' is not permitted in reduction" "" { target "*-*-*" } 67 }
+! { dg-error "Array 'la1' is not permitted in reduction" "" { target "*-*-*" } 71 }
+! { dg-error "Array 'ta1' is not permitted in reduction" "" { target "*-*-*" } 77 }
+! { dg-error "Array 'ia2' is not permitted in reduction" "" { target "*-*-*" } 81 }
+! { dg-error "Array 'ra1' is not permitted in reduction" "" { target "*-*-*" } 85 }
+! { dg-error "Array 'da1' is not permitted in reduction" "" { target "*-*-*" } 89 }
+! { dg-error "Array 'ca1' is not permitted in reduction" "" { target "*-*-*" } 93 }
+! { dg-error "Array 'ta1' is not permitted in reduction" "" { target "*-*-*" } 99 }
+! { dg-error "Array 'ca1' is not permitted in reduction" "" { target "*-*-*" } 103 }
+! { dg-error "Array 'la1' is not permitted in reduction" "" { target "*-*-*" } 107 }
+! { dg-error "Array 'ta1' is not permitted in reduction" "" { target "*-*-*" } 113 }
+! { dg-error "Array 'ra1' is not permitted in reduction" "" { target "*-*-*" } 117 }
+! { dg-error "Array 'da1' is not permitted in reduction" "" { target "*-*-*" } 121 }
+! { dg-error "Array 'ca1' is not permitted in reduction" "" { target "*-*-*" } 125 }
+! { dg-error "Array 'la1' is not permitted in reduction" "" { target "*-*-*" } 129 }
+! { dg-error "Array 'ta1' is not permitted in reduction" "" { target "*-*-*" } 135 }
diff --git a/gcc/testsuite/gfortran.dg/graphite/id-26.f03 b/gcc/testsuite/gfortran.dg/graphite/id-26.f03
new file mode 100644
index 00000000000..c22cb169015
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/graphite/id-26.f03
@@ -0,0 +1,132 @@
+! { dg-options "-fcray-pointer -floop-nest-optimize" }
+
+ use iso_c_binding, only : c_ptr, c_ptrdiff_t, c_loc
+ interface
+ subroutine foo (x, y, z, w)
+ use iso_c_binding, only : c_ptr
+ real, pointer :: x(:), y(:), w(:)
+ type(c_ptr) :: z
+ end subroutine
+ subroutine bar (x, y, z, w)
+ use iso_c_binding, only : c_ptr
+ real, pointer :: x(:), y(:), w(:)
+ type(c_ptr) :: z
+ end subroutine
+ subroutine baz (x, c)
+ real, pointer :: x(:)
+ real, allocatable :: c(:)
+ end subroutine
+ end interface
+ type dt
+ real, allocatable :: a(:)
+ end type
+ type (dt) :: b(64)
+ real, target :: a(4096+63)
+ real, pointer :: p(:), q(:), r(:), s(:)
+ real, allocatable :: c(:)
+ integer(c_ptrdiff_t) :: o
+ integer :: i
+ o = 64 - mod (loc (a), 64)
+ if (o == 64) o = 0
+ o = o / sizeof(0.0)
+ p => a(o + 1:o + 1024)
+ q => a(o + 1025:o + 2048)
+ r => a(o + 2049:o + 3072)
+ s => a(o + 3073:o + 4096)
+ do i = 1, 1024
+ p(i) = i
+ q(i) = i
+ r(i) = i
+ s(i) = i
+ end do
+ call foo (p, q, c_loc (r(1)), s)
+ do i = 1, 1024
+ if (p(i) /= i * i + 3 * i + 2) call abort
+ p(i) = i
+ end do
+ call bar (p, q, c_loc (r(1)), s)
+ do i = 1, 1024
+ if (p(i) /= i * i + 3 * i + 2) call abort
+ end do
+ ! Attempt to create 64-byte aligned allocatable
+ do i = 1, 64
+ allocate (c(1023 + i))
+ if (iand (loc (c(1)), 63) == 0) exit
+ deallocate (c)
+ allocate (b(i)%a(1023 + i))
+ allocate (c(1023 + i))
+ if (iand (loc (c(1)), 63) == 0) exit
+ deallocate (c)
+ end do
+ if (allocated (c)) then
+ do i = 1, 1024
+ c(i) = 2 * i
+ end do
+ call baz (p, c)
+ do i = 1, 1024
+ if (p(i) /= i * i + 5 * i + 2) call abort
+ end do
+ end if
+end
+subroutine foo (x, y, z, w)
+ use iso_c_binding, only : c_ptr, c_f_pointer
+ real, pointer :: x(:), y(:), w(:), p(:)
+ type(c_ptr) :: z
+ integer :: i
+ real :: pt(1024)
+ pointer (ip, pt)
+ ip = loc (w)
+!$omp simd aligned (x, y : 64)
+ do i = 1, 1024
+ x(i) = x(i) * y(i) + 2.0
+ end do
+!$omp simd aligned (x, z : 64) private (p)
+ do i = 1, 1024
+ call c_f_pointer (z, p, shape=[1024])
+ x(i) = x(i) + p(i)
+ end do
+!$omp simd aligned (x, ip : 64)
+ do i = 1, 1024
+ x(i) = x(i) + 2 * pt(i)
+ end do
+!$omp end simd
+end subroutine
+subroutine bar (x, y, z, w)
+ use iso_c_binding, only : c_ptr, c_f_pointer
+ real, pointer :: x(:), y(:), w(:), a(:), b(:)
+ type(c_ptr) :: z, c
+ integer :: i
+ real :: pt(1024)
+ pointer (ip, pt)
+ ip = loc (w)
+ a => x
+ b => y
+ c = z
+!$omp simd aligned (a, b : 64)
+ do i = 1, 1024
+ a(i) = a(i) * b(i) + 2.0
+ end do
+!$omp simd aligned (a, c : 64)
+ do i = 1, 1024
+ block
+ real, pointer :: p(:)
+ call c_f_pointer (c, p, shape=[1024])
+ a(i) = a(i) + p(i)
+ end block
+ end do
+!$omp simd aligned (a, ip : 64)
+ do i = 1, 1024
+ a(i) = a(i) + 2 * pt(i)
+ end do
+!$omp end simd
+end subroutine
+subroutine baz (x, c)
+ real, pointer :: x(:)
+ real, allocatable :: c(:)
+ integer :: i
+!$omp simd aligned (x, c : 64)
+ do i = 1, 1024
+ x(i) = x(i) + c(i)
+ end do
+!$omp end simd
+end subroutine baz
diff --git a/gcc/testsuite/gfortran.dg/graphite/pr68550-1.f90 b/gcc/testsuite/gfortran.dg/graphite/pr68550-1.f90
new file mode 100644
index 00000000000..beed63eb184
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/graphite/pr68550-1.f90
@@ -0,0 +1,36 @@
+! { dg-do compile }
+! { dg-options "-floop-nest-optimize -O2" }
+
+SUBROUTINE integrate_core_1(grid,coef_xyz,pol_x,pol_y,&
+ pol_z,map,sphere_bounds,cmax,gridbounds)
+ INTEGER, PARAMETER :: dp=8
+ INTEGER, INTENT(IN) :: sphere_bounds(*), cmax, &
+ map(-cmax:cmax,1:3), &
+ gridbounds(2,3)
+ REAL(dp), INTENT(IN) :: grid(gridbounds(1,1):gridbounds(2,1), &
+ gridbounds(1,2):gridbounds(2,2),&
+ gridbounds(1,3):gridbounds(2,3))
+ INTEGER, PARAMETER :: lp = 1
+ REAL(dp), INTENT(IN) :: pol_x(0:lp,-cmax:cmax), &
+ pol_y(1:2,0:lp,-cmax:0), &
+ pol_z(1:2,0:lp,-cmax:0)
+ REAL(dp), INTENT(OUT) :: coef_xyz(((lp+1)*(lp+2)*(lp+3))/6)
+ INTEGER :: i, ig, igmax, igmin, j, j2, &
+ jg, jg2, jgmin, k, k2, kg, &
+ kg2, kgmin, lxp, sci
+ REAL(dp) :: coef_x(4,0:lp), &
+ coef_xy(2,((lp+1)*(lp+2))/2), &
+ s(4)
+ DO kg=kgmin,0
+ DO jg=jgmin,0
+ coef_x=0.0_dp
+ DO ig=igmin,igmax
+ DO lxp=0,lp
+ coef_x(:,lxp)=coef_x(:,lxp)+s(:)*pol_x(lxp,ig)
+ ENDDO
+ END DO
+ coef_xy(:,3)=coef_xy(:,3)+coef_x(3:4,0)*pol_y(2,1,jg)
+ END DO
+ coef_xyz(3)=coef_xyz(3)+coef_xy(1,3)*pol_z(1,0,kg)
+ END DO
+ END SUBROUTINE integrate_core_1
diff --git a/gcc/testsuite/gfortran.dg/graphite/pr68550-2.f90 b/gcc/testsuite/gfortran.dg/graphite/pr68550-2.f90
new file mode 100644
index 00000000000..fae0c92a7dc
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/graphite/pr68550-2.f90
@@ -0,0 +1,14 @@
+! { dg-do compile }
+! { dg-options "-floop-nest-optimize -fcheck=bounds -O1" }
+
+SUBROUTINE PD2VAL(RES,NDERIV,TG1,TG2,C0)
+ INTEGER, PARAMETER :: dp=8
+ REAL(KIND=dp), INTENT(OUT) :: res(*)
+ REAL(KIND=dp), INTENT(IN) :: TG1, TG2, C0(105,*)
+ REAL(KIND=dp) :: T1(0:13), T2(0:13)
+ DO K=1,NDERIV+1
+ RES(K)=RES(K)+DOT_PRODUCT(T1(0:7),C0(70:77,K))*T2(6)
+ RES(K)=RES(K)+DOT_PRODUCT(T1(0:4),C0(91:95,K))*T2(9)
+ RES(K)=RES(K)+DOT_PRODUCT(T1(0:3),C0(96:99,K))*T2(10)
+ ENDDO
+END SUBROUTINE PD2VAL
diff --git a/gcc/testsuite/gfortran.dg/graphite/run-id-3.f90 b/gcc/testsuite/gfortran.dg/graphite/run-id-3.f90
new file mode 100644
index 00000000000..54139efcc8f
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/graphite/run-id-3.f90
@@ -0,0 +1,12 @@
+! { dg-do run }
+! { dg-options "-ffrontend-optimize -floop-nest-optimize" }
+! PR 56872 - wrong front-end optimization with a single constructor.
+! Original bug report by Rich Townsend.
+ integer :: k
+ real :: s
+ integer :: m
+ s = 2.0
+ m = 4
+ res = SUM([(s**(REAL(k-1)/REAL(m-1)),k=1,m)])
+ if (abs(res - 5.84732246) > 1e-6) call abort
+ end
diff --git a/gcc/testsuite/gfortran.dg/pr68379-1.f90 b/gcc/testsuite/gfortran.dg/pr68379-1.f90
new file mode 100644
index 00000000000..2deaca03219
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/pr68379-1.f90
@@ -0,0 +1,35 @@
+! { dg-do compile }
+! { dg-options "-O3" }
+MODULE qs_efield_berry
+ TYPE cp_error_type
+ END TYPE
+ INTEGER, PARAMETER :: dp=8
+ TYPE qs_energy_type
+ REAL(KIND=dp), POINTER :: efield
+ END TYPE
+ TYPE qs_environment_type
+ END TYPE
+ INTERFACE
+ SUBROUTINE foo(qs_env,energy,error)
+ IMPORT
+ TYPE(qs_environment_type), POINTER :: qs_env
+ TYPE(cp_error_type) :: error
+ TYPE(qs_energy_type), POINTER :: energy
+ END SUBROUTINE
+ END INTERFACE
+CONTAINS
+ SUBROUTINE qs_efield_mo_derivatives()
+ TYPE(qs_environment_type), POINTER :: qs_env
+ TYPE(cp_error_type) :: error
+ COMPLEX(dp) :: zi(3), zphase(3)
+ REAL(dp) :: ci(3)
+ TYPE(qs_energy_type), POINTER :: energy
+ CALL foo(qs_env, energy, error)
+ zi = zi * zphase
+ ci = AIMAG(LOG(zi))
+ DO idir=1,3
+ ener_field=ener_field+ci(idir)*fieldfac(idir)
+ END DO
+ energy%efield=ener_field
+ END SUBROUTINE qs_efield_mo_derivatives
+END MODULE qs_efield_berry
diff --git a/gcc/testsuite/gfortran.dg/pr68379-2.f b/gcc/testsuite/gfortran.dg/pr68379-2.f
new file mode 100644
index 00000000000..e26520e133b
--- /dev/null
+++ b/gcc/testsuite/gfortran.dg/pr68379-2.f
@@ -0,0 +1,24 @@
+! { dg-do compile }
+! { dg-additional-options "-Ofast" }
+! { dg-additional-options "-mavx" { target x86_64-*-* i?86-*-* } }
+
+ SUBROUTINE PASSB4 (IDO,L1,CC,CH,WA1,WA2,WA3)
+ IMPLICIT REAL(4) (A-H, O-Z)
+ DIMENSION CC(IDO,4,L1), CH(IDO,L1,4), WA1(*), WA2(*), WA3(*)
+ 102 DO 104 K=1,L1
+ DO 103 I=2,IDO,2
+ TI1 = CC(I,1,K)-CC(I,3,K)
+ TI2 = CC(I,1,K)+CC(I,3,K)
+ TI3 = CC(I,2,K)+CC(I,4,K)
+ TR2 = CC(I-1,1,K)+CC(I-1,3,K)
+ TI4 = CC(I-1,2,K)-CC(I-1,4,K)
+ TR3 = CC(I-1,2,K)+CC(I-1,4,K)
+ CH(I-1,K,1) = TR2+TR3
+ CH(I,K,1) = TI2+TI3
+ CI4 = TI1-TI4
+ CH(I-1,K,4) = CI4
+ CH(I,K,4) = CI4
+ 103 CONTINUE
+ 104 CONTINUE
+ RETURN
+ END
diff --git a/gcc/testsuite/gfortran.fortran-torture/compile/pr68639.f90 b/gcc/testsuite/gfortran.fortran-torture/compile/pr68639.f90
new file mode 100644
index 00000000000..bd1c3a3a4df
--- /dev/null
+++ b/gcc/testsuite/gfortran.fortran-torture/compile/pr68639.f90
@@ -0,0 +1,22 @@
+ SUBROUTINE makeCoulE0(natorb,Coul)
+ INTEGER, PARAMETER :: dp=8
+ REAL(KIND=dp), PARAMETER :: fourpi=432.42, oorootpi=13413.3142
+ INTEGER :: natorb
+ REAL(KIND=dp), DIMENSION(45, 45), &
+ INTENT(OUT) :: Coul
+ INTEGER :: gpt, imA, imB, k1, k2, k3, &
+ k4, lp, mp, np
+ REAL(KIND=dp) :: alpha, d2f(3,3), &
+ d4f(3,3,3,3), f, ff, w
+ REAL(KIND=dp), DIMENSION(3, 45) :: M1A
+ REAL(KIND=dp), DIMENSION(45) :: M0A
+ DO imA=1, (natorb*(natorb+1))/2
+ DO imB=1, (natorb*(natorb+1))/2
+ w= M0A(imA)*M0A(imB)
+ DO k1=1,3
+ w=w+ M1A(k1,imA)*M1A(k1,imB)
+ ENDDO
+ Coul(imA,imB)=Coul(imA,imB)-4.0_dp*alpha**3*oorootpi*w/3.0_dp
+ ENDDO
+ ENDDO
+ END SUBROUTINE makeCoulE0
diff --git a/gcc/testsuite/lib/g++-dg.exp b/gcc/testsuite/lib/g++-dg.exp
index 421f8b62bee..be63dea3455 100644
--- a/gcc/testsuite/lib/g++-dg.exp
+++ b/gcc/testsuite/lib/g++-dg.exp
@@ -43,9 +43,20 @@ proc g++-dg-runtest { testcases flags default-extra-flags } {
# if there's a dg-options line.
if ![search_for $test "-std=*++"] {
if [search_for $test "dg-options"] {
- set option_list { -std=gnu++98 -std=gnu++11 -std=gnu++14 }
+ set std_prefix "-std=gnu++"
} else {
- set option_list { -std=c++98 -std=c++11 -std=c++14 }
+ set std_prefix "-std=c++"
+ }
+
+ global gpp_std_list
+ if { [llength $gpp_std_list] > 0 } {
+ set std_list $gpp_std_list
+ } else {
+ set std_list { 98 11 14 }
+ }
+ set option_list { }
+ foreach x $std_list {
+ lappend option_list "${std_prefix}$x"
}
} else {
set option_list { "" }
diff --git a/gcc/testsuite/lib/g++.exp b/gcc/testsuite/lib/g++.exp
index 229fbc3f633..0b99903dd70 100644
--- a/gcc/testsuite/lib/g++.exp
+++ b/gcc/testsuite/lib/g++.exp
@@ -32,6 +32,7 @@ load_lib target-libpath.exp
set gpp_compile_options ""
+set gpp_std_list { }
#
# g++_version -- extract and print the version number of the compiler
@@ -367,6 +368,14 @@ proc ${tool}_option_proc { option } {
}
verbose -log "gpp_compile_options set to $gpp_compile_options"
return 1
+ } elseif [regexp "^--stds=" $option] {
+ global gpp_std_list
+ regsub "^--stds=" $option "" option
+ foreach x [split $option ","] {
+ lappend gpp_std_list "$x"
+ }
+ verbose -log "gpp_std_list set to $gpp_std_list"
+ return 1
} else {
return 0
}
diff --git a/gcc/testsuite/lib/target-supports.exp b/gcc/testsuite/lib/target-supports.exp
index 2275fd3f44c..4e349e9832e 100644
--- a/gcc/testsuite/lib/target-supports.exp
+++ b/gcc/testsuite/lib/target-supports.exp
@@ -5404,6 +5404,7 @@ proc check_effective_target_sync_int_128_runtime { } {
# Return 1 if the target supports atomic operations on "long long".
#
# Note: 32bit x86 targets require -march=pentium in dg-options.
+# Note: 32bit s390 targets require -mzarch in dg-options.
proc check_effective_target_sync_long_long { } {
if { [istarget x86_64-*-*] || [istarget i?86-*-*])
@@ -5411,6 +5412,7 @@ proc check_effective_target_sync_long_long { } {
|| [istarget arm*-*-*]
|| [istarget alpha*-*-*]
|| ([istarget sparc*-*-*] && [check_effective_target_lp64])
+ || [istarget s390*-*-*]
|| [istarget spu-*-*] } {
return 1
} else {
@@ -5543,6 +5545,8 @@ proc check_effective_target_bswap32 { } {
}
# Return 1 if the target supports 64-bit byte swap instructions.
+#
+# Note: 32bit s390 targets require -mzarch in dg-options.
proc check_effective_target_bswap64 { } {
global et_bswap64_saved
diff --git a/gcc/toplev.c b/gcc/toplev.c
index 5aade2fb739..aee55fc932b 100644
--- a/gcc/toplev.c
+++ b/gcc/toplev.c
@@ -1237,7 +1237,7 @@ process_options (void)
#ifndef HAVE_isl
if (flag_graphite
- || flag_loop_optimize_isl
+ || flag_loop_nest_optimize
|| flag_graphite_identity
|| flag_loop_parallelize_all)
sorry ("Graphite loop optimizations cannot be used (ISL is not available)"
diff --git a/gcc/tree-call-cdce.c b/gcc/tree-call-cdce.c
index 75ef180933b..4123130ab2a 100644
--- a/gcc/tree-call-cdce.c
+++ b/gcc/tree-call-cdce.c
@@ -959,7 +959,8 @@ use_internal_fn (gcall *call)
{
unsigned nconds = 0;
auto_vec<gimple *, 12> conds;
- gen_shrink_wrap_conditions (call, conds, &nconds);
+ if (can_test_argument_range (call))
+ gen_shrink_wrap_conditions (call, conds, &nconds);
if (nconds == 0 && !edom_only_function (call))
return false;
diff --git a/gcc/tree-cfgcleanup.c b/gcc/tree-cfgcleanup.c
index 9eee7bb8606..40ad5ca33cd 100644
--- a/gcc/tree-cfgcleanup.c
+++ b/gcc/tree-cfgcleanup.c
@@ -614,8 +614,6 @@ fixup_noreturn_call (gimple *stmt)
static bool
cleanup_tree_cfg_bb (basic_block bb)
{
- bool retval = cleanup_control_flow_bb (bb);
-
if (tree_forwarder_block_p (bb, false)
&& remove_forwarder_block (bb))
return true;
@@ -640,7 +638,7 @@ cleanup_tree_cfg_bb (basic_block bb)
}
}
- return retval;
+ return false;
}
/* Iterate the cfg cleanups, while anything changes. */
@@ -660,8 +658,26 @@ cleanup_tree_cfg_1 (void)
recording of edge to CASE_LABEL_EXPR. */
start_recording_case_labels ();
- /* Start by iterating over all basic blocks. We cannot use FOR_EACH_BB_FN,
+ /* We cannot use FOR_EACH_BB_FN for the BB iterations below
since the basic blocks may get removed. */
+
+ /* Start by iterating over all basic blocks looking for edge removal
+ opportunities. Do this first because incoming SSA form may be
+ invalid and we want to avoid performing SSA related tasks such
+ as propgating out a PHI node during BB merging in that state. */
+ n = last_basic_block_for_fn (cfun);
+ for (i = NUM_FIXED_BLOCKS; i < n; i++)
+ {
+ bb = BASIC_BLOCK_FOR_FN (cfun, i);
+ if (bb)
+ retval |= cleanup_control_flow_bb (bb);
+ }
+
+ /* After doing the above SSA form should be valid (or an update SSA
+ should be required). */
+
+ /* Continue by iterating over all basic blocks looking for BB merging
+ opportunities. */
n = last_basic_block_for_fn (cfun);
for (i = NUM_FIXED_BLOCKS; i < n; i++)
{
@@ -682,6 +698,7 @@ cleanup_tree_cfg_1 (void)
if (!bb)
continue;
+ retval |= cleanup_control_flow_bb (bb);
retval |= cleanup_tree_cfg_bb (bb);
}
diff --git a/gcc/tree-nested.c b/gcc/tree-nested.c
index 8b5aba20a01..da19e8d3d35 100644
--- a/gcc/tree-nested.c
+++ b/gcc/tree-nested.c
@@ -1072,6 +1072,7 @@ convert_nonlocal_omp_clauses (tree *pclauses, struct walk_stmt_info *wi)
case OMP_CLAUSE_SHARED:
case OMP_CLAUSE_TO_DECLARE:
case OMP_CLAUSE_LINK:
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
do_decl_clause:
@@ -1743,6 +1744,7 @@ convert_local_omp_clauses (tree *pclauses, struct walk_stmt_info *wi)
case OMP_CLAUSE_SHARED:
case OMP_CLAUSE_TO_DECLARE:
case OMP_CLAUSE_LINK:
+ case OMP_CLAUSE_USE_DEVICE:
case OMP_CLAUSE_USE_DEVICE_PTR:
case OMP_CLAUSE_IS_DEVICE_PTR:
do_decl_clause:
diff --git a/gcc/tree-ssa-math-opts.c b/gcc/tree-ssa-math-opts.c
index 66d750138a0..b00f046074b 100644
--- a/gcc/tree-ssa-math-opts.c
+++ b/gcc/tree-ssa-math-opts.c
@@ -110,6 +110,7 @@ along with GCC; see the file COPYING3. If not see
#include "tree-ssa.h"
#include "builtins.h"
#include "params.h"
+#include "internal-fn.h"
#include "case-cfn-macros.h"
/* This structure represents one basic block that either computes a
@@ -497,6 +498,31 @@ execute_cse_reciprocals_1 (gimple_stmt_iterator *def_gsi, tree def)
occ_head = NULL;
}
+/* Return an internal function that implements the reciprocal of CALL,
+ or IFN_LAST if there is no such function that the target supports. */
+
+internal_fn
+internal_fn_reciprocal (gcall *call)
+{
+ internal_fn ifn;
+
+ switch (gimple_call_combined_fn (call))
+ {
+ CASE_CFN_SQRT:
+ ifn = IFN_RSQRT;
+ break;
+
+ default:
+ return IFN_LAST;
+ }
+
+ tree_pair types = direct_internal_fn_types (ifn, call);
+ if (!direct_internal_fn_supported_p (ifn, types, OPTIMIZE_FOR_SPEED))
+ return IFN_LAST;
+
+ return ifn;
+}
+
/* Go through all the floating-point SSA_NAMEs, and call
execute_cse_reciprocals_1 on each of them. */
namespace {
@@ -586,7 +612,6 @@ pass_cse_reciprocals::execute (function *fun)
gsi_next (&gsi))
{
gimple *stmt = gsi_stmt (gsi);
- tree fndecl;
if (is_gimple_assign (stmt)
&& gimple_assign_rhs_code (stmt) == RDIV_EXPR)
@@ -600,20 +625,25 @@ pass_cse_reciprocals::execute (function *fun)
stmt1 = SSA_NAME_DEF_STMT (arg1);
if (is_gimple_call (stmt1)
- && gimple_call_lhs (stmt1)
- && (gimple_call_internal_p (stmt1)
- || ((fndecl = gimple_call_fndecl (stmt1))
- && (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL
- || (DECL_BUILT_IN_CLASS (fndecl)
- == BUILT_IN_MD)))))
+ && gimple_call_lhs (stmt1))
{
bool fail;
imm_use_iterator ui;
use_operand_p use_p;
+ tree fndecl = NULL_TREE;
- fndecl = targetm.builtin_reciprocal (as_a <gcall *> (stmt1));
- if (!fndecl)
- continue;
+ gcall *call = as_a <gcall *> (stmt1);
+ internal_fn ifn = internal_fn_reciprocal (call);
+ if (ifn == IFN_LAST)
+ {
+ fndecl = gimple_call_fndecl (call);
+ if (!fndecl
+ || DECL_BUILT_IN_CLASS (fndecl) != BUILT_IN_MD)
+ continue;
+ fndecl = targetm.builtin_reciprocal (fndecl);
+ if (!fndecl)
+ continue;
+ }
/* Check that all uses of the SSA name are divisions,
otherwise replacing the defining statement will do
@@ -636,28 +666,35 @@ pass_cse_reciprocals::execute (function *fun)
if (fail)
continue;
- gimple_replace_ssa_lhs (stmt1, arg1);
- if (gimple_call_internal_p (stmt1))
+ gimple_replace_ssa_lhs (call, arg1);
+ if (gimple_call_internal_p (call) != (ifn != IFN_LAST))
{
auto_vec<tree, 4> args;
for (unsigned int i = 0;
- i < gimple_call_num_args (stmt1); i++)
- args.safe_push (gimple_call_arg (stmt1, i));
- gcall *stmt2 = gimple_build_call_vec (fndecl, args);
+ i < gimple_call_num_args (call); i++)
+ args.safe_push (gimple_call_arg (call, i));
+ gcall *stmt2;
+ if (ifn == IFN_LAST)
+ stmt2 = gimple_build_call_vec (fndecl, args);
+ else
+ stmt2 = gimple_build_call_internal_vec (ifn, args);
gimple_call_set_lhs (stmt2, arg1);
- if (gimple_vdef (stmt1))
+ if (gimple_vdef (call))
{
- gimple_set_vdef (stmt2, gimple_vdef (stmt1));
+ gimple_set_vdef (stmt2, gimple_vdef (call));
SSA_NAME_DEF_STMT (gimple_vdef (stmt2)) = stmt2;
}
- gimple_set_vuse (stmt2, gimple_vuse (stmt1));
- gimple_stmt_iterator gsi2 = gsi_for_stmt (stmt1);
+ gimple_set_vuse (stmt2, gimple_vuse (call));
+ gimple_stmt_iterator gsi2 = gsi_for_stmt (call);
gsi_replace (&gsi2, stmt2, true);
}
else
{
- gimple_call_set_fndecl (stmt1, fndecl);
- update_stmt (stmt1);
+ if (ifn == IFN_LAST)
+ gimple_call_set_fndecl (call, fndecl);
+ else
+ gimple_call_set_internal_fn (call, ifn);
+ update_stmt (call);
}
reciprocal_stats.rfuncs_inserted++;
diff --git a/gcc/tree-ssa-structalias.c b/gcc/tree-ssa-structalias.c
index 7f4a8ad60e4..060ff3efc1d 100644
--- a/gcc/tree-ssa-structalias.c
+++ b/gcc/tree-ssa-structalias.c
@@ -4507,15 +4507,32 @@ find_func_aliases_for_builtin_call (struct function *fn, gcall *t)
return true;
}
case BUILT_IN_GOMP_PARALLEL:
+ case BUILT_IN_GOACC_PARALLEL:
{
- /* Handle __builtin_GOMP_parallel (fn, data, num_threads, flags) as
- fn (data). */
if (in_ipa_mode)
{
- tree fnarg = gimple_call_arg (t, 0);
+ unsigned int fnpos, argpos;
+ switch (DECL_FUNCTION_CODE (fndecl))
+ {
+ case BUILT_IN_GOMP_PARALLEL:
+ /* __builtin_GOMP_parallel (fn, data, num_threads, flags). */
+ fnpos = 0;
+ argpos = 1;
+ break;
+ case BUILT_IN_GOACC_PARALLEL:
+ /* __builtin_GOACC_parallel (device, fn, mapnum, hostaddrs,
+ sizes, kinds, ...). */
+ fnpos = 1;
+ argpos = 3;
+ break;
+ default:
+ gcc_unreachable ();
+ }
+
+ tree fnarg = gimple_call_arg (t, fnpos);
gcc_assert (TREE_CODE (fnarg) == ADDR_EXPR);
tree fndecl = TREE_OPERAND (fnarg, 0);
- tree arg = gimple_call_arg (t, 1);
+ tree arg = gimple_call_arg (t, argpos);
gcc_assert (TREE_CODE (arg) == ADDR_EXPR);
varinfo_t fi = get_vi_for_tree (fndecl);
@@ -5064,6 +5081,7 @@ find_func_clobbers (struct function *fn, gimple *origt)
case BUILT_IN_VA_END:
return;
case BUILT_IN_GOMP_PARALLEL:
+ case BUILT_IN_GOACC_PARALLEL:
return;
/* printf-style functions may have hooks to set pointers to
point to somewhere into the generated string. Leave them
@@ -7547,6 +7565,8 @@ ipa_pta_execute (void)
/* Handle direct calls to functions with body. */
if (gimple_call_builtin_p (stmt, BUILT_IN_GOMP_PARALLEL))
decl = TREE_OPERAND (gimple_call_arg (stmt, 0), 0);
+ else if (gimple_call_builtin_p (stmt, BUILT_IN_GOACC_PARALLEL))
+ decl = TREE_OPERAND (gimple_call_arg (stmt, 1), 0);
else
decl = gimple_call_fndecl (stmt);
diff --git a/gcc/tree-ssa.c b/gcc/tree-ssa.c
index 02fca4c8e67..ddc7a657cbd 100644
--- a/gcc/tree-ssa.c
+++ b/gcc/tree-ssa.c
@@ -119,10 +119,10 @@ redirect_edge_var_map_vector (edge e)
/* Clear the edge variable mappings. */
void
-redirect_edge_var_map_destroy (void)
+redirect_edge_var_map_empty (void)
{
- delete edge_var_maps;
- edge_var_maps = NULL;
+ if (edge_var_maps)
+ edge_var_maps->empty ();
}
@@ -1128,7 +1128,7 @@ delete_tree_ssa (struct function *fn)
fn->gimple_df = NULL;
/* We no longer need the edge variable maps. */
- redirect_edge_var_map_destroy ();
+ redirect_edge_var_map_empty ();
}
/* Return true if EXPR is a useless type conversion, otherwise return
diff --git a/gcc/tree-ssa.h b/gcc/tree-ssa.h
index 3b5bd706593..d33eb9c82fe 100644
--- a/gcc/tree-ssa.h
+++ b/gcc/tree-ssa.h
@@ -35,7 +35,7 @@ extern void redirect_edge_var_map_add (edge, tree, tree, source_location);
extern void redirect_edge_var_map_clear (edge);
extern void redirect_edge_var_map_dup (edge, edge);
extern vec<edge_var_map> *redirect_edge_var_map_vector (edge);
-extern void redirect_edge_var_map_destroy (void);
+extern void redirect_edge_var_map_empty (void);
extern edge ssa_redirect_edge (edge, basic_block);
extern void flush_pending_stmts (edge);
extern void gimple_replace_ssa_lhs (gimple *, tree);
diff --git a/gcc/tree-streamer-in.c b/gcc/tree-streamer-in.c
index 7eeab8a2a29..3162d1ae2b5 100644
--- a/gcc/tree-streamer-in.c
+++ b/gcc/tree-streamer-in.c
@@ -366,7 +366,6 @@ unpack_ts_type_common_value_fields (struct bitpack_d *bp, tree expr)
TYPE_RESTRICT (expr) = (unsigned) bp_unpack_value (bp, 1);
TYPE_USER_ALIGN (expr) = (unsigned) bp_unpack_value (bp, 1);
TYPE_READONLY (expr) = (unsigned) bp_unpack_value (bp, 1);
- TYPE_ALIAS_SET (expr) = bp_unpack_value (bp, 1) ? 0 : -1;
if (RECORD_OR_UNION_TYPE_P (expr))
{
TYPE_TRANSPARENT_AGGR (expr) = (unsigned) bp_unpack_value (bp, 1);
diff --git a/gcc/tree-streamer-out.c b/gcc/tree-streamer-out.c
index ab9b7476635..bfd06449ecb 100644
--- a/gcc/tree-streamer-out.c
+++ b/gcc/tree-streamer-out.c
@@ -317,13 +317,9 @@ pack_ts_type_common_value_fields (struct bitpack_d *bp, tree expr)
bp_pack_value (bp, TYPE_RESTRICT (expr), 1);
bp_pack_value (bp, TYPE_USER_ALIGN (expr), 1);
bp_pack_value (bp, TYPE_READONLY (expr), 1);
- /* Make sure to preserve the fact whether the frontend would assign
- alias-set zero to this type. Do that only for main variants, because
- type variants alias sets are never computed.
- FIXME: This does not work for pre-streamed builtin types. */
- bp_pack_value (bp, (TYPE_ALIAS_SET (expr) == 0
- || (!in_lto_p && TYPE_MAIN_VARIANT (expr) == expr
- && get_alias_set (expr) == 0)), 1);
+ /* We used to stream TYPE_ALIAS_SET == 0 information to let frontends mark
+ types that are opaque for TBAA. This however did not work as intended,
+ becuase TYPE_ALIAS_SET == 0 was regularly lost in type merging. */
if (RECORD_OR_UNION_TYPE_P (expr))
{
bp_pack_value (bp, TYPE_TRANSPARENT_AGGR (expr), 1);
diff --git a/gcc/tree-vect-data-refs.c b/gcc/tree-vect-data-refs.c
index 7962e360fb9..8810af1bfcd 100644
--- a/gcc/tree-vect-data-refs.c
+++ b/gcc/tree-vect-data-refs.c
@@ -2102,11 +2102,16 @@ vect_slp_analyze_and_verify_node_alignment (slp_tree node)
the node is permuted in which case we start from the first
element in the group. */
gimple *first_stmt = SLP_TREE_SCALAR_STMTS (node)[0];
+ data_reference_p first_dr = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt));
if (SLP_TREE_LOAD_PERMUTATION (node).exists ())
first_stmt = GROUP_FIRST_ELEMENT (vinfo_for_stmt (first_stmt));
data_reference_p dr = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt));
if (! vect_compute_data_ref_alignment (dr)
+ /* For creating the data-ref pointer we need alignment of the
+ first element anyway. */
+ || (dr != first_dr
+ && ! vect_compute_data_ref_alignment (first_dr))
|| ! verify_data_ref_alignment (dr))
{
if (dump_enabled_p ())
@@ -2592,6 +2597,12 @@ dr_group_sort_cmp (const void *dra_, const void *drb_)
if (dra == drb)
return 0;
+ /* DRs in different loops never belong to the same group. */
+ loop_p loopa = gimple_bb (DR_STMT (dra))->loop_father;
+ loop_p loopb = gimple_bb (DR_STMT (drb))->loop_father;
+ if (loopa != loopb)
+ return loopa->num < loopb->num ? -1 : 1;
+
/* Ordering of DRs according to base. */
if (!operand_equal_p (DR_BASE_ADDRESS (dra), DR_BASE_ADDRESS (drb), 0))
{
@@ -2683,6 +2694,12 @@ vect_analyze_data_ref_accesses (vec_info *vinfo)
matters we can push those to a worklist and re-iterate
over them. The we can just skip ahead to the next DR here. */
+ /* DRs in a different loop should not be put into the same
+ interleaving group. */
+ if (gimple_bb (DR_STMT (dra))->loop_father
+ != gimple_bb (DR_STMT (drb))->loop_father)
+ break;
+
/* Check that the data-refs have same first location (except init)
and they are both either store or load (not load and store,
not masked loads or stores). */
diff --git a/gcc/tree-vect-patterns.c b/gcc/tree-vect-patterns.c
index 5bab1f57a18..4b225fbb4ca 100644
--- a/gcc/tree-vect-patterns.c
+++ b/gcc/tree-vect-patterns.c
@@ -312,6 +312,9 @@ vect_recog_dot_prod_pattern (vec<gimple *> *stmts, tree *type_in,
{
gimple *def_stmt;
+ if (STMT_VINFO_DEF_TYPE (stmt_vinfo) != vect_reduction_def
+ && ! STMT_VINFO_GROUP_FIRST_ELEMENT (stmt_vinfo))
+ return NULL;
oprnd0 = gimple_assign_rhs1 (last_stmt);
oprnd1 = gimple_assign_rhs2 (last_stmt);
if (!types_compatible_p (TREE_TYPE (oprnd0), type)
@@ -531,6 +534,9 @@ vect_recog_sad_pattern (vec<gimple *> *stmts, tree *type_in,
{
gimple *def_stmt;
+ if (STMT_VINFO_DEF_TYPE (stmt_vinfo) != vect_reduction_def
+ && ! STMT_VINFO_GROUP_FIRST_ELEMENT (stmt_vinfo))
+ return NULL;
plus_oprnd0 = gimple_assign_rhs1 (last_stmt);
plus_oprnd1 = gimple_assign_rhs2 (last_stmt);
if (!types_compatible_p (TREE_TYPE (plus_oprnd0), sum_type)
@@ -1056,7 +1062,9 @@ vect_recog_pow_pattern (vec<gimple *> *stmts, tree *type_in,
&& real_equal (&TREE_REAL_CST (exp), &dconsthalf))
{
*type_in = get_vectype_for_scalar_type (TREE_TYPE (base));
- if (*type_in && direct_internal_fn_supported_p (IFN_SQRT, *type_in))
+ if (*type_in
+ && direct_internal_fn_supported_p (IFN_SQRT, *type_in,
+ OPTIMIZE_FOR_SPEED))
{
gcall *stmt = gimple_build_call_internal (IFN_SQRT, 1, base);
var = vect_recog_temp_ssa_var (TREE_TYPE (base), stmt);
@@ -1150,6 +1158,10 @@ vect_recog_widen_sum_pattern (vec<gimple *> *stmts, tree *type_in,
if (gimple_assign_rhs_code (last_stmt) != PLUS_EXPR)
return NULL;
+ if (STMT_VINFO_DEF_TYPE (stmt_vinfo) != vect_reduction_def
+ && ! STMT_VINFO_GROUP_FIRST_ELEMENT (stmt_vinfo))
+ return NULL;
+
oprnd0 = gimple_assign_rhs1 (last_stmt);
oprnd1 = gimple_assign_rhs2 (last_stmt);
if (!types_compatible_p (TREE_TYPE (oprnd0), type)
diff --git a/gcc/tree-vect-slp.c b/gcc/tree-vect-slp.c
index 5693ca5e35e..b8936823067 100644
--- a/gcc/tree-vect-slp.c
+++ b/gcc/tree-vect-slp.c
@@ -430,8 +430,7 @@ static bool
vect_build_slp_tree_1 (vec_info *vinfo,
vec<gimple *> stmts, unsigned int group_size,
unsigned nops, unsigned int *max_nunits,
- unsigned int vectorization_factor, bool *matches,
- bool *two_operators)
+ bool *matches, bool *two_operators)
{
unsigned int i;
gimple *first_stmt = stmts[0], *stmt = stmts[0];
@@ -523,11 +522,7 @@ vect_build_slp_tree_1 (vec_info *vinfo,
/* In case of multiple types we need to detect the smallest type. */
if (*max_nunits < TYPE_VECTOR_SUBPARTS (vectype))
- {
- *max_nunits = TYPE_VECTOR_SUBPARTS (vectype);
- if (is_a <bb_vec_info> (vinfo))
- vectorization_factor = *max_nunits;
- }
+ *max_nunits = TYPE_VECTOR_SUBPARTS (vectype);
if (gcall *call_stmt = dyn_cast <gcall *> (stmt))
{
@@ -700,31 +695,6 @@ vect_build_slp_tree_1 (vec_info *vinfo,
else
{
/* Load. */
- /* Check that the size of interleaved loads group is not
- greater than the SLP group size. */
- unsigned ncopies
- = vectorization_factor / TYPE_VECTOR_SUBPARTS (vectype);
- if (is_a <loop_vec_info> (vinfo)
- && GROUP_FIRST_ELEMENT (vinfo_for_stmt (stmt)) == stmt
- && ((GROUP_SIZE (vinfo_for_stmt (stmt))
- - GROUP_GAP (vinfo_for_stmt (stmt)))
- > ncopies * group_size))
- {
- if (dump_enabled_p ())
- {
- dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
- "Build SLP failed: the number "
- "of interleaved loads is greater than "
- "the SLP group size ");
- dump_gimple_stmt (MSG_MISSED_OPTIMIZATION, TDF_SLIM,
- stmt, 0);
- dump_printf (MSG_MISSED_OPTIMIZATION, "\n");
- }
- /* Fatal mismatch. */
- matches[0] = false;
- return false;
- }
-
first_load = GROUP_FIRST_ELEMENT (vinfo_for_stmt (stmt));
if (prev_first_load)
{
@@ -871,7 +841,6 @@ vect_build_slp_tree (vec_info *vinfo,
slp_tree *node, unsigned int group_size,
unsigned int *max_nunits,
vec<slp_tree> *loads,
- unsigned int vectorization_factor,
bool *matches, unsigned *npermutes, unsigned *tree_size,
unsigned max_tree_size)
{
@@ -895,8 +864,7 @@ vect_build_slp_tree (vec_info *vinfo,
bool two_operators = false;
if (!vect_build_slp_tree_1 (vinfo,
SLP_TREE_SCALAR_STMTS (*node), group_size, nops,
- max_nunits, vectorization_factor, matches,
- &two_operators))
+ max_nunits, matches, &two_operators))
return false;
SLP_TREE_TWO_OPERATORS (*node) = two_operators;
@@ -959,8 +927,7 @@ vect_build_slp_tree (vec_info *vinfo,
}
if (vect_build_slp_tree (vinfo, &child,
- group_size, max_nunits, loads,
- vectorization_factor, matches,
+ group_size, max_nunits, loads, matches,
npermutes, &this_tree_size, max_tree_size))
{
/* If we have all children of child built up from scalars then just
@@ -1074,7 +1041,6 @@ vect_build_slp_tree (vec_info *vinfo,
bool *tem = XALLOCAVEC (bool, group_size);
if (vect_build_slp_tree (vinfo, &child,
group_size, max_nunits, loads,
- vectorization_factor,
tem, npermutes, &this_tree_size,
max_tree_size))
{
@@ -1656,7 +1622,6 @@ vect_analyze_slp_instance (vec_info *vinfo,
unsigned int unrolling_factor = 1, nunits;
tree vectype, scalar_type = NULL_TREE;
gimple *next;
- unsigned int vectorization_factor = 0;
unsigned int i;
unsigned int max_nunits = 0;
vec<slp_tree> loads;
@@ -1697,12 +1662,7 @@ vect_analyze_slp_instance (vec_info *vinfo,
return false;
}
-
nunits = TYPE_VECTOR_SUBPARTS (vectype);
- if (is_a <loop_vec_info> (vinfo))
- vectorization_factor = as_a <loop_vec_info> (vinfo)->vectorization_factor;
- else
- vectorization_factor = nunits;
/* Calculate the unrolling factor. */
unrolling_factor = least_common_multiple (nunits, group_size) / group_size;
@@ -1755,8 +1715,7 @@ vect_analyze_slp_instance (vec_info *vinfo,
unsigned npermutes = 0;
if (vect_build_slp_tree (vinfo, &node, group_size,
&max_nunits, &loads,
- vectorization_factor, matches, &npermutes, NULL,
- max_tree_size))
+ matches, &npermutes, NULL, max_tree_size))
{
/* Calculate the unrolling factor based on the smallest type. */
if (max_nunits > nunits)
@@ -1852,7 +1811,7 @@ vect_analyze_slp_instance (vec_info *vinfo,
loads.release ();
/* For basic block SLP, try to break the group up into multiples of the
- vectorization factor. */
+ vector size. */
if (is_a <bb_vec_info> (vinfo)
&& GROUP_FIRST_ELEMENT (vinfo_for_stmt (stmt))
&& STMT_VINFO_GROUPED_ACCESS (vinfo_for_stmt (stmt)))
@@ -1862,11 +1821,11 @@ vect_analyze_slp_instance (vec_info *vinfo,
for (i = 0; i < group_size; i++)
if (!matches[i]) break;
- if (i >= vectorization_factor && i < group_size)
+ if (i >= nunits && i < group_size)
{
/* Split into two groups at the first vector boundary before i. */
- gcc_assert ((vectorization_factor & (vectorization_factor - 1)) == 0);
- unsigned group1_size = i & ~(vectorization_factor - 1);
+ gcc_assert ((nunits & (nunits - 1)) == 0);
+ unsigned group1_size = i & ~(nunits - 1);
gimple *rest = vect_split_slp_store_group (stmt, group1_size);
bool res = vect_analyze_slp_instance (vinfo, stmt, max_tree_size);
@@ -1874,9 +1833,9 @@ vect_analyze_slp_instance (vec_info *vinfo,
skip the rest of that vector. */
if (group1_size < i)
{
- i = group1_size + vectorization_factor;
+ i = group1_size + nunits;
if (i < group_size)
- rest = vect_split_slp_store_group (rest, vectorization_factor);
+ rest = vect_split_slp_store_group (rest, nunits);
}
if (i < group_size)
res |= vect_analyze_slp_instance (vinfo, rest, max_tree_size);
@@ -3274,18 +3233,6 @@ vect_transform_slp_perm_load (slp_tree node, vec<tree> dr_chain,
mode = TYPE_MODE (vectype);
- if (!can_vec_perm_p (mode, false, NULL))
- {
- if (dump_enabled_p ())
- {
- dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location,
- "no vect permute for ");
- dump_gimple_stmt (MSG_MISSED_OPTIMIZATION, TDF_SLIM, stmt, 0);
- dump_printf (MSG_MISSED_OPTIMIZATION, "\n");
- }
- return false;
- }
-
/* The generic VEC_PERM_EXPR code always uses an integral type of the
same size as the vector element being permuted. */
mask_element_type = lang_hooks.types.type_for_mode
diff --git a/gcc/tree-vect-stmts.c b/gcc/tree-vect-stmts.c
index 3b078da1320..9f116528b47 100644
--- a/gcc/tree-vect-stmts.c
+++ b/gcc/tree-vect-stmts.c
@@ -1300,7 +1300,25 @@ vect_init_vector (gimple *stmt, tree val, tree type, gimple_stmt_iterator *gsi)
{
if (!types_compatible_p (TREE_TYPE (type), TREE_TYPE (val)))
{
- if (CONSTANT_CLASS_P (val))
+ /* Scalar boolean value should be transformed into
+ all zeros or all ones value before building a vector. */
+ if (VECTOR_BOOLEAN_TYPE_P (type))
+ {
+ tree true_val = build_zero_cst (TREE_TYPE (type));
+ tree false_val = build_all_ones_cst (TREE_TYPE (type));
+
+ if (CONSTANT_CLASS_P (val))
+ val = integer_zerop (val) ? false_val : true_val;
+ else
+ {
+ new_temp = make_ssa_name (TREE_TYPE (type));
+ init_stmt = gimple_build_assign (new_temp, COND_EXPR,
+ val, true_val, false_val);
+ vect_init_vector_1 (stmt, init_stmt, gsi);
+ val = new_temp;
+ }
+ }
+ else if (CONSTANT_CLASS_P (val))
val = fold_convert (TREE_TYPE (type), val);
else
{
@@ -1663,7 +1681,8 @@ vectorizable_internal_function (combined_fn cfn, tree fndecl,
{
tree type0 = (info.type0 < 0 ? vectype_out : vectype_in);
tree type1 = (info.type1 < 0 ? vectype_out : vectype_in);
- if (direct_internal_fn_supported_p (ifn, tree_pair (type0, type1)))
+ if (direct_internal_fn_supported_p (ifn, tree_pair (type0, type1),
+ OPTIMIZE_FOR_SPEED))
return ifn;
}
}
@@ -2122,6 +2141,31 @@ vectorizable_mask_load_store (gimple *stmt, gimple_stmt_iterator *gsi,
return true;
}
+/* Return true if vector types VECTYPE_IN and VECTYPE_OUT have
+ integer elements and if we can narrow VECTYPE_IN to VECTYPE_OUT
+ in a single step. On success, store the binary pack code in
+ *CONVERT_CODE. */
+
+static bool
+simple_integer_narrowing (tree vectype_out, tree vectype_in,
+ tree_code *convert_code)
+{
+ if (!INTEGRAL_TYPE_P (TREE_TYPE (vectype_out))
+ || !INTEGRAL_TYPE_P (TREE_TYPE (vectype_in)))
+ return false;
+
+ tree_code code;
+ int multi_step_cvt = 0;
+ auto_vec <tree, 8> interm_types;
+ if (!supportable_narrowing_operation (NOP_EXPR, vectype_out, vectype_in,
+ &code, &multi_step_cvt,
+ &interm_types)
+ || multi_step_cvt)
+ return false;
+
+ *convert_code = code;
+ return true;
+}
/* Function vectorizable_call.
@@ -2288,7 +2332,12 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
tree callee = gimple_call_fndecl (stmt);
/* First try using an internal function. */
- if (cfn != CFN_LAST)
+ tree_code convert_code = ERROR_MARK;
+ if (cfn != CFN_LAST
+ && (modifier == NONE
+ || (modifier == NARROW
+ && simple_integer_narrowing (vectype_out, vectype_in,
+ &convert_code))))
ifn = vectorizable_internal_function (cfn, callee, vectype_out,
vectype_in);
@@ -2328,7 +2377,7 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
if (slp_node || PURE_SLP_STMT (stmt_info))
ncopies = 1;
- else if (modifier == NARROW)
+ else if (modifier == NARROW && ifn == IFN_LAST)
ncopies = LOOP_VINFO_VECT_FACTOR (loop_vinfo) / nunits_out;
else
ncopies = LOOP_VINFO_VECT_FACTOR (loop_vinfo) / nunits_in;
@@ -2344,6 +2393,10 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
dump_printf_loc (MSG_NOTE, vect_location, "=== vectorizable_call ==="
"\n");
vect_model_simple_cost (stmt_info, ncopies, dt, NULL, NULL);
+ if (ifn != IFN_LAST && modifier == NARROW && !slp_node)
+ add_stmt_cost (stmt_info->vinfo->target_cost_data, ncopies / 2,
+ vec_promote_demote, stmt_info, 0, vect_body);
+
return true;
}
@@ -2357,9 +2410,9 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
vec_dest = vect_create_destination_var (scalar_dest, vectype_out);
prev_stmt_info = NULL;
- switch (modifier)
+ if (modifier == NONE || ifn != IFN_LAST)
{
- case NONE:
+ tree prev_res = NULL_TREE;
for (j = 0; j < ncopies; ++j)
{
/* Build argument list for the vectorized call. */
@@ -2387,12 +2440,30 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
vec<tree> vec_oprndsk = vec_defs[k];
vargs[k] = vec_oprndsk[i];
}
- if (ifn != IFN_LAST)
- new_stmt = gimple_build_call_internal_vec (ifn, vargs);
+ if (modifier == NARROW)
+ {
+ tree half_res = make_ssa_name (vectype_in);
+ new_stmt = gimple_build_call_internal_vec (ifn, vargs);
+ gimple_call_set_lhs (new_stmt, half_res);
+ vect_finish_stmt_generation (stmt, new_stmt, gsi);
+ if ((i & 1) == 0)
+ {
+ prev_res = half_res;
+ continue;
+ }
+ new_temp = make_ssa_name (vec_dest);
+ new_stmt = gimple_build_assign (new_temp, convert_code,
+ prev_res, half_res);
+ }
else
- new_stmt = gimple_build_call_vec (fndecl, vargs);
- new_temp = make_ssa_name (vec_dest, new_stmt);
- gimple_call_set_lhs (new_stmt, new_temp);
+ {
+ if (ifn != IFN_LAST)
+ new_stmt = gimple_build_call_internal_vec (ifn, vargs);
+ else
+ new_stmt = gimple_build_call_vec (fndecl, vargs);
+ new_temp = make_ssa_name (vec_dest, new_stmt);
+ gimple_call_set_lhs (new_stmt, new_temp);
+ }
vect_finish_stmt_generation (stmt, new_stmt, gsi);
SLP_TREE_VEC_STMTS (slp_node).quick_push (new_stmt);
}
@@ -2436,6 +2507,21 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
new_temp = make_ssa_name (vec_dest);
new_stmt = gimple_build_assign (new_temp, new_var);
}
+ else if (modifier == NARROW)
+ {
+ tree half_res = make_ssa_name (vectype_in);
+ new_stmt = gimple_build_call_internal_vec (ifn, vargs);
+ gimple_call_set_lhs (new_stmt, half_res);
+ vect_finish_stmt_generation (stmt, new_stmt, gsi);
+ if ((j & 1) == 0)
+ {
+ prev_res = half_res;
+ continue;
+ }
+ new_temp = make_ssa_name (vec_dest);
+ new_stmt = gimple_build_assign (new_temp, convert_code,
+ prev_res, half_res);
+ }
else
{
if (ifn != IFN_LAST)
@@ -2447,17 +2533,16 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
}
vect_finish_stmt_generation (stmt, new_stmt, gsi);
- if (j == 0)
+ if (j == (modifier == NARROW ? 1 : 0))
STMT_VINFO_VEC_STMT (stmt_info) = *vec_stmt = new_stmt;
else
STMT_VINFO_RELATED_STMT (prev_stmt_info) = new_stmt;
prev_stmt_info = vinfo_for_stmt (new_stmt);
}
-
- break;
-
- case NARROW:
+ }
+ else if (modifier == NARROW)
+ {
for (j = 0; j < ncopies; ++j)
{
/* Build argument list for the vectorized call. */
@@ -2528,10 +2613,7 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
vargs.quick_push (vec_oprnd1);
}
- if (ifn != IFN_LAST)
- new_stmt = gimple_build_call_internal_vec (ifn, vargs);
- else
- new_stmt = gimple_build_call_vec (fndecl, vargs);
+ new_stmt = gimple_build_call_vec (fndecl, vargs);
new_temp = make_ssa_name (vec_dest, new_stmt);
gimple_call_set_lhs (new_stmt, new_temp);
vect_finish_stmt_generation (stmt, new_stmt, gsi);
@@ -2545,13 +2627,10 @@ vectorizable_call (gimple *gs, gimple_stmt_iterator *gsi, gimple **vec_stmt,
}
*vec_stmt = STMT_VINFO_VEC_STMT (stmt_info);
-
- break;
-
- case WIDEN:
- /* No current target implements this case. */
- return false;
}
+ else
+ /* No current target implements this case. */
+ return false;
vargs.release ();
@@ -6130,6 +6209,7 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
bool grouped_load = false;
bool load_lanes_p = false;
gimple *first_stmt;
+ gimple *first_stmt_for_drptr = NULL;
bool inv_p;
bool negative = false;
bool compute_in_loop = false;
@@ -6733,10 +6813,14 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
if (grouped_load)
{
first_stmt = GROUP_FIRST_ELEMENT (stmt_info);
- /* For BB vectorization we directly vectorize a subchain
+ /* For SLP vectorization we directly vectorize a subchain
without permutation. */
if (slp && ! SLP_TREE_LOAD_PERMUTATION (slp_node).exists ())
- first_stmt = SLP_TREE_SCALAR_STMTS (slp_node)[0];
+ first_stmt = SLP_TREE_SCALAR_STMTS (slp_node)[0];
+ /* For BB vectorization always use the first stmt to base
+ the data ref pointer on. */
+ if (bb_vinfo)
+ first_stmt_for_drptr = SLP_TREE_SCALAR_STMTS (slp_node)[0];
/* Check if the chain of loads is already vectorized. */
if (STMT_VINFO_VEC_STMT (vinfo_for_stmt (first_stmt))
@@ -6948,6 +7032,24 @@ vectorizable_load (gimple *stmt, gimple_stmt_iterator *gsi, gimple **vec_stmt,
(DR_REF (first_dr)), 0);
inv_p = false;
}
+ else if (first_stmt_for_drptr
+ && first_stmt != first_stmt_for_drptr)
+ {
+ dataref_ptr
+ = vect_create_data_ref_ptr (first_stmt_for_drptr, aggr_type,
+ at_loop, offset, &dummy, gsi,
+ &ptr_incr, simd_lane_access_p,
+ &inv_p, byte_offset);
+ /* Adjust the pointer by the difference to first_stmt. */
+ data_reference_p ptrdr
+ = STMT_VINFO_DATA_REF (vinfo_for_stmt (first_stmt_for_drptr));
+ tree diff = fold_convert (sizetype,
+ size_binop (MINUS_EXPR,
+ DR_INIT (first_dr),
+ DR_INIT (ptrdr)));
+ dataref_ptr = bump_vector_ptr (dataref_ptr, ptr_incr, gsi,
+ stmt, diff);
+ }
else
dataref_ptr
= vect_create_data_ref_ptr (first_stmt, aggr_type, at_loop,
diff --git a/gcc/tree.c b/gcc/tree.c
index 2387debccb2..bd5cf73b659 100644
--- a/gcc/tree.c
+++ b/gcc/tree.c
@@ -3231,8 +3231,6 @@ decl_address_ip_invariant_p (const_tree op)
not handle arithmetic; that's handled in skip_simple_arithmetic and
tree_invariant_p). */
-static bool tree_invariant_p (tree t);
-
static bool
tree_invariant_p_1 (tree t)
{
@@ -3282,7 +3280,7 @@ tree_invariant_p_1 (tree t)
/* Return true if T is function-invariant. */
-static bool
+bool
tree_invariant_p (tree t)
{
tree inner = skip_simple_arithmetic (t);
@@ -11118,7 +11116,8 @@ maybe_build_call_expr_loc (location_t loc, combined_fn fn, tree type,
if (direct_internal_fn_p (ifn))
{
tree_pair types = direct_internal_fn_types (ifn, type, argarray);
- if (!direct_internal_fn_supported_p (ifn, types))
+ if (!direct_internal_fn_supported_p (ifn, types,
+ OPTIMIZE_FOR_BOTH))
return NULL_TREE;
}
return build_call_expr_internal_loc_array (loc, ifn, type, n, argarray);
@@ -13849,7 +13848,9 @@ nonnull_arg_p (const_tree arg)
tree t, attrs, fntype;
unsigned HOST_WIDE_INT arg_num;
- gcc_assert (TREE_CODE (arg) == PARM_DECL && POINTER_TYPE_P (TREE_TYPE (arg)));
+ gcc_assert (TREE_CODE (arg) == PARM_DECL
+ && (POINTER_TYPE_P (TREE_TYPE (arg))
+ || TREE_CODE (TREE_TYPE (arg)) == OFFSET_TYPE));
/* The static chain decl is always non null. */
if (arg == cfun->static_chain_decl)
diff --git a/gcc/tree.h b/gcc/tree.h
index 0c1602ee7de..a60e9dd31cb 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -4320,6 +4320,10 @@ extern tree staticp (tree);
extern tree save_expr (tree);
+/* Return true if T is function-invariant. */
+
+extern bool tree_invariant_p (tree);
+
/* Look inside EXPR into any simple arithmetic operations. Return the
outermost non-arithmetic or non-invariant node. */