GCC Middle and Back End API Reference
|
#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "backend.h"
#include "target.h"
#include "tree.h"
#include "langhooks.h"
#include "gimple.h"
#include "tree-pass.h"
#include "cgraph.h"
#include "fold-const.h"
#include "gimplify.h"
#include "gimple-iterator.h"
#include "gimple-walk.h"
#include "gomp-constants.h"
#include "omp-general.h"
#include "diagnostic-core.h"
Data Structures | |
struct | adjust_nested_loop_clauses_wi_info |
class | control_flow_regions |
Functions | |
static gimple * | top_level_omp_for_in_stmt (gimple *stmt) |
static tree | adjust_region_code_walk_stmt_fn (gimple_stmt_iterator *gsi_p, bool *handled_ops_p, struct walk_stmt_info *wi) |
static void | adjust_region_code (gimple_seq gs, int *region_code) |
static tree | visit_loops_in_gang_single_region (gimple_stmt_iterator *gsi_p, bool *handled_ops_p, struct walk_stmt_info *) |
static void | make_loops_gang_single (gimple_seq gs) |
static gimple * | make_region_seq (location_t loc, gimple_seq stmts, tree num_gangs_clause, tree num_workers_clause, tree vector_length_clause, tree clauses) |
static tree | add_parent_or_loop_num_clause (tree parent_clause, tree loop_clause, omp_clause_code clause_code, tree clauses) |
static tree | adjust_nested_loop_clauses (gimple_stmt_iterator *gsi_p, bool *, struct walk_stmt_info *wi) |
static tree | transform_kernels_loop_clauses (gimple *omp_for, tree num_gangs_clause, tree num_workers_clause, tree vector_length_clause, tree clauses) |
static gimple * | make_region_loop_nest (gimple *omp_for, gimple_seq stmts, tree num_gangs_clause, tree num_workers_clause, tree vector_length_clause, tree clauses) |
static tree | flatten_binds (gbind *bind, bool include_toplevel_vars=false) |
static gimple * | make_data_region_try_statement (location_t loc, gimple *body) |
static gimple * | maybe_build_inner_data_region (location_t loc, gimple *body, tree inner_bind_vars, gimple *inner_cleanup) |
static void | add_wait (location_t loc, gimple_seq *region_body) |
static void | add_async_clauses_and_wait (location_t loc, gimple_seq *region_body) |
static gimple * | decompose_kernels_region_body (gimple *kernels_region, tree kernels_clauses) |
static gimple * | omp_oacc_kernels_decompose_1 (gimple *kernels_stmt) |
static tree | omp_oacc_kernels_decompose_callback_stmt (gimple_stmt_iterator *gsi_p, bool *handled_ops_p, struct walk_stmt_info *) |
static unsigned int | omp_oacc_kernels_decompose (void) |
gimple_opt_pass * | make_pass_omp_oacc_kernels_decompose (gcc::context *ctxt) |
|
static |
Helper function of decompose_kernels_region_body. The statements in REGION_BODY are expected to be decomposed parts; add an 'async' clause to each. Also add a 'wait' directive at the end of the sequence.
References add_wait(), as_a(), build_int_cst(), build_omp_clause(), gimple_omp_target_clauses(), gimple_omp_target_set_clauses(), gsi_end_p(), gsi_next(), gsi_start(), gsi_stmt(), integer_type_node, OMP_CLAUSE_ASYNC, OMP_CLAUSE_CHAIN, and OMP_CLAUSE_OPERAND.
Referenced by decompose_kernels_region_body().
|
static |
Helper function for make_region_loop_nest. Adds a 'num_gangs' ('num_workers', 'vector_length') clause to the given CLAUSES, either the one from the parent compute construct (PARENT_CLAUSE) or a new one based on the loop's own LOOP_CLAUSE ('gang (num: N)' or similar for 'worker' or 'vector' clauses) with the given CLAUSE_CODE. Does nothing if neither PARENT_CLAUSE nor LOOP_CLAUSE exist. Returns the new clauses.
References build_omp_clause(), NULL, OMP_CLAUSE_CHAIN, OMP_CLAUSE_LOCATION, OMP_CLAUSE_OPERAND, and unshare_expr().
Referenced by make_region_loop_nest(), and transform_kernels_loop_clauses().
|
static |
References build_int_cst(), builtin_decl_explicit(), gimple_build_call(), gimple_seq_add_stmt(), gimple_set_location(), integer_type_node, and integer_zero_node.
Referenced by add_async_clauses_and_wait(), and decompose_kernels_region_body().
|
static |
References build_omp_clause(), cst_and_fits_in_hwi(), error_at(), gimple_location(), gimple_omp_for_clauses(), gimple_omp_for_set_clauses(), gsi_stmt(), inform(), int_cst_value(), adjust_nested_loop_clauses_wi_info::loop_gang_clause_ptr, adjust_nested_loop_clauses_wi_info::loop_vector_clause_ptr, adjust_nested_loop_clauses_wi_info::loop_worker_clause_ptr, NULL, OMP_CLAUSE_AUTO, OMP_CLAUSE_CHAIN, OMP_CLAUSE_CODE, omp_clause_code_name, OMP_CLAUSE_GANG, OMP_CLAUSE_INDEPENDENT, OMP_CLAUSE_LOCATION, OMP_CLAUSE_OPERAND, OMP_CLAUSE_SEQ, OMP_CLAUSE_VECTOR, OMP_CLAUSE_WORKER, and unshare_expr().
Referenced by transform_kernels_loop_clauses().
|
static |
Adjust the REGION_CODE for the region in GS.
References adjust_region_code_walk_stmt_fn(), NULL, and walk_gimple_seq().
Referenced by make_region_loop_nest(), and make_region_seq().
|
static |
Helper for adjust_region_code: evaluate the statement at GSI_P.
References gcc_unreachable, GF_OMP_TARGET_KIND_OACC_KERNELS, gimple_omp_for_clauses(), gsi_stmt(), integer_zero_node, NULL, OMP_CLAUSE_INDEPENDENT, OMP_CLAUSE_SEQ, and omp_find_clause().
Referenced by adjust_region_code().
|
static |
Decompose the body of the KERNELS_REGION, which was originally annotated with the KERNELS_CLAUSES, into a series of compute constructs.
References add_async_clauses_and_wait(), add_wait(), as_a(), build_omp_clause(), DECL_ARTIFICIAL, DECL_SIZE_UNIT, dump_enabled_p(), dump_printf_loc(), flatten_binds(), gcc_checking_assert, gcc_unreachable, gimple_assign_lhs(), gimple_bind_body(), gimple_bind_vars(), gimple_build_bind(), gimple_build_nop(), gimple_code_name, gimple_location(), gimple_omp_body(), gimple_seq_add_stmt(), gimple_seq_singleton_p(), gimple_set_location(), gimple_try_cleanup(), gimple_try_eval(), GSI_CONTINUE_LINKING, gsi_end_p(), gsi_insert_seq_before(), gsi_next(), gsi_remove(), gsi_start(), gsi_stmt(), control_flow_regions::is_unconditional_oacc_for_loop(), make_node(), make_region_loop_nest(), make_region_seq(), maybe_build_inner_data_region(), MSG_MISSED_OPTIMIZATION, NULL, OMP_CLAUSE_ASYNC, OMP_CLAUSE_CHAIN, OMP_CLAUSE_CODE, OMP_CLAUSE_DECL, OMP_CLAUSE_MAP, OMP_CLAUSE_NUM_GANGS, OMP_CLAUSE_NUM_WORKERS, OMP_CLAUSE_SET_MAP_KIND, OMP_CLAUSE_SIZE, OMP_CLAUSE_VECTOR_LENGTH, sorry_at(), top_level_omp_for_in_stmt(), TREE_CHAIN, and TREE_CODE.
Referenced by omp_oacc_kernels_decompose_1().
Eliminate any binds directly inside BIND by adding their statements to BIND (i.e., modifying it in place), excluding binds that hold only an OMP_FOR loop and associated setup/cleanup code. Recurse into binds but not other statements. Return a chain of the local variables of eliminated binds, i.e., the local variables found in nested binds. If INCLUDE_TOPLEVEL_VARS is true, this also includes the variables belonging to BIND itself.
References as_a(), flatten_binds(), gcc_assert, gimple_bind_body(), gimple_bind_set_body(), gimple_bind_vars(), gimple_seq_add_seq(), gimple_seq_add_stmt(), gsi_end_p(), gsi_next(), gsi_start(), gsi_stmt(), NULL, top_level_omp_for_in_stmt(), and TREE_CHAIN.
Referenced by decompose_kernels_region_body(), and flatten_binds().
Helper function for places where we construct data regions. Wraps the BODY inside a try-finally construct at LOC that calls __builtin_GOACC_data_end in its cleanup block. Returns this try statement.
References builtin_decl_explicit(), gimple_build_call(), gimple_build_try(), gimple_seq_add_stmt(), gimple_set_location(), GIMPLE_TRY_FINALLY, and NULL.
Referenced by maybe_build_inner_data_region(), and omp_oacc_kernels_decompose_1().
|
static |
Visit all nested OpenACC loops in the sequence indicated by GS. This statement is expected to be inside a gang-single region. Issue a warning for any loops inside it that have gang clauses and remove the clauses.
References NULL, visit_loops_in_gang_single_region(), and walk_gimple_seq().
Referenced by make_region_seq().
gimple_opt_pass * make_pass_omp_oacc_kernels_decompose | ( | gcc::context * | ctxt | ) |
|
static |
Construct a possibly gang-parallel compute construct containing the STMT, which must be identical to, or a bind containing, the loop OMP_FOR. The NUM_GANGS_CLAUSE, NUM_WORKERS_CLAUSE, and VECTOR_LENGTH_CLAUSE are optional clauses from the original kernels region and must not be contained in the other CLAUSES. The newly created compute construct is annotated with the optional NUM_GANGS_CLAUSE as well as the other CLAUSES. If there is no NUM_GANGS_CLAUSE but the loop has a 'gang (num: N)' clause, that is converted to a 'num_gangs (N)' clause on the new compute construct, and similarly for 'worker' and 'vector' clauses. The outermost loop gets an 'auto' clause unless there already is an 'seq'/'independent'/'auto' clause. Nested loops inside OMP_FOR are treated similarly by the adjust_nested_loop_clauses function.
References add_parent_or_loop_num_clause(), adjust_region_code(), dump_enabled_p(), dump_printf_loc(), gcc_unreachable, GF_OMP_TARGET_KIND_OACC_KERNELS, GF_OMP_TARGET_KIND_OACC_PARALLEL_KERNELS_PARALLELIZED, gimple_build_bind(), gimple_build_omp_target(), gimple_location(), gimple_set_location(), make_node(), MSG_NOTE, NULL, OMP_CLAUSE_NUM_GANGS, OMP_CLAUSE_NUM_WORKERS, OMP_CLAUSE_VECTOR_LENGTH, transform_kernels_loop_clauses(), and unshare_expr().
Referenced by decompose_kernels_region_body().
|
static |
Construct a "gang-single" compute construct at LOC containing the STMTS. Annotate with CLAUSES, which must not contain a 'num_gangs' clause, and an additional 'num_gangs (1)' clause to force "gang-single" execution.
References adjust_region_code(), build_omp_clause(), dump_enabled_p(), dump_printf_loc(), gcc_unreachable, GF_OMP_TARGET_KIND_OACC_KERNELS, GF_OMP_TARGET_KIND_OACC_PARALLEL_KERNELS_GANG_SINGLE, gimple_build_bind(), gimple_build_omp_target(), gimple_omp_set_body(), gimple_seq_first(), gimple_set_location(), integer_one_node, make_loops_gang_single(), make_node(), MSG_NOTE, NULL, OMP_CLAUSE_CHAIN, OMP_CLAUSE_NUM_GANGS, OMP_CLAUSE_OPERAND, and unshare_expr().
Referenced by decompose_kernels_region_body().
|
static |
If INNER_BIND_VARS holds variables, build an OpenACC data region with location LOC containing BODY and having 'create (var)' clauses for each variable (as a side effect, such variables also get TREE_ADDRESSABLE set). If INNER_CLEANUP is present, add a try-finally statement with this cleanup code in the finally block. Return the new data region, or the original BODY if no data region was needed.
References build_omp_clause(), current_function_decl, DECL_ARTIFICIAL, DECL_SIZE_UNIT, lang_hooks::decls, dump_enabled_p(), dump_printf_loc(), dump_user_location_t::from_location_t(), gcc_assert, lang_hooks_for_decls::get_generic_function_decl, GF_OMP_TARGET_KIND_OACC_DATA_KERNELS, gimple_build_bind(), gimple_build_omp_target(), gimple_build_try(), gimple_omp_set_body(), gimple_set_location(), GIMPLE_TRY_FINALLY, make_data_region_try_statement(), make_node(), MSG_NOTE, NULL, OMP_CLAUSE_CHAIN, OMP_CLAUSE_DECL, OMP_CLAUSE_MAP, OMP_CLAUSE_MAP_DECL_MAKE_ADDRESSABLE, OMP_CLAUSE_SET_MAP_KIND, OMP_CLAUSE_SIZE, TREE_ADDRESSABLE, TREE_CHAIN, and TREE_CODE.
Referenced by decompose_kernels_region_body().
|
static |
Decompose one OpenACC 'kernels' construct into an OpenACC 'data' construct containing the original OpenACC 'kernels' construct's region cut up into a sequence of compute constructs.
References build_omp_clause(), DECL_ARTIFICIAL, DECL_P, decompose_kernels_region_body(), dump_enabled_p(), dump_printf_loc(), dump_user_location_t::from_location_t(), gcc_checking_assert, GF_OMP_TARGET_KIND_OACC_DATA_KERNELS, GF_OMP_TARGET_KIND_OACC_KERNELS, gimple_build_omp_target(), gimple_location(), gimple_omp_set_body(), gimple_omp_target_clauses(), gimple_omp_target_kind(), gimple_set_location(), integer_zerop(), make_data_region_try_statement(), MSG_NOTE, nreverse(), NULL, OMP_CLAUSE_CHAIN, OMP_CLAUSE_CODE, OMP_CLAUSE_DECL, OMP_CLAUSE_IF, OMP_CLAUSE_LOCATION, OMP_CLAUSE_MAP, OMP_CLAUSE_MAP_DECL_MAKE_ADDRESSABLE, OMP_CLAUSE_MAP_KIND, OMP_CLAUSE_SELF, OMP_CLAUSE_SET_MAP_KIND, OMP_CLAUSE_SIZE, TREE_ADDRESSABLE, unshare_expr(), and user_omp_clause_code_name().
Referenced by omp_oacc_kernels_decompose_callback_stmt().
|
static |
Decompose OpenACC 'kernels' constructs in the current function.
References GF_OMP_TARGET_KIND_OACC_KERNELS, gimple_omp_target_kind(), gsi_replace(), gsi_stmt(), NULL, and omp_oacc_kernels_decompose_1().
Referenced by omp_oacc_kernels_decompose().
Decompose OpenACC 'kernels' constructs into parts, a sequence of compute constructs Copyright (C) 2020-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/>.
This preprocessing pass is run immediately before lower_omp. It decomposes OpenACC 'kernels' constructs into parts, a sequence of compute constructs. The translation is as follows: - The entire 'kernels' region is turned into a 'data' region with clauses taken from the 'kernels' region. New 'create' clauses are added for all variables declared at the top level in the kernels region. - Any loop nests annotated with an OpenACC 'loop' directive are wrapped in a new compute construct. - 'loop' directives without an explicit 'independent' or 'seq' clause get an 'auto' clause added; other clauses are preserved on the loop or moved to the new surrounding compute construct, as applicable. - Any sequences of other code (non-loops, non-OpenACC 'loop's) are wrapped in new "gang-single" compute construct: 'worker'/'vector' parallelism is preserved, but 'num_gangs (1)' is enforced. - Both points above only apply at the topmost level in the region, that is, the transformation does not introduce new compute constructs inside nested statement bodies. In particular, this means that a gang-parallelizable loop inside an 'if' statement is made "gang-single". - In order to make the host wait only once for the whole region instead of once per device kernel launch, the new compute constructs are annotated 'async'. Unless the original 'kernels' construct already was marked 'async', the entire region ends with a 'wait' directive. If the original 'kernels' construct was marked 'async', the synthesized 'async' clauses use the original 'kernels' construct's 'async' argument (possibly implicit).
Helper function for decompose_kernels_region_body. If STMT contains a "top-level" OMP_FOR statement, returns a pointer to that statement; returns NULL otherwise. A "top-level" OMP_FOR statement is one that is possibly accompanied by small snippets of setup code. Specifically, this function accepts an OMP_FOR possibly wrapped in a singleton bind and a singleton try statement to allow for a local loop variable, but not an OMP_FOR statement nested in any other constructs. Alternatively, it accepts a non-singleton bind containing only assignments and then an OMP_FOR statement at the very end. The former style can be generated by the C frontend, the latter by the Fortran frontend.
References as_a(), gimple_bind_body(), gimple_seq_first_stmt(), gimple_seq_singleton_p(), gimple_try_eval(), gsi_end_p(), gsi_next(), gsi_one_before_end_p(), gsi_start(), gsi_stmt(), and NULL.
Referenced by control_flow_regions::compute_regions(), decompose_kernels_region_body(), and flatten_binds().
|
static |
Helper for make_region_loop_nest. Transform OpenACC 'kernels'/'loop' construct clauses into OpenACC 'parallel'/'loop' construct ones.
References add_parent_or_loop_num_clause(), adjust_nested_loop_clauses(), build_omp_clause(), error_at(), gimple_location(), gimple_omp_body(), gimple_omp_for_clauses(), gimple_omp_for_set_clauses(), inform(), adjust_nested_loop_clauses_wi_info::loop_gang_clause_ptr, adjust_nested_loop_clauses_wi_info::loop_vector_clause_ptr, adjust_nested_loop_clauses_wi_info::loop_worker_clause_ptr, NULL, OMP_CLAUSE_AUTO, OMP_CLAUSE_CHAIN, OMP_CLAUSE_CODE, omp_clause_code_name, OMP_CLAUSE_GANG, OMP_CLAUSE_INDEPENDENT, OMP_CLAUSE_LOCATION, OMP_CLAUSE_NUM_GANGS, OMP_CLAUSE_NUM_WORKERS, OMP_CLAUSE_OPERAND, OMP_CLAUSE_SEQ, OMP_CLAUSE_VECTOR, OMP_CLAUSE_VECTOR_LENGTH, OMP_CLAUSE_WORKER, unshare_expr(), and walk_gimple_seq().
Referenced by make_region_loop_nest().
|
static |
Helper function for make_loops_gang_single for walking the tree. If the statement indicated by GSI_P is an OpenACC for loop with a gang clause, issue a warning and remove the clause.
References gcc_unreachable, gimple_location(), gimple_omp_for_clauses(), gimple_omp_for_set_clauses(), gsi_stmt(), internal_error(), NULL, OMP_CLAUSE_CHAIN, OMP_CLAUSE_CODE, OMP_CLAUSE_GANG, sorry(), walk_stmt_info::stmt, and warning_at().
Referenced by make_loops_gang_single().