This patch changes the semantics of target_version and target_clones attributes to match the behavior described in the Arm C Language extension.
The changes to behavior are: - The scope and signature of an FMV function set is now that of the default version. - The FMV resolver is now created at the locations of the default version implementation. Previously this was at the first call to an FMV function. - When a TU has a single annotated function version, it gets mangled. - This includes a lone annotated default version. This only affects targets with TARRGET_HAS_FMV_TARGET_ATTRIBUTE set to false. Currently that is aarch64 and riscv. This is achieved by: - Skipping the existing FMV dispatching code at C++ gimplification and instead making use of the target_clones dispatching code in multiple_targets.cc. (This fixes PR target/118313 for aarch64 and riscv). - Splitting target_clones pass in two, an early and late pass, where the early pass handles cases where multiple declarations are used to define a version, and the late pass handling target semantics targets, and cases where a FMV set is defined by a single target_clones decl. - Changing the logic in add_candidates and resolve_address of overloaded function to prevent resolution of any version except a default version. (thus making the default version determine scope and signature of the versioned function set). - Adding logic for dispatching a lone annotated default version in multiple_targets.cc - As as annotated default version gets mangled an alias is created from the dispatched symbol to the default version as no ifunc resolution is required in this case. (ie, an alias from `_Z3foov_` to `_Z3foov.default`) - Adding logic to symbol_table::remove_unreachable_nodes and analyze_functions that a reference to the default function version also implies a possible reference to the other versions (so they shouldnt be deleted and do need to be analyzed). gcc/ChangeLog: PR target/118313 * cgraphunit.cc (analyze_functions): Add logic for target version dependencies. * ipa.cc (symbol_table::remove_unreachable_nodes): Ditto. * multiple_target.cc (create_dispatcher_calls): Change to support target version semantics. (ipa_target_clone): Change to dispatch all function sets in target_version semantics, and to have early and late pass. (is_simple_target_clones_case): New function. * config/aarch64/aarch64.cc: (aarch64_get_function_versions_dispatcher): Refactor with the assumption that the DECL node will be default. * config/riscv/riscv.cc: (riscv_get_function_versions_dispatcher): Refactor with the assumption that the DECL node will be default. * passes.def: Split target_clones pass into early and late version. gcc/cp/ChangeLog: PR target/118313 * call.cc (add_candidates): Change to not resolve non-default versions in target_version semantics. * class.cc (resolve_address_of_overloaded_function): Ditto. * cp-gimplify.cc (cp_genericize_r): Change logic to not apply for target_version semantics. * decl.cc (start_decl): Change to mark and therefore mangle all target_version decls. (start_preparsed_function): Ditto. * typeck.cc (cp_build_function_call_vec): Add error for calling unresolvable non-default node in target_version semantics. gcc/testsuite/ChangeLog: * g++.target/aarch64/mv-1.C: Change for target_version semantics. * g++.target/aarch64/mv-symbols2.C: Ditto. * g++.target/aarch64/mv-symbols3.C: Ditto. * g++.target/aarch64/mv-symbols4.C: Ditto. * g++.target/aarch64/mv-symbols5.C: Ditto. * g++.target/aarch64/mvc-symbols3.C: Ditto. * g++.target/riscv/mv-symbols2.C: Ditto. * g++.target/riscv/mv-symbols3.C: Ditto. * g++.target/riscv/mv-symbols4.C: Ditto. * g++.target/riscv/mv-symbols5.C: Ditto. * g++.target/riscv/mvc-symbols3.C: Ditto. * g++.target/aarch64/mv-symbols10.C: New test. * g++.target/aarch64/mv-symbols11.C: New test. * g++.target/aarch64/mv-symbols12.C: New test. * g++.target/aarch64/mv-symbols13.C: New test. * g++.target/aarch64/mv-symbols6.C: New test. * g++.target/aarch64/mv-symbols7.C: New test. * g++.target/aarch64/mv-symbols8.C: New test. * g++.target/aarch64/mv-symbols9.C: New test. --- gcc/cgraphunit.cc | 9 ++ gcc/config/aarch64/aarch64.cc | 43 ++---- gcc/config/riscv/riscv.cc | 43 ++---- gcc/cp/call.cc | 10 ++ gcc/cp/class.cc | 13 +- gcc/cp/cp-gimplify.cc | 11 +- gcc/cp/decl.cc | 14 ++ gcc/cp/typeck.cc | 10 ++ gcc/ipa.cc | 11 ++ gcc/multiple_target.cc | 141 ++++++++++++++++-- gcc/passes.def | 3 +- gcc/testsuite/g++.target/aarch64/mv-1.C | 4 + .../g++.target/aarch64/mv-symbols10.C | 27 ++++ .../g++.target/aarch64/mv-symbols11.C | 30 ++++ .../g++.target/aarch64/mv-symbols12.C | 28 ++++ .../g++.target/aarch64/mv-symbols13.C | 28 ++++ .../g++.target/aarch64/mv-symbols2.C | 12 +- .../g++.target/aarch64/mv-symbols3.C | 6 +- .../g++.target/aarch64/mv-symbols4.C | 6 +- .../g++.target/aarch64/mv-symbols5.C | 6 +- .../g++.target/aarch64/mv-symbols6.C | 21 +++ .../g++.target/aarch64/mv-symbols7.C | 48 ++++++ .../g++.target/aarch64/mv-symbols8.C | 46 ++++++ .../g++.target/aarch64/mv-symbols9.C | 43 ++++++ .../g++.target/aarch64/mvc-symbols3.C | 12 +- gcc/testsuite/g++.target/riscv/mv-symbols2.C | 12 +- gcc/testsuite/g++.target/riscv/mv-symbols3.C | 6 +- gcc/testsuite/g++.target/riscv/mv-symbols4.C | 6 +- gcc/testsuite/g++.target/riscv/mv-symbols5.C | 6 +- gcc/testsuite/g++.target/riscv/mvc-symbols3.C | 12 +- 30 files changed, 546 insertions(+), 121 deletions(-) create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols10.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols11.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols12.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols13.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols6.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols7.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols8.C create mode 100644 gcc/testsuite/g++.target/aarch64/mv-symbols9.C diff --git a/gcc/cgraphunit.cc b/gcc/cgraphunit.cc index fa54a59d02b..272b2fd5374 100644 --- a/gcc/cgraphunit.cc +++ b/gcc/cgraphunit.cc @@ -1264,6 +1264,15 @@ analyze_functions (bool first_time) if (!cnode->analyzed) cnode->analyze (); + /* A reference to a default node in a function set implies a + reference to all versions in the set. */ + cgraph_function_version_info *node_v = cnode->function_version (); + if (node_v && is_function_default_version (node->decl)) + for (cgraph_function_version_info *fvi = node_v->next; + fvi; + fvi = fvi->next) + enqueue_node (fvi->this_node); + for (edge = cnode->callees; edge; edge = edge->next_callee) if (edge->callee->definition && (!DECL_EXTERNAL (edge->callee->decl) diff --git a/gcc/config/aarch64/aarch64.cc b/gcc/config/aarch64/aarch64.cc index 43ac50c7734..83b8fc719f9 100644 --- a/gcc/config/aarch64/aarch64.cc +++ b/gcc/config/aarch64/aarch64.cc @@ -20730,42 +20730,29 @@ aarch64_generate_version_dispatcher_body (void *node_p) return resolver_decl; } -/* Make a dispatcher declaration for the multi-versioned function DECL. - Calls to DECL function will be replaced with calls to the dispatcher - by the front-end. Returns the decl of the dispatcher function. */ +/* Make a dispatcher declaration for the multi-versioned default function DECL. + Calls to DECL function will be replaced with calls to the dispatcher by + the target_clones pass. Returns the decl of the dispatcher function. */ tree aarch64_get_function_versions_dispatcher (void *decl) { - tree fn = (tree) decl; - struct cgraph_node *node = NULL; - struct cgraph_node *default_node = NULL; - struct cgraph_function_version_info *node_v = NULL; - + tree default_decl = (tree) decl; tree dispatch_decl = NULL; - struct cgraph_function_version_info *default_version_info = NULL; - - gcc_assert (fn != NULL && DECL_FUNCTION_VERSIONED (fn)); - - node = cgraph_node::get (fn); - gcc_assert (node != NULL); + gcc_assert (decl != NULL + && DECL_FUNCTION_VERSIONED (default_decl) + && is_function_default_version (default_decl)); - node_v = node->function_version (); - gcc_assert (node_v != NULL); + struct cgraph_node *default_node = cgraph_node::get (default_decl); + gcc_assert (default_node != NULL); - if (node_v->dispatcher_resolver != NULL) - return node_v->dispatcher_resolver; + struct cgraph_function_version_info *default_node_v + = default_node->function_version (); + gcc_assert (default_node_v != NULL && !default_node_v->prev); - /* The default node is always the beginning of the chain. */ - default_version_info = node_v; - while (default_version_info->prev) - default_version_info = default_version_info->prev; - default_node = default_version_info->this_node; - - /* If there is no default node, just return NULL. */ - if (!is_function_default_version (default_node->decl)) - return NULL; + if (default_node_v->dispatcher_resolver != NULL) + return default_node_v->dispatcher_resolver; if (targetm.has_ifunc_p ()) { @@ -20775,7 +20762,7 @@ aarch64_get_function_versions_dispatcher (void *decl) dispatch_decl = make_dispatcher_decl (default_node->decl); /* Set the dispatcher for all the versions. */ - it_v = default_version_info; + it_v = default_node_v; while (it_v != NULL) { it_v->dispatcher_resolver = dispatch_decl; diff --git a/gcc/config/riscv/riscv.cc b/gcc/config/riscv/riscv.cc index 5f10cb9accf..a6281d233ac 100644 --- a/gcc/config/riscv/riscv.cc +++ b/gcc/config/riscv/riscv.cc @@ -13712,42 +13712,29 @@ riscv_generate_version_dispatcher_body (void *node_p) return resolver_decl; } -/* Make a dispatcher declaration for the multi-versioned function DECL. - Calls to DECL function will be replaced with calls to the dispatcher - by the front-end. Returns the decl of the dispatcher function. */ +/* Make a dispatcher declaration for the multi-versioned default function DECL. + Calls to DECL function will be replaced with calls to the dispatcher by + the target_clones pass. Returns the decl of the dispatcher function. */ tree riscv_get_function_versions_dispatcher (void *decl) { - tree fn = (tree) decl; - struct cgraph_node *node = NULL; - struct cgraph_node *default_node = NULL; - struct cgraph_function_version_info *node_v = NULL; - + tree default_decl = (tree) decl; tree dispatch_decl = NULL; - struct cgraph_function_version_info *default_version_info = NULL; - - gcc_assert (fn != NULL && DECL_FUNCTION_VERSIONED (fn)); - - node = cgraph_node::get (fn); - gcc_assert (node != NULL); - - node_v = node->function_version (); - gcc_assert (node_v != NULL); + gcc_assert (decl != NULL + && DECL_FUNCTION_VERSIONED (default_decl) + && is_function_default_version (default_decl)); - if (node_v->dispatcher_resolver != NULL) - return node_v->dispatcher_resolver; + struct cgraph_node *default_node = cgraph_node::get (default_decl); + gcc_assert (default_node != NULL); - /* The default node is always the beginning of the chain. */ - default_version_info = node_v; - while (default_version_info->prev) - default_version_info = default_version_info->prev; - default_node = default_version_info->this_node; + struct cgraph_function_version_info *default_node_v + = default_node->function_version (); + gcc_assert (default_node_v != NULL && !default_node_v->prev); - /* If there is no default node, just return NULL. */ - if (!is_function_default_version (default_node->decl)) - return NULL; + if (default_node_v->dispatcher_resolver != NULL) + return default_node_v->dispatcher_resolver; if (targetm.has_ifunc_p ()) { @@ -13757,7 +13744,7 @@ riscv_get_function_versions_dispatcher (void *decl) dispatch_decl = make_dispatcher_decl (default_node->decl); /* Set the dispatcher for all the versions. */ - it_v = default_version_info; + it_v = default_node_v; while (it_v != NULL) { it_v->dispatcher_resolver = dispatch_decl; diff --git a/gcc/cp/call.cc b/gcc/cp/call.cc index 6caac8963cc..ebb6a898643 100644 --- a/gcc/cp/call.cc +++ b/gcc/cp/call.cc @@ -6868,6 +6868,16 @@ add_candidates (tree fns, tree first_arg, const vec<tree, va_gc> *args, continue; } + /* Do not resolve any non-default function. Only the default version + is resolvable (for the target_version attribute semantics.) */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && TREE_CODE (fn) == FUNCTION_DECL + && !is_function_default_version (fn)) + { + add_ignored_candidate (candidates, fn); + continue; + } + if (TREE_CODE (fn) == TEMPLATE_DECL) add_template_candidate (candidates, fn, diff --git a/gcc/cp/class.cc b/gcc/cp/class.cc index 93f1a1bdd81..c28d9e5b3ab 100644 --- a/gcc/cp/class.cc +++ b/gcc/cp/class.cc @@ -8846,6 +8846,13 @@ resolve_address_of_overloaded_function (tree target_type, if (!constraints_satisfied_p (fn)) continue; + /* For target_version semantics, never resolve a non-default + version. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && TREE_CODE (fn) == FUNCTION_DECL + && !is_function_default_version (fn)) + continue; + if (undeduced_auto_decl (fn)) { /* Force instantiation to do return type deduction. */ @@ -9071,8 +9078,10 @@ resolve_address_of_overloaded_function (tree target_type, /* If a pointer to a function that is multi-versioned is requested, the pointer to the dispatcher function is returned instead. This works well because indirectly calling the function will dispatch the right - function version at run-time. */ - if (DECL_FUNCTION_VERSIONED (fn)) + function version at run-time. + This is done at multiple_target.cc for target_version semantics. */ + + if (DECL_FUNCTION_VERSIONED (fn) && TARGET_HAS_FMV_TARGET_ATTRIBUTE) { fn = get_function_version_dispatcher (fn); if (fn == NULL) diff --git a/gcc/cp/cp-gimplify.cc b/gcc/cp/cp-gimplify.cc index d2423fd1848..fa6c3a44e17 100644 --- a/gcc/cp/cp-gimplify.cc +++ b/gcc/cp/cp-gimplify.cc @@ -2153,13 +2153,16 @@ cp_genericize_r (tree *stmt_p, int *walk_subtrees, void *data) returns the function with the highest target priority, that is, the version that will checked for dispatching first. If this version is inlinable, a direct call to this version can be made - otherwise the call should go through the dispatcher. */ + otherwise the call should go through the dispatcher. + This is done at multiple_target.cc for target_version semantics. */ { tree fn = cp_get_callee_fndecl_nofold (stmt); - if (fn && DECL_FUNCTION_VERSIONED (fn) + if (TARGET_HAS_FMV_TARGET_ATTRIBUTE + && fn + && DECL_FUNCTION_VERSIONED (fn) && (current_function_decl == NULL - || !targetm.target_option.can_inline_p (current_function_decl, - fn))) + || !targetm.target_option.can_inline_p + (current_function_decl, fn))) if (tree dis = get_function_version_dispatcher (fn)) { mark_versions_used (dis); diff --git a/gcc/cp/decl.cc b/gcc/cp/decl.cc index 7cf39bcee7f..ec4b1755741 100644 --- a/gcc/cp/decl.cc +++ b/gcc/cp/decl.cc @@ -6171,6 +6171,13 @@ start_decl (const cp_declarator *declarator, was_public = TREE_PUBLIC (decl); + /* For target_version semantics, mark any annotated function as versioned + so that it gets mangled even when on its own in a TU. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && TREE_CODE (decl) == FUNCTION_DECL + && get_target_version (decl).is_valid ()) + maybe_mark_function_versioned (decl); + if ((DECL_EXTERNAL (decl) || TREE_CODE (decl) == FUNCTION_DECL) && current_function_decl) { @@ -18813,6 +18820,13 @@ start_preparsed_function (tree decl1, tree attrs, int flags) if (!DECL_OMP_DECLARE_REDUCTION_P (decl1)) start_lambda_scope (decl1); + /* For target_version semantics, mark any annotated function as versioned + so that it gets mangled even when on its own in a TU. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && TREE_CODE (decl1) == FUNCTION_DECL + && get_target_version (decl1).is_valid ()) + maybe_mark_function_versioned (decl1); + return true; } diff --git a/gcc/cp/typeck.cc b/gcc/cp/typeck.cc index 88f8f34e806..e8ae9866a6c 100644 --- a/gcc/cp/typeck.cc +++ b/gcc/cp/typeck.cc @@ -4439,6 +4439,16 @@ cp_build_function_call_vec (tree function, vec<tree, va_gc> **params, return error_mark_node; fndecl = function; + /* For target_version semantics, the funciton set cannot be called + if there is no default version in scope. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && !is_function_default_version (fndecl)) + { + if (complain & tf_error) + error ("no default version in scope"); + return error_mark_node; + } + /* Convert anything with function type to a pointer-to-function. */ if (DECL_MAIN_P (function)) { diff --git a/gcc/ipa.cc b/gcc/ipa.cc index 8a7b067a526..dea22ea0b49 100644 --- a/gcc/ipa.cc +++ b/gcc/ipa.cc @@ -433,6 +433,17 @@ symbol_table::remove_unreachable_nodes (FILE *file) e, &first, &reachable); } } + + /* A reference to the default node implies use of all the other + versions (they get used in the function resolver made later + in multiple_target.cc) */ + cgraph_function_version_info *node_v = cnode->function_version (); + if (node_v && is_function_default_version (node->decl)) + for (cgraph_function_version_info *fvi = node_v->next; + fvi; + fvi = fvi->next) + enqueue_node (fvi->this_node, &first, &reachable); + for (e = cnode->callees; e; e = e->next_callee) { symtab_node *body = e->callee->function_symbol (); diff --git a/gcc/multiple_target.cc b/gcc/multiple_target.cc index 44340cbc6a4..bb430bc4fbf 100644 --- a/gcc/multiple_target.cc +++ b/gcc/multiple_target.cc @@ -58,8 +58,15 @@ replace_function_decl (tree *op, int *walk_subtrees, void *data) return NULL; } -/* If the call in NODE has multiple target attribute with multiple fields, - replace it with dispatcher call and create dispatcher (once). */ +/* In target FMV attributes, if the call in NODE has multiple target attribute + with multiple fields, replace it with calls to the dispatched symbol and + create the disptacher body (once). + + In target_version semantics, if it is a lone annotated default, then + the dispatched symbol is changed to be an alias and no resolver is + required. Otherwise, redirect all calls and references to the dispatched + symbol, but only create the resolver body if the default version is + implemented. */ static void create_dispatcher_calls (struct cgraph_node *node) @@ -90,13 +97,48 @@ create_dispatcher_calls (struct cgraph_node *node) cgraph_node *inode = cgraph_node::get (idecl); gcc_assert (inode); - tree resolver_decl = targetm.generate_version_dispatcher_body (inode); - - /* Update aliases. */ - inode->alias = true; - inode->alias_target = resolver_decl; - if (!inode->analyzed) - inode->resolve_alias (cgraph_node::get (resolver_decl)); + cgraph_function_version_info *inode_info = inode->function_version (); + gcc_assert (inode_info); + + tree resolver_decl = NULL; + + /* For target_version semantics, if there is a lone default declaration + it needs to be mangled, with an alias from the dispatched symbol to the + default version. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE + && TREE_STATIC (node->decl) + && inode_info->next + && !inode_info->next->next) + { + inode->alias = true; + inode->alias_target = inode_info->next->this_node->decl; + inode->externally_visible = true; + if (!inode->analyzed) + inode->resolve_alias + (cgraph_node::get (inode_info->next->this_node->decl)); + + DECL_ATTRIBUTES (idecl) + = make_attribute ("alias", + IDENTIFIER_POINTER + (DECL_ASSEMBLER_NAME + (inode_info->next->this_node->decl)), + DECL_ATTRIBUTES (node->decl)); + TREE_USED (idecl) = true; + DECL_EXTERNAL (idecl) = false; + TREE_STATIC (idecl) = true; + return; + } + /* In target_version semantics, only create the resolver if the + default node is implemented. */ + else if (TARGET_HAS_FMV_TARGET_ATTRIBUTE || TREE_STATIC (node->decl)) + { + resolver_decl = targetm.generate_version_dispatcher_body (inode); + /* Update aliases. */ + inode->alias = true; + inode->alias_target = resolver_decl; + if (!inode->analyzed) + inode->resolve_alias (cgraph_node::get (resolver_decl)); + } auto_vec<cgraph_edge *> edges_to_redirect; /* We need to capture the references by value rather than just pointers to them @@ -333,8 +375,7 @@ expand_target_clones (struct cgraph_node *node, bool definition) continue; /* Create new target clone. */ - tree attributes = make_attribute (new_attr_name, attr, - DECL_ATTRIBUTES (node->decl)); + tree attributes = make_attribute (new_attr_name, attr, attrs); cgraph_node *new_node = create_target_clone (node, definition, NULL, attributes); @@ -424,15 +465,76 @@ redirect_to_specific_clone (cgraph_node *node) } } +static bool is_simple_target_clones_case (cgraph_node *node) +{ + /* target attribute semantics doesnt support the complex case, + so this is always true. */ + if (TARGET_HAS_FMV_TARGET_ATTRIBUTE) + return true; + + int num_defaults = 0; + auto versions = get_clone_versions (node->decl, &num_defaults); + if (versions.is_empty () || num_defaults != 1) + return false; + + cgraph_function_version_info *fv = node->function_version (); + + if (fv && (fv->next || fv->prev)) + return false; + + return true; +} + static unsigned int -ipa_target_clone (void) +ipa_target_clone (bool early) { struct cgraph_node *node; auto_vec<cgraph_node *> to_dispatch; + /* Don't need to do anything early for target attribute semantics. */ + if (early && TARGET_HAS_FMV_TARGET_ATTRIBUTE) + return 0; + + /* For target attribute semantics, this pass skips the early phase, and in + the later stage is only responsible for expanding and dispatching + target_clone declarations, as target annotated functions are dispatched + in the front end. + + The expanding and dispatching can be done at the late stage as the + target_clone functions aren't allowed to be part of a larger FMV set, so + all versions will all have the same body, so early optimisations are safe + to treat a call to a target_clones set as a call to one function. + + For target_version semantics, this pass is responsible for expanding + target_clones and dispatching all FMV function sets, including ones only + made up of target_version declarations. + + Cases where there is more than one declaration must be expanded and + dispatched at the early stage, as the declarations may have different + bodies, and so the early optimisation passes would not be valid. + + The late stage is only used for the expansion and dispatching of the simple + case where the FMV set is defined by a single target_clone attribute. */ + FOR_EACH_FUNCTION (node) - if (expand_target_clones (node, node->definition)) - to_dispatch.safe_push (node); + { + /* In the early stage, we need to expand any target clone that is not + the simple case. */ + if ((!early || !is_simple_target_clones_case (node))) + if (expand_target_clones (node, node->definition) + && TARGET_HAS_FMV_TARGET_ATTRIBUTE) + /* In non target_version semantics, dispatch all target clones. */ + to_dispatch.safe_push (node); + } + + /* In target_version semantics dispatch all FMV function sets with a default + implementation. */ + if (!TARGET_HAS_FMV_TARGET_ATTRIBUTE) + FOR_EACH_FUNCTION (node) + if (is_function_default_version (node->decl) + && !lookup_attribute ("target_clones", DECL_ATTRIBUTES (node->decl)) + && DECL_FUNCTION_VERSIONED (node->decl)) + to_dispatch.safe_push (node); for (unsigned i = 0; i < to_dispatch.length (); i++) create_dispatcher_calls (to_dispatch[i]); @@ -463,14 +565,21 @@ class pass_target_clone : public simple_ipa_opt_pass { public: pass_target_clone (gcc::context *ctxt) - : simple_ipa_opt_pass (pass_data_target_clone, ctxt) + : simple_ipa_opt_pass (pass_data_target_clone, ctxt), early_p (false) {} + bool early_p; + void set_pass_param (unsigned int n, bool param) final override + { + gcc_assert (n == 0); + early_p = param; + } /* opt_pass methods: */ bool gate (function *) final override; + opt_pass * clone () final override { return new pass_target_clone (m_ctxt); } unsigned int execute (function *) final override { - return ipa_target_clone (); + return ipa_target_clone (early_p); } }; diff --git a/gcc/passes.def b/gcc/passes.def index 9fd85a35a63..3aef2b60573 100644 --- a/gcc/passes.def +++ b/gcc/passes.def @@ -51,6 +51,7 @@ along with GCC; see the file COPYING3. If not see NEXT_PASS (pass_ipa_function_and_variable_visibility); NEXT_PASS (pass_ipa_strub_mode); NEXT_PASS (pass_build_ssa_passes); + NEXT_PASS (pass_target_clone, true); PUSH_INSERT_PASSES_WITHIN (pass_build_ssa_passes) NEXT_PASS (pass_fixup_cfg); NEXT_PASS (pass_build_ssa); @@ -138,7 +139,7 @@ along with GCC; see the file COPYING3. If not see POP_INSERT_PASSES () POP_INSERT_PASSES () - NEXT_PASS (pass_target_clone); + NEXT_PASS (pass_target_clone, false); NEXT_PASS (pass_ipa_auto_profile); NEXT_PASS (pass_ipa_tree_profile); PUSH_INSERT_PASSES_WITHIN (pass_ipa_tree_profile) diff --git a/gcc/testsuite/g++.target/aarch64/mv-1.C b/gcc/testsuite/g++.target/aarch64/mv-1.C index b10037f1b9b..93b8a136587 100644 --- a/gcc/testsuite/g++.target/aarch64/mv-1.C +++ b/gcc/testsuite/g++.target/aarch64/mv-1.C @@ -37,3 +37,7 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3foov\._Mrng:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._MrngMflagm:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._Mflagm:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols10.C b/gcc/testsuite/g++.target/aarch64/mv-symbols10.C new file mode 100644 index 00000000000..92d4ab617d8 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols10.C @@ -0,0 +1,27 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +__attribute__ ((target_version ("default"))) void +foo (int a = 3); + +__attribute__ ((target_version ("sve"))) void +foo (int a = 4); + +void bar() { + foo(); +} + +__attribute__ ((target_version ("sve"))) void +foo2 (int a = 6); + +__attribute__ ((target_version ("default"))) void +foo2 (int a = 5); + +void bar2() { + foo2(); +} + + +/* { dg-final { scan-assembler-times "\n\tmov\tw\[0-9\]\+, 3\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tmov\tw\[0-9\]\+, 5\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols11.C b/gcc/testsuite/g++.target/aarch64/mv-symbols11.C new file mode 100644 index 00000000000..dadde22622e --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols11.C @@ -0,0 +1,30 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +__attribute__ ((target_version ("default"))) int +foo () { return 1; } + +__attribute__ ((target_version ("dotprod"))) int +foo () { return 3; } + +int (*test)(); + +void bar () +{ + test = foo; +} + +__attribute__ ((target_version ("default"))) int +foo2 (); + +__attribute__ ((target_version ("dotprod"))) int +foo2 (); + +void bar2 () +{ + test = foo2; +} + +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z4foo2v\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols12.C b/gcc/testsuite/g++.target/aarch64/mv-symbols12.C new file mode 100644 index 00000000000..d78ee4b91c5 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols12.C @@ -0,0 +1,28 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +int foo () { + return 1; +} + +void +bar () +{ + foo (); +} + +__attribute__ ((target_version ("dotprod"))) int +foo (); + +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 0 } } */ + +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._Mdotprod\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\.default\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols13.C b/gcc/testsuite/g++.target/aarch64/mv-symbols13.C new file mode 100644 index 00000000000..997b9bad6d6 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols13.C @@ -0,0 +1,28 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +int foo () { + return 1; +} + +void bar () +{ + int (*test)() = foo; + + test(); +} + +__attribute__ ((target_version ("dotprod"))) int foo (); + +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 0 } } */ + +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._Mdotprod\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\.default\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols2.C b/gcc/testsuite/g++.target/aarch64/mv-symbols2.C index 6da88ddfb48..55f2d48f5e4 100644 --- a/gcc/testsuite/g++.target/aarch64/mv-symbols2.C +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols2.C @@ -41,13 +41,13 @@ int foo (int) /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._Mdotprod:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._MsveMsve2:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols3.C b/gcc/testsuite/g++.target/aarch64/mv-symbols3.C index 5dd7b49be2a..6ba02a2aae9 100644 --- a/gcc/testsuite/g++.target/aarch64/mv-symbols3.C +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols3.C @@ -29,10 +29,10 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._Mdotprod:\n" 0 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols4.C b/gcc/testsuite/g++.target/aarch64/mv-symbols4.C index 4b25d17cc15..cc013c47848 100644 --- a/gcc/testsuite/g++.target/aarch64/mv-symbols4.C +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols4.C @@ -44,6 +44,6 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._Mdotprod:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._MsveMsve2:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols5.C b/gcc/testsuite/g++.target/aarch64/mv-symbols5.C index fac00b20313..1396ca379e4 100644 --- a/gcc/testsuite/g++.target/aarch64/mv-symbols5.C +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols5.C @@ -44,10 +44,10 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._Mdotprod:\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols6.C b/gcc/testsuite/g++.target/aarch64/mv-symbols6.C new file mode 100644 index 00000000000..2b67bcb47a4 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols6.C @@ -0,0 +1,21 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +__attribute__ ((target_version ("default"))) int +foo () +{ + return 1; +} + +int bar() +{ + return foo(); +} + +/* { dg-final { scan-assembler-times "\n_Z3foov:\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ +/* { dg-final { scan-assembler-times "bl\t_Z3foov.default\n" 1 } } */ +/* { dg-final { scan-assembler-times ".global\t_Z3foov\n" 1 } } */ +/* { dg-final { scan-assembler-times ".set\t_Z3foov,_Z3foov.default\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols7.C b/gcc/testsuite/g++.target/aarch64/mv-symbols7.C new file mode 100644 index 00000000000..3998adb54a7 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols7.C @@ -0,0 +1,48 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +__attribute__ ((target_version ("dotprod"))) int +foo (); + +__attribute__ ((target_version ("sve+sve2"))) int +foo (); + +__attribute__ ((target_version ("default"))) int +foo (); + +__attribute__ ((target_version ("sve+sve2"))) int +foo () +{ + return 5; +} +__attribute__ ((target_version ("dotprod"))) int +foo () +{ + return 3; +} +__attribute__ ((target_version ("default"))) int +foo () +{ + return 1; +} + +int +bar () +{ + return foo (); +} + +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._MsveMsve2\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._Mdotprod\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\.default\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols8.C b/gcc/testsuite/g++.target/aarch64/mv-symbols8.C new file mode 100644 index 00000000000..5983bbd6925 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols8.C @@ -0,0 +1,46 @@ +/* { dg-do compile } */ +/* { dg-require-ifunc "" } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +__attribute__ ((target_version ("dotprod"))) int +foo (); +__attribute__ ((target_version ("sve+sve2"))) int +foo (); + +int +foo () +{ + return 1; +} + +__attribute__ ((target_version ("dotprod"))) int +foo () +{ + return 3; +} +__attribute__ ((target_version ("sve+sve2"))) int +foo () +{ + return 5; +} + +int +bar () +{ + return foo (); +} + +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._MsveMsve2\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._Mdotprod\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\.default\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mv-symbols9.C b/gcc/testsuite/g++.target/aarch64/mv-symbols9.C new file mode 100644 index 00000000000..bfad9bb5850 --- /dev/null +++ b/gcc/testsuite/g++.target/aarch64/mv-symbols9.C @@ -0,0 +1,43 @@ +/* { dg-do compile } */ +/* { dg-options "-O0" } */ +/* { dg-additional-options "-Wno-experimental-fmv-target" } */ + +int +foo (); + +int +foo () +{ + return 1; +} + +__attribute__ ((target_version ("dotprod"))) int +foo () +{ + return 3; +} +__attribute__ ((target_version ("sve+sve2"))) int +foo () +{ + return 5; +} + +int +bar () +{ + return foo (); +} + +/* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._MsveMsve2\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\._Mdotprod\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\tadrp\tx\[0-9\]+, _Z3foov\.default\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ + +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/aarch64/mvc-symbols3.C b/gcc/testsuite/g++.target/aarch64/mvc-symbols3.C index 350a5586643..2a315d2db5c 100644 --- a/gcc/testsuite/g++.target/aarch64/mvc-symbols3.C +++ b/gcc/testsuite/g++.target/aarch64/mvc-symbols3.C @@ -22,15 +22,15 @@ int bar(int x) /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._Mdotprod:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\._MsveMsve2:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tbl\t_Z3foov\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, %gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._Mdotprod:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\._MsveMsve2:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tbl\t_Z3fooi\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, %gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ diff --git a/gcc/testsuite/g++.target/riscv/mv-symbols2.C b/gcc/testsuite/g++.target/riscv/mv-symbols2.C index 43fa1502b7d..8a5c5a0bc9f 100644 --- a/gcc/testsuite/g++.target/riscv/mv-symbols2.C +++ b/gcc/testsuite/g++.target/riscv/mv-symbols2.C @@ -47,15 +47,15 @@ int foo (int) /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__v:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__zba__zbb:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3foov\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__v:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__zba__zbb:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3fooi\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/riscv/mv-symbols3.C b/gcc/testsuite/g++.target/riscv/mv-symbols3.C index 6596a277f6a..2a7b2bc8e42 100644 --- a/gcc/testsuite/g++.target/riscv/mv-symbols3.C +++ b/gcc/testsuite/g++.target/riscv/mv-symbols3.C @@ -36,10 +36,10 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__v:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__zba__zbb:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3foov(?:@plt)?\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__v:\n" 0 } } */ diff --git a/gcc/testsuite/g++.target/riscv/mv-symbols4.C b/gcc/testsuite/g++.target/riscv/mv-symbols4.C index 83d51e33706..7665e775239 100644 --- a/gcc/testsuite/g++.target/riscv/mv-symbols4.C +++ b/gcc/testsuite/g++.target/riscv/mv-symbols4.C @@ -50,7 +50,7 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__v:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__zba__zbb:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3fooi(?:@plt)?\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/riscv/mv-symbols5.C b/gcc/testsuite/g++.target/riscv/mv-symbols5.C index c92421ab0fb..5ca31851618 100644 --- a/gcc/testsuite/g++.target/riscv/mv-symbols5.C +++ b/gcc/testsuite/g++.target/riscv/mv-symbols5.C @@ -48,10 +48,10 @@ int bar() /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__v:\n" 1 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__zba__zbb:\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3foov(?:@plt)?\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__v:\n" 1 } } */ diff --git a/gcc/testsuite/g++.target/riscv/mvc-symbols3.C b/gcc/testsuite/g++.target/riscv/mvc-symbols3.C index 78f027b0457..e3987eaa75a 100644 --- a/gcc/testsuite/g++.target/riscv/mvc-symbols3.C +++ b/gcc/testsuite/g++.target/riscv/mvc-symbols3.C @@ -28,15 +28,15 @@ int bar(int x) /* { dg-final { scan-assembler-times "\n_Z3foov\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__v:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3foov\.arch__zba__zbb:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3foov\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3foov(?:@plt)?\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3foov, @gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3foov,_Z3foov\.resolver\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.default:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__v:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n_Z3fooi\.arch__zba__zbb:\n" 0 } } */ -/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n_Z3fooi\.resolver:\n" 0 } } */ /* { dg-final { scan-assembler-times "\n\tcall\t_Z3fooi(?:@plt)?\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 1 } } */ -/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 1 } } */ +/* { dg-final { scan-assembler-times "\n\t\.type\t_Z3fooi, @gnu_indirect_function\n" 0 } } */ +/* { dg-final { scan-assembler-times "\n\t\.set\t_Z3fooi,_Z3fooi\.resolver\n" 0 } } */ -- 2.34.1