GCC Middle and Back End API Reference
tree-vect-generic.cc File Reference
#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "backend.h"
#include "rtl.h"
#include "tree.h"
#include "gimple.h"
#include "tree-pass.h"
#include "ssa.h"
#include "expmed.h"
#include "optabs-tree.h"
#include "diagnostic.h"
#include "fold-const.h"
#include "stor-layout.h"
#include "langhooks.h"
#include "tree-eh.h"
#include "gimple-iterator.h"
#include "gimplify-me.h"
#include "gimplify.h"
#include "tree-cfg.h"
#include "tree-vector-builder.h"
#include "vec-perm-indices.h"
#include "insn-config.h"
#include "tree-ssa-dce.h"
#include "gimple-fold.h"
#include "gimple-match.h"
#include "recog.h"
#include "optabs-libfuncs.h"
#include "cfgloop.h"
#include "tree-vectorizer.h"
#include "gt-tree-vect-generic.h"
Include dependency graph for tree-vect-generic.cc:

Macros

#define INCLUDE_MEMORY
 

Typedefs

typedef tree(* elem_op_func) (gimple_stmt_iterator *, tree, tree, tree, tree, tree, enum tree_code, tree)
 

Functions

static tree gimplify_build3 (gimple_stmt_iterator *gsi, enum tree_code code, tree type, tree a, tree b, tree c)
 
static tree gimplify_build2 (gimple_stmt_iterator *gsi, enum tree_code code, tree type, tree a, tree b)
 
static tree gimplify_build1 (gimple_stmt_iterator *gsi, enum tree_code code, tree type, tree a)
 
static void expand_vector_operations_1 (gimple_stmt_iterator *, bitmap)
 
static unsigned int nunits_for_known_piecewise_op (const_tree type)
 
static bool subparts_gt (tree type1, tree type2)
 
static tree build_word_mode_vector_type (int nunits)
 
tree tree_vec_extract (gimple_stmt_iterator *gsi, tree type, tree t, tree bitsize, tree bitpos)
 
static tree do_unop (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree do_binop (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree do_compare (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree do_plus_minus (gimple_stmt_iterator *gsi, tree word_type, tree a, tree b, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree do_negate (gimple_stmt_iterator *gsi, tree word_type, tree b, tree unused, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree expand_vector_piecewise (gimple_stmt_iterator *gsi, elem_op_func f, tree type, tree inner_type, tree a, tree b, enum tree_code code, bool parallel_p, tree ret_type=NULL_TREE)
 
static tree expand_vector_parallel (gimple_stmt_iterator *gsi, elem_op_func f, tree type, tree a, tree b, enum tree_code code)
 
static tree expand_vector_addition (gimple_stmt_iterator *gsi, elem_op_func f, elem_op_func f_parallel, tree type, tree a, tree b, enum tree_code code)
 
static bool expand_vector_condition (gimple_stmt_iterator *gsi, bitmap dce_ssa_names)
 
static tree expand_vector_comparison (gimple_stmt_iterator *gsi, tree type, tree op0, tree op1, enum tree_code code, bitmap dce_ssa_names)
 
static tree add_rshift (gimple_stmt_iterator *gsi, tree type, tree op0, int *shiftcnts)
 
static tree expand_vector_divmod (gimple_stmt_iterator *gsi, tree type, tree op0, tree op1, enum tree_code code)
 
static tree expand_vector_operation (gimple_stmt_iterator *gsi, tree type, tree compute_type, gassign *assign, enum tree_code code, bitmap dce_ssa_names)
 
static void optimize_vector_constructor (gimple_stmt_iterator *gsi)
 
static tree type_for_widest_vector_mode (tree original_vector_type, optab op)
 
static tree vector_element (gimple_stmt_iterator *gsi, tree vect, tree idx, tree *ptmpvec)
 
static void lower_vec_perm (gimple_stmt_iterator *gsi)
 
static tree ssa_uniform_vector_p (tree op)
 
static tree get_compute_type (enum tree_code code, optab op, tree type)
 
static tree do_cond (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree b, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static void expand_vector_scalar_condition (gimple_stmt_iterator *gsi)
 
static tree do_vec_conversion (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree decl, tree bitpos, tree bitsize, enum tree_code code, tree type)
 
static tree do_vec_narrow_conversion (gimple_stmt_iterator *gsi, tree inner_type, tree a, tree, tree bitpos, tree, enum tree_code code, tree type)
 
static void expand_vector_conversion (gimple_stmt_iterator *gsi)
 
static unsigned int expand_vector_operations (void)
 
gimple_opt_passmake_pass_lower_vector (gcc::context *ctxt)
 
gimple_opt_passmake_pass_lower_vector_ssa (gcc::context *ctxt)
 

Variables

static tree vector_inner_type
 
static tree vector_last_type
 
static int vector_last_nunits
 

Macro Definition Documentation

◆ INCLUDE_MEMORY

#define INCLUDE_MEMORY
Lower vector operations to scalar operations.
   Copyright (C) 2004-2024 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/>.   

Typedef Documentation

◆ elem_op_func

typedef tree(* elem_op_func) (gimple_stmt_iterator *, tree, tree, tree, tree, tree, enum tree_code, tree)

Function Documentation

◆ add_rshift()

static tree add_rshift ( gimple_stmt_iterator * gsi,
tree type,
tree op0,
int * shiftcnts )
static
Helper function of expand_vector_divmod.  Gimplify a RSHIFT_EXPR in type
of OP0 with shift counts in SHIFTCNTS array and return the temporary holding
the result if successful, otherwise return NULL_TREE.   

References build_int_cst(), gimplify_build2(), i, NULL_TREE, nunits_for_known_piecewise_op(), optab_for_tree_code(), optab_handler(), optab_scalar, optab_vector, TREE_TYPE, TYPE_MODE, and unknown_optab.

Referenced by expand_vector_divmod().

◆ build_word_mode_vector_type()

static tree build_word_mode_vector_type ( int nunits)
static
Return a suitable vector types made of SUBPARTS units each of mode
"word_mode" (the global variable).   

References build_vector_type(), gcc_assert, if(), TREE_CODE, lang_hooks_for_types::type_for_mode, lang_hooks::types, vector_inner_type, vector_last_nunits, vector_last_type, and word_mode.

Referenced by expand_vector_parallel().

◆ do_binop()

static tree do_binop ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree b,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static

◆ do_compare()

static tree do_compare ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree b,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static
Construct expression (A[BITPOS] code B[BITPOS]) ? -1 : 0

INNER_TYPE is the type of A and B elements

returned expression is of signed integer type with the
size equal to the size of INNER_TYPE.   

References a, b, boolean_type_node, build2(), build_all_ones_cst(), build_zero_cst(), gimplify_build3(), TREE_TYPE, and tree_vec_extract().

Referenced by expand_vector_comparison().

◆ do_cond()

static tree do_cond ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree b,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static

◆ do_negate()

static tree do_negate ( gimple_stmt_iterator * gsi,
tree word_type,
tree b,
tree unused,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static

◆ do_plus_minus()

static tree do_plus_minus ( gimple_stmt_iterator * gsi,
tree word_type,
tree a,
tree b,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static
Expand vector addition to scalars.  This does bit twiddling
in order to increase parallelism:

a + b = (((int) a & 0x7f7f7f7f) + ((int) b & 0x7f7f7f7f)) ^
        (a ^ b) & 0x80808080

a - b =  (((int) a | 0x80808080) - ((int) b & 0x7f7f7f7f)) ^
         (a ^ ~b) & 0x80808080

-b = (0x80808080 - ((int) b & 0x7f7f7f7f)) ^ (~b & 0x80808080)

This optimization should be done only if 4 vector items or more
fit into a word.   

References a, b, build_replicated_int_cst(), GET_MODE_MASK, gimplify_build1(), gimplify_build2(), TREE_TYPE, tree_vec_extract(), TYPE_MODE, and vector_element_bits().

Referenced by expand_vector_operation().

◆ do_unop()

static tree do_unop ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree b,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static

◆ do_vec_conversion()

static tree do_vec_conversion ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree decl,
tree bitpos,
tree bitsize,
enum tree_code code,
tree type )
static
Callback for expand_vector_piecewise to do VEC_CONVERT ifn call
lowering.  If INNER_TYPE is not a vector type, this is a scalar
fallback.   

References a, build_vector_type(), g, gimple_build_call(), gimple_call_set_lhs(), gimplify_build1(), gsi_insert_before(), GSI_SAME_STMT, make_ssa_name(), TREE_TYPE, tree_vec_extract(), TYPE_VECTOR_SUBPARTS(), and VECTOR_TYPE_P.

Referenced by expand_vector_conversion().

◆ do_vec_narrow_conversion()

static tree do_vec_narrow_conversion ( gimple_stmt_iterator * gsi,
tree inner_type,
tree a,
tree ,
tree bitpos,
tree ,
enum tree_code code,
tree type )
static

◆ expand_vector_addition()

static tree expand_vector_addition ( gimple_stmt_iterator * gsi,
elem_op_func f,
elem_op_func f_parallel,
tree type,
tree a,
tree b,
enum tree_code code )
static
Expand a vector operation to scalars; for integer types we can use
special bit twiddling tricks to do the sums a word at a time, using
function F_PARALLEL instead of F.  These tricks are done only if
they can process at least four items, that is, only if the vector
holds at least four items and if a word can hold four items.   

References a, b, BITS_PER_WORD, expand_vector_parallel(), expand_vector_piecewise(), INTEGRAL_TYPE_P, nunits_for_known_piecewise_op(), TREE_TYPE, and vector_element_bits().

Referenced by expand_vector_operation().

◆ expand_vector_comparison()

◆ expand_vector_condition()

◆ expand_vector_conversion()

◆ expand_vector_divmod()

◆ expand_vector_operation()

◆ expand_vector_operations()

static unsigned int expand_vector_operations ( void )
static
Use this to lower vector operations introduced by the vectorizer,
if it may need the bit-twiddling tricks implemented in this file.   

References boolean_false_node, cfg_changed, cfun, expand_vector_operations_1(), fold_loop_internal_call(), FOR_EACH_BB_FN, gimple_call_internal_p(), gimple_purge_dead_eh_edges(), gsi_end_p(), gsi_next(), gsi_start_bb(), gsi_stmt(), maybe_clean_eh_stmt(), simple_dce_from_worklist(), and TODO_cleanup_cfg.

◆ expand_vector_operations_1()

◆ expand_vector_parallel()

◆ expand_vector_piecewise()

◆ expand_vector_scalar_condition()

◆ get_compute_type()

static tree get_compute_type ( enum tree_code code,
optab op,
tree type )
static

◆ gimplify_build1()

static tree gimplify_build1 ( gimple_stmt_iterator * gsi,
enum tree_code code,
tree type,
tree a )
static

◆ gimplify_build2()

static tree gimplify_build2 ( gimple_stmt_iterator * gsi,
enum tree_code code,
tree type,
tree a,
tree b )
static
Build a binary operation and gimplify it.  Emit code before GSI.
Return the gimple_val holding the result.   

References a, b, gimple_build(), gimple_location(), GSI_SAME_STMT, and gsi_stmt().

Referenced by add_rshift(), do_binop(), do_negate(), do_plus_minus(), do_vec_narrow_conversion(), expand_vector_comparison(), expand_vector_condition(), expand_vector_conversion(), expand_vector_divmod(), and expand_vector_operations_1().

◆ gimplify_build3()

static tree gimplify_build3 ( gimple_stmt_iterator * gsi,
enum tree_code code,
tree type,
tree a,
tree b,
tree c )
static
Build a ternary operation and gimplify it.  Emit code before GSI.
Return the gimple_val holding the result.   

References a, b, gimple_build(), gimple_location(), GSI_SAME_STMT, and gsi_stmt().

Referenced by do_compare(), do_cond(), expand_vector_comparison(), and expand_vector_condition().

◆ lower_vec_perm()

static void lower_vec_perm ( gimple_stmt_iterator * gsi)
static
Check if VEC_PERM_EXPR within the given setting is supported
by hardware, or lower it piecewise.

When VEC_PERM_EXPR has the same first and second operands:
VEC_PERM_EXPR <v0, v0, mask> the lowered version would be
{v0[mask[0]], v0[mask[1]], ...}
MASK and V0 must have the same number of elements.

Otherwise VEC_PERM_EXPR <v0, v1, mask> is lowered to
{mask[0] < len(v0) ? v0[mask[0]] : v1[mask[0]], ...}
V0 and V1 must have the same type.  MASK, V0, V1 must have the
same number of arguments.   

References as_a(), boolean_type_node, build_constructor(), build_int_cst(), build_vector_from_ctor(), build_zero_cst(), can_vec_perm_const_p(), can_vec_perm_var_p(), CONSTANT_CLASS_P, CONSTRUCTOR_APPEND_ELT, fold_build2, fold_build3, force_gimple_operand_gsi(), gimple_assign_lhs(), gimple_assign_rhs1(), gimple_assign_rhs2(), gimple_assign_rhs3(), gimple_assign_rhs_code(), gimple_assign_set_rhs3(), gimple_assign_set_rhs_from_tree(), gimple_location(), GSI_SAME_STMT, gsi_stmt(), i, initializer_zerop(), is_gimple_assign(), known_eq, known_lt, maybe_ge, NULL_TREE, operand_equal_p(), optab_handler(), si, size_int, SSA_NAME_DEF_STMT, TREE_CODE, tree_fits_uhwi_p(), TREE_INT_CST_LOW, tree_to_vec_perm_builder(), TREE_TYPE, TYPE_MODE, TYPE_VECTOR_SUBPARTS(), update_stmt(), vec_alloc(), vector_element(), warning_at(), and warning_suppressed_p().

Referenced by expand_vector_operations_1().

◆ make_pass_lower_vector()

gimple_opt_pass * make_pass_lower_vector ( gcc::context * ctxt)

◆ make_pass_lower_vector_ssa()

gimple_opt_pass * make_pass_lower_vector_ssa ( gcc::context * ctxt)

◆ nunits_for_known_piecewise_op()

static unsigned int nunits_for_known_piecewise_op ( const_tree type)
static
Return the number of elements in a vector type TYPE that we have
already decided needs to be expanded piecewise.  We don't support
this kind of expansion for variable-length vectors, since we should
always check for target support before introducing uses of those.   

References poly_int< N, C >::to_constant(), and TYPE_VECTOR_SUBPARTS().

Referenced by add_rshift(), expand_vector_addition(), expand_vector_comparison(), expand_vector_condition(), expand_vector_conversion(), expand_vector_divmod(), expand_vector_piecewise(), and vector_element().

◆ optimize_vector_constructor()

static void optimize_vector_constructor ( gimple_stmt_iterator * gsi)
static

◆ ssa_uniform_vector_p()

static tree ssa_uniform_vector_p ( tree op)
static
If OP is a uniform vector return the element it is a splat from.   

References gimple_assign_rhs1(), gimple_assign_single_p(), NULL_TREE, SSA_NAME_DEF_STMT, TREE_CODE, and uniform_vector_p().

Referenced by expand_vector_operations_1().

◆ subparts_gt()

static bool subparts_gt ( tree type1,
tree type2 )
inlinestatic
Return true if TYPE1 has more elements than TYPE2, where either
type may be a vector or a scalar.   

References known_gt, TYPE_VECTOR_SUBPARTS(), and VECTOR_TYPE_P.

Referenced by expand_vector_operations_1().

◆ tree_vec_extract()

◆ type_for_widest_vector_mode()

static tree type_for_widest_vector_mode ( tree original_vector_type,
optab op )
static
Return a type for the widest vector mode with the same element type as
type ORIGINAL_VECTOR_TYPE, with at most the same number of elements as type
ORIGINAL_VECTOR_TYPE and that is supported by the target for an operation
with optab OP, or return NULL_TREE if none is found.   

References build_vector_type_for_mode(), FOR_EACH_MODE_FROM, gcc_assert, GET_MODE_INNER, GET_MODE_NUNITS(), known_le, maybe_gt, NULL_TREE, optab_handler(), SCALAR_ACCUM_MODE_P, SCALAR_FLOAT_MODE_P, SCALAR_FRACT_MODE_P, SCALAR_UACCUM_MODE_P, SCALAR_UFRACT_MODE_P, TREE_TYPE, TYPE_MODE, TYPE_VECTOR_SUBPARTS(), and VECTOR_TYPE_P.

Referenced by expand_vector_conversion(), and get_compute_type().

◆ vector_element()

static tree vector_element ( gimple_stmt_iterator * gsi,
tree vect,
tree idx,
tree * ptmpvec )
static
Build a reference to the element of the vector VECT.  Function
returns either the element itself, either BIT_FIELD_REF, or an
ARRAY_REF expression.

GSI is required to insert temporary variables while building a
refernece to the element of the vector VECT.

PTMPVEC is a pointer to the temporary variable for caching
purposes.  In case when PTMPVEC is NULL new temporary variable
will be created.   

References bitsize_int, bitsizetype, build1(), build4(), build_array_type_nelts(), build_int_cst(), build_zero_cst(), CONSTRUCTOR_ELT, CONSTRUCTOR_NELTS, create_tmp_var, fold_build2, fold_build3, gimple_assign_rhs1(), gimple_assign_rhs_code(), gimple_build_assign(), gsi_insert_before(), GSI_SAME_STMT, is_gimple_assign(), NULL_TREE, nunits_for_known_piecewise_op(), SSA_NAME_DEF_STMT, TREE_ADDRESSABLE, TREE_CODE, tree_fits_uhwi_p(), TREE_INT_CST_LOW, TREE_TYPE, VECTOR_CST_ELT, and vector_element_bits_tree().

Referenced by lower_vec_perm().

Variable Documentation

◆ vector_inner_type

tree vector_inner_type
static

◆ vector_last_nunits

int vector_last_nunits
static

◆ vector_last_type

tree vector_last_type
static