diff options
author | Nathan Sidwell <nathan@gcc.gnu.org> | 2018-08-16 14:13:51 +0000 |
---|---|---|
committer | Nathan Sidwell <nathan@gcc.gnu.org> | 2018-08-16 14:13:51 +0000 |
commit | b27d440b39fff2befe700afa30d5f71faeb02e97 (patch) | |
tree | 5d4774bbdf70ad62bb5b7ef7ce0e55bf8670c2b3 | |
parent | 646ba1e958822368e8b2034e832f35383395abae (diff) | |
parent | 3f6677f418564e634e3b77b0fc385891d1fdf1da (diff) | |
download | gcc-b27d440b39fff2befe700afa30d5f71faeb02e97.zip gcc-b27d440b39fff2befe700afa30d5f71faeb02e97.tar.gz gcc-b27d440b39fff2befe700afa30d5f71faeb02e97.tar.bz2 |
Merge trunk r263587.
From-SVN: r263588
108 files changed, 3178 insertions, 835 deletions
diff --git a/ChangeLog.name-lookup b/ChangeLog.name-lookup index 0afb884..0f2ae63 100644 --- a/ChangeLog.name-lookup +++ b/ChangeLog.name-lookup @@ -1,3 +1,7 @@ +2018-08-16 Nathan Sidwell <nathan@acm.org> + + Merge trunk r263587. + 2018-08-15 Nathan Sidwell <nathan@acm.org> Merge trunk r263558. diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 5728118..fdac7e7 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,123 @@ +2018-08-16 Nathan Sidwell <nathan@acm.org> + + * config/rs6000/rs6000-c.c (rs6000_macro_to_expend): Use cpp_macro_p. + * config/powerpcspc/powerpcspe-c.c (rs6000_macro_to_expend): Likewise. + +2018-08-16 Tamar Christina <tamar.christina@arm.com> + + PR target/84711 + * config/arm/arm.c (arm_can_change_mode_class): Disallow subreg. + * config/arm/neon.md (movv4hf, movv8hf): Refactored to.. + (mov<mov>): ..this and enable unconditionally. + +2018-08-16 Tamar Christina <tamar.christina@arm.com> + + * config/arm/neon.md (*neon_mov<mode>): Remove reg-to-reg alternative. + +2018-08-16 Sam Tebbs <sam.tebbs@arm.com> + + * config/aarch64/aarch64.opt (mlow-precision-recip-sqrt) + (mlow-precision-sqrt, mlow-precision-div, mverbose-cost-dump): Replace + "Common" with "Target". + +2018-08-15 Uros Bizjak <ubizjak@gmail.com> + + * config/i386/i386.opt (mmitigate-rop): Mark as deprecated. + * doc/invoke.texi (mmitigate-rop): Remove. + * config/i386/i386.c: Do not include "regrename.h". + (ix86_rop_should_change_byte_p, reg_encoded_number) + (ix86_get_modrm_for_rop, set_rop_modrm_reg_bits, ix86_mitigate_rop): + Remove. + (ix86_reorg): Remove call to ix86_mitigate_rop. + * config/i386/i386.md (attr "modrm_class"): Remove. + (cmp<mode>_ccno_1, mov<mode>_xor, movstrict<mode>_xor) + (x86_mov<mode>cc_0_m1. x86_mov<mode>cc_0_m1_se) + (x86_mov<mode>cc_0_m1_neg): Remove modrm_class attribute override. + +2018-08-15 Will Schmidt <will_schmidt@vnet.ibm.com> + + * config/rs6000/rs600.c (rs6000_gimple_fold_builtin): Add entries to + allow folding of mergeh() and mergel() for the float and double types. + (fold_mergehl_helper): Rework to handle building a permute tree + for float vectors. + +2018-08-15 Uros Bizjak <ubizjak@gmail.com> + + * config/i386/i386.c (expand_vec_perm_movs): Enable V4SFmode + for TARGET_SSE. + +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * common.opt (fdiagnostics-show-labels): New option. + * diagnostic-show-locus.c (class layout_range): Add field + "m_label". + (class layout): Add field "m_show_labels_p". + (layout_range::layout_range): Add param "label" and use it to + initialize m_label. + (make_range): Pass in NULL for new "label" param of layout_range's + ctor. + (layout::layout): Initialize m_show_labels_p. + (layout::maybe_add_location_range): Pass in loc_range->m_label + when constructing layout_range instances. + (struct line_label): New struct. + (layout::print_any_labels): New member function. + (layout::print_line): Call it if label-printing is enabled. + (selftest::test_one_liner_labels): New test. + (selftest::test_diagnostic_show_locus_one_liner): Call it. + * diagnostic.c (diagnostic_initialize): Initialize + context->show_labels_p. + * diagnostic.h (struct diagnostic_context): Add field + "show_labels_p". + * doc/invoke.texi (Diagnostic Message Formatting Options): Add + -fno-diagnostics-show-labels. + * dwarf2out.c (gen_producer_string): Add + OPT_fdiagnostics_show_labels to the ignored options. + * gcc-rich-location.c (gcc_rich_location::add_expr): Add "label" + param. + (gcc_rich_location::maybe_add_expr): Likewise. + * gcc-rich-location.h (gcc_rich_location::gcc_rich_location): Add + label" param, defaulting to NULL. + (gcc_rich_location::add_expr): Add "label" param. + (gcc_rich_location::maybe_add_expr): Likewise. + (class text_range_label): New class. + (class range_label_for_type_mismatch): New class. + * gimple-ssa-sprintf.c (fmtwarn): Pass NULL for new label params + of format_warning_va. + (fmtwarn_n): Likewise for new params of format_warning_n_va. + * lto-wrapper.c (merge_and_complain): Add + OPT_fdiagnostics_show_labels to the "pick one setting" options. + (append_compiler_options): Likewise to the dropped options. + (append_diag_options): Likewise to the passed-on options. + * opts.c (common_handle_option): Handle the new option. + * selftest-diagnostic.c + (test_diagnostic_context::test_diagnostic_context): Enable + show_labels_p. + * substring-locations.c: Include "gcc-rich-location.h". + (format_warning_n_va): Add "fmt_label" and "param_label" params + and use them as appropriate. + (format_warning_va): Add "fmt_label" and "param_label" params, + passing them on to format_warning_n_va. + (format_warning_at_substring): Likewise. + (format_warning_at_substring_n): Likewise. + * substring-locations.h (format_warning_va): Add "fmt_label" and + "param_label" params. + (format_warning_n_va): Likewise. + (format_warning_at_substring): Likewise. + (format_warning_at_substring_n): Likewise. + * toplev.c (general_init): Initialize global_dc->show_labels_p. + +2018-08-15 Qing Zhao <qing.zhao@oracle.com> + + PR testsuite/86519 + * builtins.c (expand_builtin_memcmp): Do not expand the call + when overflow is detected. + +2018-08-15 Martin Sebor <msebor@redhat.com> + + PR tree-optimization/71625 + * config/aarch64/aarch64-builtins.c + (aarch64_init_simd_builtin_types): Clear Poly8_t's TYPE_STRING_FLAG. + 2018-08-15 Ilya Leoshkevich <iii@linux.ibm.com> * config/s390/s390.c (s390_reorg): Remove loop. @@ -18,13 +138,13 @@ 2018-08-15 Martin Liska <mliska@suse.cz> - PR tree-optimization/86925 + PR tree-optimization/86925 * predict.c (expr_expected_value_1): When taking - later predictor, assign also probability. - Use fold_build2_initializer_loc in order to fold - the expression in -frounding-math. + later predictor, assign also probability. + Use fold_build2_initializer_loc in order to fold + the expression in -frounding-math. -2018-08-14 Allan Sandfeld Jensen <allan.jensen@qt.io> +2018-08-14 Allan Sandfeld Jensen <allan.jensen@qt.io> * config/i386/i386.c (expand_vec_perm_movs): New method matching movs patterns. @@ -32,9 +152,9 @@ 2018-08-14 Ilya Leoshkevich <iii@linux.ibm.com> - PR target/86547 + PR target/86547 * lra-lives.c (remove_some_program_points_and_update_live_ranges): - Check whether lra_live_max_point is 0 before dividing. + Check whether lra_live_max_point is 0 before dividing. 2018-08-14 Martin Sebor <msebor@redhat.com> @@ -58,13 +178,13 @@ * gcc/config/rs6000/rs6000.c (rs6000_gimple_fold_builtin): Add support for folding vec_perm. -2018-08-13 Will Schmidt <will_schmidt@vnet.ibm.com> +2018-08-13 Will Schmidt <will_schmidt@vnet.ibm.com> * config/rs6000/rs6000.c (rs6000_gimple_fold_builtin): Add support for gimple-folding of vec_pack() and vec_unpack() intrinsics. -2018-08-13 Will Schmidt <will_schmidt@vnet.ibm.com> +2018-08-13 Will Schmidt <will_schmidt@vnet.ibm.com> * config/rs6000/rs6000.c (rs6000_builtin_valid_without_lhs): Add vec_xst variants to the list. @@ -85,9 +205,9 @@ 2018-08-13 Ilya Leoshkevich <iii@linux.ibm.com> * config/s390/s390.c (s390_decompose_constant_pool_ref): - New function. + New function. (s390_decompose_address): Factor out constant pool ref - decomposition. + decomposition. 2018-08-12 Chung-Ju Wu <jasonwucj@gmail.com> @@ -161,14 +281,14 @@ 2018-08-10 Martin Liska <mliska@suse.cz> - PR target/83610 + PR target/83610 * builtin-types.def (BT_FN_LONG_LONG_LONG_DOUBLE): Add new - function type. + function type. * builtins.c (expand_builtin_expect_with_probability): - New function. + New function. (expand_builtin_expect_with_probability): New function. (build_builtin_expect_predicate): Add new argumnet probability - for BUILT_IN_EXPECT_WITH_PROBABILITY. + for BUILT_IN_EXPECT_WITH_PROBABILITY. (fold_builtin_expect): (fold_builtin_2): (fold_builtin_3): @@ -178,30 +298,30 @@ * doc/invoke.texi: Likewise. * gimple-fold.c (gimple_fold_call): Pass new argument. * ipa-fnsummary.c (find_foldable_builtin_expect): Handle - also BUILT_IN_EXPECT_WITH_PROBABILITY. + also BUILT_IN_EXPECT_WITH_PROBABILITY. * predict.c (get_predictor_value): New function. (expr_expected_value): Add new argument probability. Assume - that predictor and probability are always non-null. + that predictor and probability are always non-null. (expr_expected_value_1): Likewise. For __builtin_expect and - __builtin_expect_with_probability set probability. Handle - combination in binary expressions. + __builtin_expect_with_probability set probability. Handle + combination in binary expressions. (tree_predict_by_opcode): Simplify code by simply calling - get_predictor_value. + get_predictor_value. (pass_strip_predict_hints::execute): Add handling of - BUILT_IN_EXPECT_WITH_PROBABILITY. + BUILT_IN_EXPECT_WITH_PROBABILITY. * predict.def (PRED_BUILTIN_EXPECT_WITH_PROBABILITY): Add - new predictor. + new predictor. * tree.h (DECL_BUILT_IN_P): New function. 2018-08-10 Martin Liska <mliska@suse.cz> - PR tree-optimization/85799 + PR tree-optimization/85799 * passes.def: Add argument for pass_strip_predict_hints. * predict.c (class pass_strip_predict_hints): Add new argument - early_p. + early_p. (strip_predictor_early): New function. (pass_strip_predict_hints::execute): Call the function to - strip predictors. + strip predictors. (strip_predict_hints): New function. * predict.def: Fix comment. @@ -294,14 +414,14 @@ 2018-08-09 Martin Liska <mliska@suse.cz> - PR c/86895 + PR c/86895 * common.opt: Remove extra line. 2018-08-09 Martin Liska <mliska@suse.cz> * params.def (PARAM_ALIGN_LOOP_ITERATIONS): Remove double dots - at the end of a line, make first letter capital and end up - a sentence with a dot. + at the end of a line, make first letter capital and end up + a sentence with a dot. (PARAM_LOOP_INTERCHANGE_STRIDE_RATIO): Likewise. (PARAM_LOOP_BLOCK_TILE_SIZE): Likewise. (PARAM_GRAPHITE_MAX_NB_SCOP_PARAMS): Likewise. @@ -368,7 +488,7 @@ 2018-08-08 Ilya Leoshkevich <iii@linux.ibm.com> * config/s390/s390.c (s390_loadrelative_operand_p): - Remove TARGET_CPU_ZARCH usages. + Remove TARGET_CPU_ZARCH usages. (s390_rtx_costs): Likewise. (s390_legitimate_constant_p): Likewise. (s390_cannot_force_const_mem): Likewise. @@ -388,7 +508,7 @@ (s390_register_info): Remove split_branches_pending_p uages. (s390_optimize_register_info): Likewise. (s390_init_frame_layout): Remove TARGET_CPU_ZARCH and - split_branches_pending_p usages. + split_branches_pending_p usages. (s390_can_eliminate): Remove TARGET_CPU_ZARCH usages. (s390_load_got): Likewise. (s390_expand_split_stack_prologue): Likewise. @@ -398,9 +518,9 @@ (s390_conditional_register_usage): Likewise. (s390_optimize_prologue): Likewise. (s390_reorg): Remove TARGET_CPU_ZARCH and - split_branches_pending_p usages. + split_branches_pending_p usages. (s390_option_override_internal): Remove TARGET_CPU_ZARCH - usages. + usages. (s390_output_indirect_thunk_function): Likewise. * config/s390/s390.h (TARGET_CPU_ZARCH): Removed. (TARGET_CPU_ZARCH_P): Removed. @@ -410,29 +530,29 @@ 2018-08-08 Ilya Leoshkevich <iii@linux.ibm.com> * common/config/s390/s390-common.c (processor_flags_table): - Remove flags. + Remove flags. * config.gcc: Remove with_arch/with_tune support. * config/s390/2064.md: Remove cpu attribute comparisons. * config/s390/driver-native.c (s390_host_detect_local_cpu): - Remove MTN. + Remove MTN. * config/s390/linux.h (ASM_SPEC): - Remove -march support. + Remove -march support. * config/s390/s390-c.c (s390_cpu_cpp_builtins_internal): - Use a table to get an arch level. + Use a table to get an arch level. * config/s390/s390-opts.h (enum processor_type): - Remove enum values. + Remove enum values. * config/s390/s390.c - (processor_table): Remove entries, add arch_level values. - (s390_issue_rate): Remove cases. - (s390_option_override): Adjust - s390_option_override_internal() call. + (processor_table): Remove entries, add arch_level values. + (s390_issue_rate): Remove cases. + (s390_option_override): Adjust + s390_option_override_internal() call. (s390_option_override_internal): Remove deprecation warning. - (s390_valid_target_attribute_tree): Adjust - s390_option_override_internal() call. + (s390_valid_target_attribute_tree): Adjust + s390_option_override_internal() call. * config/s390/s390.h (struct s390_processor): - Share with s390-c.c, add arch_level field. + Share with s390-c.c, add arch_level field. * config/s390/s390.md: - Remove occurrences in cpu attribute. + Remove occurrences in cpu attribute. * config/s390/s390.opt: Remove -march/-mtune support. * config/s390/tpf.h (ASM_SPEC): Remove -march support. * doc/invoke.texi: Remove deprecation warning. @@ -460,12 +580,12 @@ 2018-08-07 Martin Liska <mliska@suse.cz> - PR middle-end/83023 + PR middle-end/83023 * predict.c (expr_expected_value_1): Handle DECL_IS_MALLOC, - BUILT_IN_REALLOC and DECL_IS_OPERATOR_NEW. + BUILT_IN_REALLOC and DECL_IS_OPERATOR_NEW. * predict.def (PRED_MALLOC_NONNULL): New predictor. * doc/extend.texi: Document that malloc attribute adds - hit to compiler. + hit to compiler. 2018-08-06 John David Anglin <danglin@gcc.gnu.org> @@ -479,7 +599,7 @@ the vr_values instance to cprop_into_stmt. (cprop_into_stmt): Pass vr_values instance down to cprop_operand. (cprop_operand): Also query EVRP to determine if OP is a constant. - + 2018-08-06 Nathan Sidwell <nathan@acm.org> * diagnostic.c (diagnostic_report_current_module): Reroll @@ -706,7 +826,7 @@ 2018-08-03 Martin Liska <mliska@suse.cz> * predict.c (dump_prediction): Change to 2 digits - in fraction part. + in fraction part. 2018-08-03 Siddhesh Poyarekar <siddhesh@sourceware.org> @@ -907,11 +1027,11 @@ 2018-08-02 Martin Liska <mliska@suse.cz> - PR gcov-profile/86817 + PR gcov-profile/86817 * gcov.c (process_all_functions): New function. (main): Call it. (process_file): Move functions processing to - process_all_functions. + process_all_functions. 2018-08-02 David Malcolm <dmalcolm@redhat.com> @@ -926,8 +1046,8 @@ PR tree-optimization/86650 * gimple-pretty-print.c (percent_G_format): Accept a "gimple *" rather than a "gcall *". Directly pass the data of interest - to percent_K_format, rather than building a temporary CALL_EXPR - to hold it. + to percent_K_format, rather than building a temporary CALL_EXPR + to hold it. * gimple-fold.c (gimple_fold_builtin_strncpy): Adjust. (gimple_fold_builtin_strncat): Adjust. * gimple-ssa-warn-restrict.h (check_bounds_or_overlap): Replace @@ -1078,16 +1198,16 @@ 2018-08-01 Martin Liska <mliska@suse.cz> * value-prof.c (gimple_divmod_fixed_value_transform): Unify - format how successful transformation is dumped. + format how successful transformation is dumped. (gimple_mod_pow2_value_transform): Likewise. (gimple_mod_subtract_transform): Likewise. (gimple_stringops_transform): Likewise. 2018-08-01 Martin Liska <mliska@suse.cz> - PR value-prof/35543 + PR value-prof/35543 * value-prof.c (interesting_stringop_to_profile_p): - Simplify the code and add BUILT_IN_MEMMOVE. + Simplify the code and add BUILT_IN_MEMMOVE. (gimple_stringops_transform): Likewise. 2018-08-01 Sam Tebbs <sam.tebbs@arm.com> @@ -1115,7 +1235,7 @@ * graphite.h: Include isl/id.h and isl/space.h to allow build with ISL 0.20. -2018-08-01 Jan Willem Jagersma <jwjagersma@gmail.com> +2018-08-01 Jan Willem Jagersma <jwjagersma@gmail.com> PR target/86651 * dwarf2out.c (dwarf2out_early_finish): Do not generate assembly in LTO @@ -1138,7 +1258,7 @@ * final.c (decl_to_instance_map): Document LTO strategy. 2018-07-31 Alexandre Oliva <oliva@adacore.com> - Olivier Hainque <hainque@adacore.com> + Olivier Hainque <hainque@adacore.com> * debug.h (decl_to_instance_map_t): New type. (decl_to_instance_map): Declare. @@ -2200,29 +2320,29 @@ 2018-07-31 Martin Liska <mliska@suse.cz> - PR gcov-profile/85338 - PR gcov-profile/85350 - PR gcov-profile/85372 - * profile.c (struct location_triplet): New. + PR gcov-profile/85338 + PR gcov-profile/85350 + PR gcov-profile/85372 + * profile.c (struct location_triplet): New. (struct location_triplet_hash): Likewise. (output_location): Do not output a BB that - is already recorded for a line. + is already recorded for a line. (branch_prob): Use streamed_locations. 2018-07-31 Martin Liska <mliska@suse.cz> - PR gcov-profile/85370 + PR gcov-profile/85370 * coverage.c (coverage_begin_function): Do not mark target - clones as artificial functions. + clones as artificial functions. 2018-07-31 Martin Liska <mliska@suse.cz> - PR gcov-profile/83813 - PR gcov-profile/84758 - PR gcov-profile/85217 - PR gcov-profile/85332 + PR gcov-profile/83813 + PR gcov-profile/84758 + PR gcov-profile/85217 + PR gcov-profile/85332 * profile.c (branch_prob): Do not record GOTO expressions - for GIMPLE statements which locations are already streamed. + for GIMPLE statements which locations are already streamed. 2018-07-31 Olivier Hainque <hainque@adacore.com> @@ -2297,7 +2417,7 @@ 2018-07-30 Ilya Leoshkevich <iii@linux.ibm.com> - PR target/86547 + PR target/86547 * lra-constraints.c (spill_hard_reg_in_range): When selecting the hard_regno, make sure no insn between `from` and `to` clobbers it. @@ -2398,9 +2518,9 @@ 2018-07-26 Martin Liska <mliska@suse.cz> - PR lto/86548 + PR lto/86548 * lto-wrapper.c: Add linker_output as prefix - for ltrans_output_file. + for ltrans_output_file. 2018-07-26 Segher Boessenkool <segher@kernel.crashing.org> @@ -2448,7 +2568,7 @@ 2018-07-25 Martin Liska <mliska@suse.cz> * config/powerpcspe/powerpcspe-protos.h (rs6000_loop_align): Fix - return type. + return type. 2018-07-25 Richard Biener <rguenther@suse.de> @@ -2464,22 +2584,22 @@ 2018-07-25 Martin Liska <mliska@suse.cz> - PR middle-end/86645 + PR middle-end/86645 * dumpfile.c: And excluded values with TDF_ALL_VALUES. * dumpfile.h (enum dump_flag): Defince TDF_ALL_VALUES. 2018-07-25 Martin Liska <mliska@suse.cz> - PR sanitizer/79635 + PR sanitizer/79635 * params.def: Explain ASan abbreviation and provide - a documentation link. + a documentation link. 2018-07-24 Martin Sebor <msebor@redhat.com> PR tree-optimization/86622 PR tree-optimization/86532 * builtins.h (string_length): Declare. - * builtins.c (c_strlen): Correct handling of non-constant offsets. + * builtins.c (c_strlen): Correct handling of non-constant offsets. (check_access): Be prepared for non-constant length ranges. (string_length): Make extern. * expr.c (string_constant): Only handle the minor non-constant @@ -2654,7 +2774,7 @@ to unsigned_char_type_node for strcmp/strncmp, add conversions to the two operands. (inline_expand_builtin_string_cmp): Delete the last parameter, give up - the inlining expansion on target where the type of the call has same or + the inlining expansion on target where the type of the call has same or narrower precision than unsigned char. 2018-07-20 David Malcolm <dmalcolm@redhat.com> @@ -2980,8 +3100,8 @@ 2018-07-18 Kugan Vivekanandarajah <kuganv@linaro.org> PR middle-end/86544 - * tree-ssa-phiopt.c (cond_removal_in_popcount_pattern): Handle comparision with EQ_EXPR - in last stmt. + * tree-ssa-phiopt.c (cond_removal_in_popcount_pattern): Handle + comparision with EQ_EXPR in last stmt. 2018-07-18 Kelvin Nilsen <kelvin@gcc.gnu.org> @@ -3081,7 +3201,7 @@ 2018-07-17 Martin Liska <mliska@suse.cz> * config/i386/att.h (ASM_OUTPUT_ALIGN): Fix spacing - in order to fulfil coding style. + in order to fulfil coding style. * config/i386/cygming.h (ASM_OUTPUT_ALIGN): Likewise. * config/i386/gas.h (ASM_OUTPUT_MAX_SKIP_ALIGN): Likewise. * config/i386/x86-64.h (ASM_OUTPUT_MAX_SKIP_PAD): Likewise. @@ -3095,11 +3215,12 @@ 2018-07-17 Martin Liska <mliska@suse.cz> * align.h: New file. - * config/alpha/alpha.c (alpha_align_insns_1): Use align_functions directly. + * config/alpha/alpha.c (alpha_align_insns_1): Use align_functions + directly. * config/i386/i386.c (ix86_avoid_jump_mispredicts): Use new return type align_flags of label_to_alignment. - * config/m32r/m32r.h (LOOP_ALIGN): Wrap returned values into align_flags - class. + * config/m32r/m32r.h (LOOP_ALIGN): Wrap returned values into + align_flags class. * config/m68k/m68k.c: Do not use removed align_labels_value and align_loops_value. * config/nds32/nds32.h (JUMP_ALIGN): Wrap result into align_flags class. @@ -3117,11 +3238,11 @@ (rs6000_loop_align_max_skip): Remove. * config/rx/rx.h (JUMP_ALIGN): Wrap integer values * config/rx/rx-protos.h (rx_align_for_label): Make it - static function. + static function. * config/rx/rx.c (rx_align_for_label): Change return type - to align_flags. + to align_flags. (rx_max_skip_for_label): Remove TARGET_ASM_*_ALIGN_MAX_SKIP - macro definitions. + macro definitions. into align_flags class. (LABEL_ALIGN): Likewise. (LOOP_ALIGN): Likewise. @@ -3144,7 +3265,7 @@ * coretypes.h: Include align.h header file. * doc/tm.texi: Remove TARGET_ASM_JUMP_ALIGN_MAX_SKIP, TARGET_ASM_LOOP_ALIGN_MAX_SKIP, TARGET_ASM_LABEL_ALIGN_MAX_SKIP - and TARGET_ASM_LABEL_ALIGN_AFTER_BARRIER_MAX_SKIP macros. + and TARGET_ASM_LABEL_ALIGN_AFTER_BARRIER_MAX_SKIP macros. * doc/tm.texi.in: Likewise. * final.c (struct label_alignment): Remove not used structure. (LABEL_ALIGN): Change type to align_flags. @@ -3286,9 +3407,9 @@ 2018-07-16 Martin Liska <mliska@suse.cz> - PR ipa/86529 + PR ipa/86529 * ipa-pure-const.c (malloc_candidate_p): Revert ::get - to ::get_create. + to ::get_create. 2017-07-16 Claudiu Zissulescu <claziss@synopsys.com> @@ -3337,19 +3458,19 @@ 2018-07-16 Aldy Hernandez <aldyh@redhat.com> - * fold-const.c (int_const_binop_1): Abstract... - (wide_int_binop): ...wide int code here. + * fold-const.c (int_const_binop_1): Abstract... + (wide_int_binop): ...wide int code here. (poly_int_binop): ...poly int code here. Abstract the rest of int_const_binop_1 into int_const_binop. - * fold-const.h (wide_int_binop): New. - * tree-vrp.c (vrp_int_const_binop): Call wide_int_binop. + * fold-const.h (wide_int_binop): New. + * tree-vrp.c (vrp_int_const_binop): Call wide_int_binop. Remove useless PLUS/MINUS_EXPR case. - (zero_nonzero_bits_from_vr): Move wide int code... - (zero_nonzero_bits_from_bounds): ...here. - (extract_range_from_binary_expr_1): Move mask optimization code... - (range_easy_mask_min_max): ...here. - * tree-vrp.h (zero_nonzero_bits_from_bounds): New. - (range_easy_mask_min_max): New. + (zero_nonzero_bits_from_vr): Move wide int code... + (zero_nonzero_bits_from_bounds): ...here. + (extract_range_from_binary_expr_1): Move mask optimization code... + (range_easy_mask_min_max): ...here. + * tree-vrp.h (zero_nonzero_bits_from_bounds): New. + (range_easy_mask_min_max): New. 2018-07-15 Jeff Law <law@redhat.com> @@ -3441,14 +3562,14 @@ 2018-07-12 Kito Cheng <kito.cheng@gmail.com> - * config/riscv/riscv.c (enum riscv_privilege_levels): Add UNKNOWN_MODE. - (riscv_expand_epilogue): Add assertion to check interrupt mode. - (riscv_set_current_function): Extract getting interrupt type to new - function. - (riscv_get_interrupt_type): New function. - (riscv_merge_decl_attributes): New function, checking interrupt type is - same. - (TARGET_MERGE_DECL_ATTRIBUTES): Define. + * config/riscv/riscv.c (enum riscv_privilege_levels): Add UNKNOWN_MODE. + (riscv_expand_epilogue): Add assertion to check interrupt mode. + (riscv_set_current_function): Extract getting interrupt type to new + function. + (riscv_get_interrupt_type): New function. + (riscv_merge_decl_attributes): New function, checking interrupt type is + same. + (TARGET_MERGE_DECL_ATTRIBUTES): Define. 2018-07-12 Paul Koning <ni1d@arrl.net> @@ -3761,7 +3882,7 @@ 2018-07-11 Aldy Hernandez <aldyh@redhat.com> - * tree-ssa-threadupdate.c (thread_through_all_blocks): Do not jump + * tree-ssa-threadupdate.c (thread_through_all_blocks): Do not jump thread twice from the same starting edge. 2018-07-11 Aldy Hernandez <aldyh@redhat.com> @@ -4078,7 +4199,7 @@ 2018-07-04 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c: Define - max_ratio_for_speed and max_ratio_for_size constants. + max_ratio_for_speed and max_ratio_for_size constants. 2018-07-04 Denys Vlasenko <dvlasenk@redhat.com> Martin Liska <mliska@suse.cz> @@ -4124,13 +4245,13 @@ max skip conditionally. (ASM_OUTPUT_MAX_SKIP_PAD): Likewise. * config/ia64/ia64.c (ia64_option_override): Set default values - for alignment options. + for alignment options. * config/m68k/m68k.c: Handle new str_align_* options. * config/mips/mips.c (mips_set_compression_mode): Change type of constants. (mips_option_override): Set default values for options. * config/powerpcspe/powerpcspe.c (rs6000_option_override_internal): - Likewise. + Likewise. * config/rs6000/rs6000.c (rs6000_option_override_internal): Likewise. * config/rx/rx.c (rx_option_override): Likewise. @@ -4138,15 +4259,15 @@ (LABEL_ALIGN): Use align_labels_log. (LOOP_ALIGN): Use align_loops_align. * config/s390/s390.c (s390_asm_output_function_label): Use new - macros. + macros. * config/sh/sh.c (sh_override_options_after_change): Change type of constants. * config/spu/spu.c (spu_sched_init): Likewise. * config/sparc/sparc.c (sparc_option_override): Set default - values for options. + values for options. * config/visium/visium.c (visium_option_override): Likewise. * config/visium/visium.h (ASM_OUTPUT_MAX_SKIP_ALIGN): Do not - emit p2align format with last argument if it's not needed. + emit p2align format with last argument if it's not needed. * doc/invoke.texi: Document extended format of -falign-*. * final.c: Use align_labels alignment. * flags.h (struct target_flag_state): Change type to use @@ -4216,7 +4337,7 @@ * config/i386/x86-64.h (ASM_OUTPUT_MAX_SKIP_ALIGN): Likewise. 2018-07-04 Martin Liska <mliska@suse.cz> - Jonathan Wakely <jwakely@redhat.com> + Jonathan Wakely <jwakely@redhat.com> * coverage.c: Use correct type. * doc/invoke.texi: Language correction. @@ -4550,13 +4671,13 @@ 2018-07-02 Martin Liska <mliska@suse.cz> - PR ipa/86279 + PR ipa/86279 * ipa-pure-const.c (malloc_candidate_p): Revert usage of ::get. (propagate_nothrow): Likewise. 2018-07-02 Martin Liska <mliska@suse.cz> - PR ipa/86323 + PR ipa/86323 * ipa-inline.c (early_inliner): Revert wrongly added ::get call. 2018-07-02 David Malcolm <dmalcolm@redhat.com> @@ -4783,9 +4904,9 @@ 2018-06-29 Martin Liska <mliska@suse.cz> - PR tree-optimization/86263 + PR tree-optimization/86263 * tree-switch-conversion.c (switch_decision_tree::try_switch_expansion): - Make edge redirection. + Make edge redirection. 2018-06-29 David Malcolm <dmalcolm@redhat.com> @@ -4878,33 +4999,33 @@ 2018-06-28 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c (jump_table_cluster::can_be_handled): - Use newly introduced constants. + Use newly introduced constants. * tree-switch-conversion.h (struct jump_table_cluster): - Define max_ratio_for_size and max_ratio_for_speed. + Define max_ratio_for_size and max_ratio_for_speed. 2018-06-28 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c (jump_table_cluster::find_jump_tables): - Add new checking assert to catch invalid state. + Add new checking assert to catch invalid state. (jump_table_cluster::can_be_handled): Handle single case - clusters. + clusters. (jump_table_cluster::is_beneficial): Bail out for such case. (bit_test_cluster::find_bit_tests): - Add new checking assert to catch invalid state. + Add new checking assert to catch invalid state. (bit_test_cluster::can_be_handled): Handle single case - clusters. + clusters. (bit_test_cluster::is_beneficial): Bail out for such case. (switch_decision_tree::analyze_switch_statement): - Fix comment. + Fix comment. 2018-06-28 Martin Liska <mliska@suse.cz> * common.opt: Introduce -completion option. * gcc.c (driver_handle_option): Handle it. (driver::main): Print completions if completion - is set. + is set. * opt-suggestions.c (option_proposer::get_completions): - New function. + New function. (option_proposer::suggest_completion): Likewise. (option_proposer::find_param_completions): Likewise. (verify_autocompletions): Likewise. @@ -4918,7 +5039,7 @@ * opt-suggestions.h: Declare new functions. * opts.c (common_handle_option): Handle OPT__completion_. * selftest-run-tests.c (selftest::run_tests): Add - opt_proposer_c_tests. + opt_proposer_c_tests. * selftest.c (assert_str_startswith): New. * selftest.h (assert_str_startswith): Likewise. (opt_proposer_c_tests): New. @@ -5150,7 +5271,7 @@ * doc/invoke.texi (ARM Options): Document cortex-a76 and cortex-a76.cortex-a55. -2018-06-27 Tamar Christina <tamar.christina@arm.com> +2018-06-27 Tamar Christina <tamar.christina@arm.com> PR target/85769 * config/aarch64/aarch64.md (*movhf_aarch64): Add dup v0.4h pattern. @@ -5311,8 +5432,8 @@ 2018-06-26 Robin Dapp <rdapp@linux.vnet.ibm.com> - * config/s390/s390.h (enum processor_flags): Do not use - default tune parameter when -march was specified. + * config/s390/s390.h (enum processor_flags): Do not use + default tune parameter when -march was specified. 2018-06-26 Jakub Jelinek <jakub@redhat.com> @@ -5536,11 +5657,11 @@ 2018-06-22 Martin Liska <mliska@suse.cz> - PR tree-optimization/86263 + PR tree-optimization/86263 * tree-switch-conversion.c (jump_table_cluster::find_jump_tables): - Bail out if is_enabled is false. + Bail out if is_enabled is false. * tree-switch-conversion.h (jump_table_cluster::is_enabled): - New declaration. + New declaration. (jump_table_cluster::is_enabled): New function. 2018-06-22 Jan Hubicka <hubicka@ucw.cz> @@ -5560,9 +5681,9 @@ 2018-06-22 Martin Liska <mliska@suse.cz> * symbol-summary.h (get): Make it pure and inline move - functionality from ::get function. - (get): Remove and inline into ::get and ::get_create. - (get_create): Move code from ::get function. + functionality from ::get function. + (get): Remove and inline into ::get and ::get_create. + (get_create): Move code from ::get function. 2018-06-22 Rainer Orth <ro@CeBiTec.Uni-Bielefeld.DE> @@ -5616,7 +5737,7 @@ 2018-06-21 Martin Liska <mliska@suse.cz> * ipa-pure-const.c (propagate_nothrow): Use - funct_state_summaries->get. + funct_state_summaries->get. (dump_malloc_lattice): Likewise. (propagate_malloc): Likewise. @@ -5760,21 +5881,21 @@ 2018-06-20 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c (jump_table_cluster::can_be_handled): - Change default ratio from 10 to 8. + Change default ratio from 10 to 8. 2018-06-20 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c (jump_table_cluster::find_jump_tables): - New. + New. (bit_test_cluster::find_bit_tests): Likewise. (switch_decision_tree::analyze_switch_statement): Find clusters. * tree-switch-conversion.h (struct jump_table_cluster): Document - hierarchy. + hierarchy. 2018-06-20 Martin Liska <mliska@suse.cz> * tree-switch-conversion.c (switch_conversion::collect): - Record m_uniq property. + Record m_uniq property. (switch_conversion::expand): Bail out for special conditions. (group_cluster::~group_cluster): New. (group_cluster::group_cluster): Likewise. @@ -6011,9 +6132,9 @@ 2018-06-19 Martin Liska <mliska@suse.cz> * config/i386/i386.c (ix86_can_inline_p): Do not use - ipa_fn_summaries::get_create. + ipa_fn_summaries::get_create. * ipa-cp.c (ipcp_cloning_candidate_p): Replace get_create with - get. + get. (devirtualization_time_bonus): Likewise. (ipcp_propagate_stage): Likewise. * ipa-fnsummary.c (redirect_to_unreachable): Likewise. @@ -6027,13 +6148,13 @@ (ipa_fn_summary_t::remove): Rename to ... (ipa_fn_summary_t::remove_callees): ... this. (ipa_fn_summary_t::duplicate): Use placement new - instead of memory copy. + instead of memory copy. (ipa_call_summary_t::duplicate): Likewise. (ipa_call_summary_t::remove): Remove. (dump_ipa_call_summary): Change get_create to get. (ipa_dump_fn_summary): Dump only when summary exists. (analyze_function_body): Use symbol_summary::get instead - of get_create. + of get_create. (compute_fn_summary): Likewise. (estimate_edge_devirt_benefit): Likewise. (estimate_edge_size_and_time): Likewise. @@ -6047,7 +6168,7 @@ * ipa-fnsummary.h (struct GTY): Add new ctor and copy ctor. (struct ipa_call_summary): Likewise. * ipa-icf.c (sem_function::merge): Use symbol_summary::get instead - of get_create. + of get_create. * ipa-inline-analysis.c (do_estimate_edge_time): Likewise. (estimate_size_after_inlining): Likewise. (estimate_growth): Likewise. @@ -6780,7 +6901,7 @@ * config/i386/i386.opt: Make MPX-related options as Deprecated. * opt-functions.awk: Handle Deprecated flag. * opts-common.c (decode_cmdline_option): Handle cl_deprecated - and report error. + and report error. (read_cmdline_option): Report warning for a deprecated option. * opts.h (struct cl_option): Add new field cl_deprecated. (CL_ERR_DEPRECATED): New. @@ -6902,7 +7023,7 @@ * PR tree-optimization/86083 * tree-ssa-strlen.c (handle_char_store): Use tree_expr_nonzero_p. -2018-06-11 Zhouyi Zhou <zhouzhouyi@gmail.com> +2018-06-11 Zhouyi Zhou <zhouzhouyi@gmail.com> * tree-eh.c (lower_eh_constructs_2): Add a comma to comment. @@ -6915,7 +7036,7 @@ 2018-06-11 Martin Liska <mliska@suse.cz> - PR tree-optimization/86089 + PR tree-optimization/86089 * tree-ssa-strlen.c (get_string_length): Move back removed hunk. 2018-06-11 Julia Koval <julia.koval@intel.com> @@ -6947,12 +7068,12 @@ 2018-06-08 Martin Liska <mliska@suse.cz> * tree-cfg.h (debug_function): Fix argument type to match - implementation. + implementation. 2018-06-08 Martin Liska <mliska@suse.cz> * config/powerpcspe/powerpcspe.c (rs6000_xcoff_visibility): - Remove usage of MPX-related (and removed) fields. + Remove usage of MPX-related (and removed) fields. * config/rs6000/rs6000.c (rs6000_xcoff_visibility): Likewise. 2018-06-08 David Malcolm <dmalcolm@redhat.com> @@ -7046,7 +7167,7 @@ 2018-06-08 Martin Liska <mliska@suse.cz> * ipa-pure-const.c (propagate_pure_const): Use ::get at places - where we expect an existing summary. + where we expect an existing summary. 2018-06-08 Martin Liska <mliska@suse.cz> @@ -8264,7 +8385,7 @@ * omp-low.c (lower_omp_target): Avoid reference-type processing on pointers for firstprivate clause. -2018-05-31 Sameera Deshpande <sameera.deshpande@linaro.org> +2018-05-31 Sameera Deshpande <sameera.deshpande@linaro.org> * config/aarch64/aarch64-simd-builtins.def (ld1x3): New. (st1x2): Likewise. @@ -8385,7 +8506,7 @@ (expand_builtin_stpcpy): Call it, and call maybe_warn_nonstring_arg only if the former succeeds. -2018-05-31 Sameera Deshpande <sameera.deshpande@linaro.org> +2018-05-31 Sameera Deshpande <sameera.deshpande@linaro.org> * config/aarch64/aarch64-cores.def (saphira) : Add support for ARMv8.4 in saphira. @@ -11449,7 +11570,7 @@ * doc/invoke.texi (Developer Options): Document dump filename determination early. Document stdin/stdout selection. -2018-04-30 Andrew Sadek <andrew.sadek.se@gmail.com> +2018-04-30 Andrew Sadek <andrew.sadek.se@gmail.com> Microblaze Target: PIC data text relative @@ -13549,7 +13670,7 @@ (DIVDE): Use it. (DIVDEU): Likewise. -2018-03-28 Carl Love <cel@us.ibm.com> +2018-03-28 Carl Love <cel@us.ibm.com> Revert 2017-09-27 Carl Love <cel@us.ibm.com> @@ -18391,7 +18512,7 @@ Limit immediates. * config/aarch64/predicates.md (Uti): Add new constraint. -2018-01-17 Carl Love <cel@us.ibm.com> +2018-01-17 Carl Love <cel@us.ibm.com> * config/rs6000/vsx.md (define_expand xl_len_r, define_expand stxvl, define_expand *stxvl): Add match_dup argument. diff --git a/gcc/DATESTAMP b/gcc/DATESTAMP index e00be59..d8abe1f 100644 --- a/gcc/DATESTAMP +++ b/gcc/DATESTAMP @@ -1 +1 @@ -20180815 +20180816 diff --git a/gcc/builtins.c b/gcc/builtins.c index 867d153..6716aab 100644 --- a/gcc/builtins.c +++ b/gcc/builtins.c @@ -4481,11 +4481,16 @@ expand_builtin_memcmp (tree exp, rtx target, bool result_eq) /*objsize=*/NULL_TREE); } + /* If the specified length exceeds the size of either object, + call the function. */ + if (!no_overflow) + return NULL_RTX; + /* Due to the performance benefit, always inline the calls first when result_eq is false. */ rtx result = NULL_RTX; - if (!result_eq && fcode != BUILT_IN_BCMP && no_overflow) + if (!result_eq && fcode != BUILT_IN_BCMP) { result = inline_expand_builtin_string_cmp (exp, target); if (result) diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog index 3aec883..d293d99 100644 --- a/gcc/c-family/ChangeLog +++ b/gcc/c-family/ChangeLog @@ -1,3 +1,25 @@ +2018-08-16 Nathan Sidwell <nathan@acm.org> + + * c-ada-spec.c (count_ada_macro): Use cpp_user_macro_p. + (store_ada_macro): Likewise. + * c-ppoutput.c (cb_used_define, dump_macro): Likewise. + * c-spellcheck.cc (should-suggest_as_macro_p): Likewise, + +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * c-format.c: Include "selftest-diagnostic.h" and + "gcc-rich-location.h". + (format_warning_at_char): Pass NULL for new label params of + format_warning_va. + (class indirection_suffix): New class. + (class range_label_for_format_type_mismatch): New class. + (format_type_warning): Move logic for generating "*" suffix to + class indirection_suffix. Create "fmt_label" and "param_label" + to show their types, and pass them to the + format_warning_at_substring calls. + (selftest::test_type_mismatch_range_labels): New test. + (selftest::c_format_c_tests): Call it. + 2018-08-13 Martin Sebor <msebor@redhat.com> PR tree-optimization/71625 diff --git a/gcc/c-family/c-format.c b/gcc/c-family/c-format.c index dc0e756..5a04f05 100644 --- a/gcc/c-family/c-format.c +++ b/gcc/c-family/c-format.c @@ -32,8 +32,10 @@ along with GCC; see the file COPYING3. If not see #include "diagnostic.h" #include "substring-locations.h" #include "selftest.h" +#include "selftest-diagnostic.h" #include "builtins.h" #include "attribs.h" +#include "gcc-rich-location.h" /* Handle attributes associated with format checking. */ @@ -97,8 +99,8 @@ format_warning_at_char (location_t fmt_string_loc, tree format_string_cst, substring_loc fmt_loc (fmt_string_loc, string_type, char_idx, char_idx, char_idx); - bool warned = format_warning_va (fmt_loc, UNKNOWN_LOCATION, NULL, opt, - gmsgid, &ap); + bool warned = format_warning_va (fmt_loc, NULL, UNKNOWN_LOCATION, NULL, + NULL, opt, gmsgid, &ap); va_end (ap); return warned; @@ -3510,6 +3512,82 @@ get_corrected_substring (const substring_loc &fmt_loc, return result; } +/* Helper class for adding zero or more trailing '*' to types. + + The format type and name exclude any '*' for pointers, so those + must be formatted manually. For all the types we currently have, + this is adequate, but formats taking pointers to functions or + arrays would require the full type to be built up in order to + print it with %T. */ + +class indirection_suffix +{ + public: + indirection_suffix (int pointer_count) : m_pointer_count (pointer_count) {} + + /* Determine the size of the buffer (including NUL-terminator). */ + + size_t get_buffer_size () const + { + return m_pointer_count + 2; + } + + /* Write the '*' to DST and add a NUL-terminator. */ + + void fill_buffer (char *dst) const + { + if (m_pointer_count == 0) + dst[0] = 0; + else if (c_dialect_cxx ()) + { + memset (dst, '*', m_pointer_count); + dst[m_pointer_count] = 0; + } + else + { + dst[0] = ' '; + memset (dst + 1, '*', m_pointer_count); + dst[m_pointer_count + 1] = 0; + } + } + + private: + int m_pointer_count; +}; + +/* Subclass of range_label for labelling the range in the format string + with the type in question, adding trailing '*' for pointer_count. */ + +class range_label_for_format_type_mismatch + : public range_label_for_type_mismatch +{ + public: + range_label_for_format_type_mismatch (tree labelled_type, tree other_type, + int pointer_count) + : range_label_for_type_mismatch (labelled_type, other_type), + m_pointer_count (pointer_count) + { + } + + label_text get_text () const FINAL OVERRIDE + { + label_text text = range_label_for_type_mismatch::get_text (); + if (text.m_buffer == NULL) + return text; + + indirection_suffix suffix (m_pointer_count); + char *p = (char *) alloca (suffix.get_buffer_size ()); + suffix.fill_buffer (p); + + char *result = concat (text.m_buffer, p, NULL); + text.maybe_free (); + return label_text (result, true); + } + + private: + int m_pointer_count; +}; + /* Give a warning about a format argument of different type from that expected. The range of the diagnostic is taken from WHOLE_FMT_LOC; the caret location is based on the location of the char at TYPE->offset_loc. @@ -3558,7 +3636,6 @@ format_type_warning (const substring_loc &whole_fmt_loc, int pointer_count = type->pointer_count; int arg_num = type->arg_num; - char *p; /* If ARG_TYPE is a typedef with a misleading name (for example, size_t but not the standard size_t expected by printf %zu), avoid printing the typedef name. */ @@ -3570,25 +3647,10 @@ format_type_warning (const substring_loc &whole_fmt_loc, && !strcmp (wanted_type_name, lang_hooks.decl_printable_name (TYPE_NAME (arg_type), 2))) arg_type = TYPE_MAIN_VARIANT (arg_type); - /* The format type and name exclude any '*' for pointers, so those - must be formatted manually. For all the types we currently have, - this is adequate, but formats taking pointers to functions or - arrays would require the full type to be built up in order to - print it with %T. */ - p = (char *) alloca (pointer_count + 2); - if (pointer_count == 0) - p[0] = 0; - else if (c_dialect_cxx ()) - { - memset (p, '*', pointer_count); - p[pointer_count] = 0; - } - else - { - p[0] = ' '; - memset (p + 1, '*', pointer_count); - p[pointer_count + 1] = 0; - } + + indirection_suffix suffix (pointer_count); + char *p = (char *) alloca (suffix.get_buffer_size ()); + suffix.fill_buffer (p); /* WHOLE_FMT_LOC has the caret at the end of the range. Set the caret to be at the offset from TYPE. Subtract one @@ -3596,6 +3658,10 @@ format_type_warning (const substring_loc &whole_fmt_loc, substring_loc fmt_loc (whole_fmt_loc); fmt_loc.set_caret_index (type->offset_loc - 1); + range_label_for_format_type_mismatch fmt_label (wanted_type, arg_type, + pointer_count); + range_label_for_type_mismatch param_label (arg_type, wanted_type); + /* Get a string for use as a replacement fix-it hint for the range in fmt_loc, or NULL. */ char *corrected_substring @@ -3606,7 +3672,7 @@ format_type_warning (const substring_loc &whole_fmt_loc, { if (arg_type) format_warning_at_substring - (fmt_loc, param_loc, + (fmt_loc, &fmt_label, param_loc, ¶m_label, corrected_substring, OPT_Wformat_, "%s %<%s%.*s%> expects argument of type %<%s%s%>, " "but argument %d has type %qT", @@ -3616,7 +3682,7 @@ format_type_warning (const substring_loc &whole_fmt_loc, wanted_type_name, p, arg_num, arg_type); else format_warning_at_substring - (fmt_loc, param_loc, + (fmt_loc, &fmt_label, param_loc, ¶m_label, corrected_substring, OPT_Wformat_, "%s %<%s%.*s%> expects a matching %<%s%s%> argument", gettext (kind_descriptions[kind]), @@ -3627,7 +3693,7 @@ format_type_warning (const substring_loc &whole_fmt_loc, { if (arg_type) format_warning_at_substring - (fmt_loc, param_loc, + (fmt_loc, &fmt_label, param_loc, ¶m_label, corrected_substring, OPT_Wformat_, "%s %<%s%.*s%> expects argument of type %<%T%s%>, " "but argument %d has type %qT", @@ -3637,7 +3703,7 @@ format_type_warning (const substring_loc &whole_fmt_loc, wanted_type, p, arg_num, arg_type); else format_warning_at_substring - (fmt_loc, param_loc, + (fmt_loc, &fmt_label, param_loc, ¶m_label, corrected_substring, OPT_Wformat_, "%s %<%s%.*s%> expects a matching %<%T%s%> argument", gettext (kind_descriptions[kind]), @@ -4217,6 +4283,66 @@ test_get_format_for_type_scanf () #undef ASSERT_FORMAT_FOR_TYPE_STREQ +/* Exercise the type-printing label code, to give some coverage + under "make selftest-valgrind" (in particular, to ensure that + the label-printing machinery doesn't leak). */ + +static void +test_type_mismatch_range_labels () +{ + /* Create a tempfile and write some text to it. + ....................0000000001 11111111 12 22222222 + ....................1234567890 12345678 90 12345678. */ + const char *content = " printf (\"msg: %i\\n\", msg);\n"; + temp_source_file tmp (SELFTEST_LOCATION, ".c", content); + line_table_test ltt; + + linemap_add (line_table, LC_ENTER, false, tmp.get_filename (), 1); + + location_t c17 = linemap_position_for_column (line_table, 17); + ASSERT_EQ (LOCATION_COLUMN (c17), 17); + location_t c18 = linemap_position_for_column (line_table, 18); + location_t c24 = linemap_position_for_column (line_table, 24); + location_t c26 = linemap_position_for_column (line_table, 26); + + /* Don't attempt to run the tests if column data might be unavailable. */ + if (c26 > LINE_MAP_MAX_LOCATION_WITH_COLS) + return; + + location_t fmt = make_location (c18, c17, c18); + ASSERT_EQ (LOCATION_COLUMN (fmt), 18); + + location_t param = make_location (c24, c24, c26); + ASSERT_EQ (LOCATION_COLUMN (param), 24); + + range_label_for_format_type_mismatch fmt_label (char_type_node, + integer_type_node, 1); + range_label_for_type_mismatch param_label (integer_type_node, + char_type_node); + gcc_rich_location richloc (fmt, &fmt_label); + richloc.add_range (param, false, ¶m_label); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + if (c_dialect_cxx ()) + /* "char*", without a space. */ + ASSERT_STREQ ("\n" + " printf (\"msg: %i\\n\", msg);\n" + " ~^ ~~~\n" + " | |\n" + " char* int\n", + pp_formatted_text (dc.printer)); + else + /* "char *", with a space. */ + ASSERT_STREQ ("\n" + " printf (\"msg: %i\\n\", msg);\n" + " ~^ ~~~\n" + " | |\n" + " | int\n" + " char *\n", + pp_formatted_text (dc.printer)); +} + /* Run all of the selftests within this file. */ void @@ -4225,6 +4351,7 @@ c_format_c_tests () test_get_modifier_for_format_len (); test_get_format_for_type_printf (); test_get_format_for_type_scanf (); + test_type_mismatch_range_labels (); } } // namespace selftest diff --git a/gcc/c-family/c-ppoutput.c b/gcc/c-family/c-ppoutput.c index 5b630b6..8187280 100644 --- a/gcc/c-family/c-ppoutput.c +++ b/gcc/c-family/c-ppoutput.c @@ -689,7 +689,6 @@ cb_def_pragma (cpp_reader *pfile, source_location line) static int dump_macro (cpp_reader *pfile, cpp_hashnode *node, void *v ATTRIBUTE_UNUSED) { - /* asserts are distinguished by beginning with '#'. */ if (cpp_user_macro_p (node)) { fputs ("#define ", print.outf); diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 5931206..7bde11c 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,19 @@ +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * c-objc-common.c: Include "gcc-rich-location.h". + (c_tree_printer): Move implemenation of '%T' to... + (print_type): ...this new function. + (range_label_for_type_mismatch::get_text): New function. + * c-typeck.c (convert_for_assignment): Add type labels to the rhs + range for the various ic_argpass cases. + (class maybe_range_label_for_tree_type_mismatch): New class. + (build_binary_op): Use it when calling binary_op_error. + +2018-08-15 Prathamesh Kulkarni <prathamesh.kulkarni@linaro.org> + + * c-decl.c (start_decl): Do not warn if variables is named as main + and is a local variable. + 2018-08-15 Iain Sandoe <iain@sandoe.co.uk> PR c/19315 diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index da42add..1bbccdd 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -4700,7 +4700,8 @@ start_decl (struct c_declarator *declarator, struct c_declspecs *declspecs, if (expr) add_stmt (fold_convert (void_type_node, expr)); - if (TREE_CODE (decl) != FUNCTION_DECL && MAIN_NAME_P (DECL_NAME (decl))) + if (TREE_CODE (decl) != FUNCTION_DECL && MAIN_NAME_P (DECL_NAME (decl)) + && TREE_PUBLIC (decl)) warning (OPT_Wmain, "%q+D is usually a function", decl); if (initialized) diff --git a/gcc/c/c-objc-common.c b/gcc/c/c-objc-common.c index ddbd60c..238af19 100644 --- a/gcc/c/c-objc-common.c +++ b/gcc/c/c-objc-common.c @@ -27,6 +27,7 @@ along with GCC; see the file COPYING3. If not see #include "gimple-pretty-print.h" #include "langhooks.h" #include "c-objc-common.h" +#include "gcc-rich-location.h" static bool c_tree_printer (pretty_printer *, text_info *, const char *, int, bool, bool, bool, bool *, const char **); @@ -61,6 +62,60 @@ c_objc_common_init (void) return c_common_init (); } +/* Print T to CPP. */ + +static void +print_type (c_pretty_printer *cpp, tree t, bool *quoted) +{ + gcc_assert (TYPE_P (t)); + struct obstack *ob = pp_buffer (cpp)->obstack; + char *p = (char *) obstack_base (ob); + /* Remember the end of the initial dump. */ + int len = obstack_object_size (ob); + + tree name = TYPE_NAME (t); + if (name && TREE_CODE (name) == TYPE_DECL && DECL_NAME (name)) + pp_identifier (cpp, lang_hooks.decl_printable_name (name, 2)); + else + cpp->type_id (t); + + /* If we're printing a type that involves typedefs, also print the + stripped version. But sometimes the stripped version looks + exactly the same, so we don't want it after all. To avoid + printing it in that case, we play ugly obstack games. */ + if (TYPE_CANONICAL (t) && t != TYPE_CANONICAL (t)) + { + c_pretty_printer cpp2; + /* Print the stripped version into a temporary printer. */ + cpp2.type_id (TYPE_CANONICAL (t)); + struct obstack *ob2 = cpp2.buffer->obstack; + /* Get the stripped version from the temporary printer. */ + const char *aka = (char *) obstack_base (ob2); + int aka_len = obstack_object_size (ob2); + int type1_len = obstack_object_size (ob) - len; + + /* If they are identical, bail out. */ + if (aka_len == type1_len && memcmp (p + len, aka, aka_len) == 0) + return; + + /* They're not, print the stripped version now. */ + if (*quoted) + pp_end_quote (cpp, pp_show_color (cpp)); + pp_c_whitespace (cpp); + pp_left_brace (cpp); + pp_c_ws_string (cpp, _("aka")); + pp_c_whitespace (cpp); + if (*quoted) + pp_begin_quote (cpp, pp_show_color (cpp)); + cpp->type_id (TYPE_CANONICAL (t)); + if (*quoted) + pp_end_quote (cpp, pp_show_color (cpp)); + pp_right_brace (cpp); + /* No further closing quotes are needed. */ + *quoted = false; + } +} + /* Called during diagnostic message formatting process to print a source-level entity onto BUFFER. The meaning of the format specifiers is as follows: @@ -82,7 +137,6 @@ c_tree_printer (pretty_printer *pp, text_info *text, const char *spec, bool *quoted, const char **) { tree t = NULL_TREE; - tree name; // FIXME: the next cast should be a dynamic_cast, when it is permitted. c_pretty_printer *cpp = (c_pretty_printer *) pp; pp->padding = pp_none; @@ -133,56 +187,8 @@ c_tree_printer (pretty_printer *pp, text_info *text, const char *spec, break; case 'T': - { - gcc_assert (TYPE_P (t)); - struct obstack *ob = pp_buffer (cpp)->obstack; - char *p = (char *) obstack_base (ob); - /* Remember the end of the initial dump. */ - int len = obstack_object_size (ob); - - name = TYPE_NAME (t); - if (name && TREE_CODE (name) == TYPE_DECL && DECL_NAME (name)) - pp_identifier (cpp, lang_hooks.decl_printable_name (name, 2)); - else - cpp->type_id (t); - - /* If we're printing a type that involves typedefs, also print the - stripped version. But sometimes the stripped version looks - exactly the same, so we don't want it after all. To avoid - printing it in that case, we play ugly obstack games. */ - if (TYPE_CANONICAL (t) && t != TYPE_CANONICAL (t)) - { - c_pretty_printer cpp2; - /* Print the stripped version into a temporary printer. */ - cpp2.type_id (TYPE_CANONICAL (t)); - struct obstack *ob2 = cpp2.buffer->obstack; - /* Get the stripped version from the temporary printer. */ - const char *aka = (char *) obstack_base (ob2); - int aka_len = obstack_object_size (ob2); - int type1_len = obstack_object_size (ob) - len; - - /* If they are identical, bail out. */ - if (aka_len == type1_len && memcmp (p + len, aka, aka_len) == 0) - return true; - - /* They're not, print the stripped version now. */ - if (*quoted) - pp_end_quote (pp, pp_show_color (pp)); - pp_c_whitespace (cpp); - pp_left_brace (cpp); - pp_c_ws_string (cpp, _("aka")); - pp_c_whitespace (cpp); - if (*quoted) - pp_begin_quote (pp, pp_show_color (pp)); - cpp->type_id (TYPE_CANONICAL (t)); - if (*quoted) - pp_end_quote (pp, pp_show_color (pp)); - pp_right_brace (cpp); - /* No further closing quotes are needed. */ - *quoted = false; - } - return true; - } + print_type (cpp, t, quoted); + return true; case 'E': if (TREE_CODE (t) == IDENTIFIER_NODE) @@ -207,6 +213,22 @@ c_tree_printer (pretty_printer *pp, text_info *text, const char *spec, return true; } +/* C-specific implementation of range_label::get_text () vfunc for + range_label_for_type_mismatch. */ + +label_text +range_label_for_type_mismatch::get_text () const +{ + if (m_labelled_type == NULL_TREE) + return label_text (NULL, false); + + c_pretty_printer cpp; + bool quoted = false; + print_type (&cpp, m_labelled_type, "ed); + return label_text (xstrdup (pp_formatted_text (&cpp)), true); +} + + /* In C and ObjC, all decls have "C" linkage. */ bool has_c_linkage (const_tree decl ATTRIBUTE_UNUSED) diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c index 2e9338e..726ea83 100644 --- a/gcc/c/c-typeck.c +++ b/gcc/c/c-typeck.c @@ -6924,13 +6924,15 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, switch (errtype) { case ic_argpass: - if (pedwarn (expr_loc, OPT_Wpointer_sign, - "pointer targets in passing argument %d of " - "%qE differ in signedness", parmnum, rname)) - inform ((fundecl && !DECL_IS_BUILTIN (fundecl)) - ? DECL_SOURCE_LOCATION (fundecl) : expr_loc, - "expected %qT but argument is of type %qT", - type, rhstype); + { + range_label_for_type_mismatch rhs_label (rhstype, type); + gcc_rich_location richloc (expr_loc, &rhs_label); + if (pedwarn (&richloc, OPT_Wpointer_sign, + "pointer targets in passing argument %d of " + "%qE differ in signedness", parmnum, rname)) + inform_for_arg (fundecl, expr_loc, parmnum, type, + rhstype); + } break; case ic_assign: pedwarn (location, OPT_Wpointer_sign, @@ -6981,10 +6983,14 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, switch (errtype) { case ic_argpass: - if (pedwarn (expr_loc, OPT_Wincompatible_pointer_types, - "passing argument %d of %qE from incompatible " - "pointer type", parmnum, rname)) - inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + { + range_label_for_type_mismatch rhs_label (rhstype, type); + gcc_rich_location richloc (expr_loc, &rhs_label); + if (pedwarn (&richloc, OPT_Wincompatible_pointer_types, + "passing argument %d of %qE from incompatible " + "pointer type", parmnum, rname)) + inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + } break; case ic_assign: pedwarn (location, OPT_Wincompatible_pointer_types, @@ -7024,10 +7030,14 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, switch (errtype) { case ic_argpass: - if (pedwarn (expr_loc, OPT_Wint_conversion, - "passing argument %d of %qE makes pointer from " - "integer without a cast", parmnum, rname)) - inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + { + range_label_for_type_mismatch rhs_label (rhstype, type); + gcc_rich_location richloc (expr_loc, &rhs_label); + if (pedwarn (&richloc, OPT_Wint_conversion, + "passing argument %d of %qE makes pointer from " + "integer without a cast", parmnum, rname)) + inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + } break; case ic_assign: pedwarn (location, OPT_Wint_conversion, @@ -7055,10 +7065,14 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, switch (errtype) { case ic_argpass: - if (pedwarn (expr_loc, OPT_Wint_conversion, - "passing argument %d of %qE makes integer from " - "pointer without a cast", parmnum, rname)) - inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + { + range_label_for_type_mismatch rhs_label (rhstype, type); + gcc_rich_location richloc (expr_loc, &rhs_label); + if (pedwarn (&richloc, OPT_Wint_conversion, + "passing argument %d of %qE makes integer from " + "pointer without a cast", parmnum, rname)) + inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + } break; case ic_assign: pedwarn (location, OPT_Wint_conversion, @@ -7094,9 +7108,13 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type, switch (errtype) { case ic_argpass: - error_at (expr_loc, "incompatible type for argument %d of %qE", parmnum, - rname); - inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + { + range_label_for_type_mismatch rhs_label (rhstype, type); + gcc_rich_location richloc (expr_loc, &rhs_label); + error_at (&richloc, "incompatible type for argument %d of %qE", parmnum, + rname); + inform_for_arg (fundecl, expr_loc, parmnum, type, rhstype); + } break; case ic_assign: error_at (location, "incompatible types when assigning to type %qT from " @@ -10992,6 +11010,38 @@ build_vec_cmp (tree_code code, tree type, return build3 (VEC_COND_EXPR, type, cmp, minus_one_vec, zero_vec); } +/* Subclass of range_label for labelling the type of EXPR when reporting + a type mismatch between EXPR and OTHER_EXPR. + Either or both of EXPR and OTHER_EXPR could be NULL. */ + +class maybe_range_label_for_tree_type_mismatch : public range_label +{ + public: + maybe_range_label_for_tree_type_mismatch (tree expr, tree other_expr) + : m_expr (expr), m_other_expr (other_expr) + { + } + + label_text get_text () const FINAL OVERRIDE + { + if (m_expr == NULL_TREE + || !EXPR_P (m_expr)) + return label_text (NULL, false); + tree expr_type = TREE_TYPE (m_expr); + + tree other_type = NULL_TREE; + if (m_other_expr && EXPR_P (m_other_expr)) + other_type = TREE_TYPE (m_other_expr); + + range_label_for_type_mismatch inner (expr_type, other_type); + return inner.get_text (); + } + + private: + tree m_expr; + tree m_other_expr; +}; + /* Build a binary-operation expression without default conversions. CODE is the kind of expression to build. LOCATION is the operator's location. @@ -11864,8 +11914,11 @@ build_binary_op (location_t location, enum tree_code code, || !vector_types_compatible_elements_p (type0, type1))) { gcc_rich_location richloc (location); - richloc.maybe_add_expr (orig_op0); - richloc.maybe_add_expr (orig_op1); + maybe_range_label_for_tree_type_mismatch + label_for_op0 (orig_op0, orig_op1), + label_for_op1 (orig_op1, orig_op0); + richloc.maybe_add_expr (orig_op0, &label_for_op0); + richloc.maybe_add_expr (orig_op1, &label_for_op1); binary_op_error (&richloc, code, type0, type1); return error_mark_node; } @@ -12106,8 +12159,11 @@ build_binary_op (location_t location, enum tree_code code, if (!result_type) { gcc_rich_location richloc (location); - richloc.maybe_add_expr (orig_op0); - richloc.maybe_add_expr (orig_op1); + maybe_range_label_for_tree_type_mismatch + label_for_op0 (orig_op0, orig_op1), + label_for_op1 (orig_op1, orig_op0); + richloc.maybe_add_expr (orig_op0, &label_for_op0); + richloc.maybe_add_expr (orig_op1, &label_for_op1); binary_op_error (&richloc, code, TREE_TYPE (op0), TREE_TYPE (op1)); return error_mark_node; } diff --git a/gcc/common.opt b/gcc/common.opt index b2f2215..507291f 100644 --- a/gcc/common.opt +++ b/gcc/common.opt @@ -1233,6 +1233,10 @@ fdiagnostics-show-caret Common Var(flag_diagnostics_show_caret) Init(1) Show the source line with a caret indicating the column. +fdiagnostics-show-labels +Common Var(flag_diagnostics_show_labels) Init(1) +Show labels annotating ranges of source code when showing source + fdiagnostics-show-line-numbers Common Var(flag_diagnostics_show_line_numbers) Init(1) Show line numbers in the left margin when showing source diff --git a/gcc/config/aarch64/aarch64-builtins.c b/gcc/config/aarch64/aarch64-builtins.c index 02c6738..8cced94 100644 --- a/gcc/config/aarch64/aarch64-builtins.c +++ b/gcc/config/aarch64/aarch64-builtins.c @@ -643,6 +643,10 @@ aarch64_init_simd_builtin_types (void) /* Poly types are a world of their own. */ aarch64_simd_types[Poly8_t].eltype = aarch64_simd_types[Poly8_t].itype = build_distinct_type_copy (unsigned_intQI_type_node); + /* Prevent front-ends from transforming Poly8_t arrays into string + literals. */ + TYPE_STRING_FLAG (aarch64_simd_types[Poly8_t].eltype) = false; + aarch64_simd_types[Poly16_t].eltype = aarch64_simd_types[Poly16_t].itype = build_distinct_type_copy (unsigned_intHI_type_node); aarch64_simd_types[Poly64_t].eltype = aarch64_simd_types[Poly64_t].itype = diff --git a/gcc/config/aarch64/aarch64.opt b/gcc/config/aarch64/aarch64.opt index bc9b22a..c8e8204 100644 --- a/gcc/config/aarch64/aarch64.opt +++ b/gcc/config/aarch64/aarch64.opt @@ -167,20 +167,20 @@ EnumValue Enum(aarch64_ra_sign_scope_t) String(all) Value(AARCH64_FUNCTION_ALL) mlow-precision-recip-sqrt -Common Var(flag_mrecip_low_precision_sqrt) Optimization +Target Var(flag_mrecip_low_precision_sqrt) Optimization Enable the reciprocal square root approximation. Enabling this reduces precision of reciprocal square root results to about 16 bits for single precision and to 32 bits for double precision. mlow-precision-sqrt -Common Var(flag_mlow_precision_sqrt) Optimization +Target Var(flag_mlow_precision_sqrt) Optimization Enable the square root approximation. Enabling this reduces precision of square root results to about 16 bits for single precision and to 32 bits for double precision. If enabled, it implies -mlow-precision-recip-sqrt. mlow-precision-div -Common Var(flag_mlow_precision_div) Optimization +Target Var(flag_mlow_precision_div) Optimization Enable the division approximation. Enabling this reduces precision of division results to about 16 bits for single precision and to 32 bits for double precision. @@ -212,7 +212,7 @@ Target RejectNegative Joined Enum(sve_vector_bits) Var(aarch64_sve_vector_bits) -msve-vector-bits=N Set the number of bits in an SVE vector register to N. mverbose-cost-dump -Common Undocumented Var(flag_aarch64_verbose_cost) +Target Undocumented Var(flag_aarch64_verbose_cost) Enables verbose cost model dumping in the debug dump files. mtrack-speculation diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c index f5eece4..1d97db5 100644 --- a/gcc/config/arm/arm.c +++ b/gcc/config/arm/arm.c @@ -31509,8 +31509,8 @@ arm_can_change_mode_class (machine_mode from, machine_mode to, { if (TARGET_BIG_END && !(GET_MODE_SIZE (from) == 16 && GET_MODE_SIZE (to) == 8) - && (GET_MODE_UNIT_SIZE (from) > UNITS_PER_WORD - || GET_MODE_UNIT_SIZE (to) > UNITS_PER_WORD) + && (GET_MODE_SIZE (from) > UNITS_PER_WORD + || GET_MODE_SIZE (to) > UNITS_PER_WORD) && reg_classes_intersect_p (VFP_REGS, rclass)) return false; return true; diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md index 1646b21..5aeee4b 100644 --- a/gcc/config/arm/neon.md +++ b/gcc/config/arm/neon.md @@ -25,9 +25,9 @@ (define_insn "*neon_mov<mode>" [(set (match_operand:VDX 0 "nonimmediate_operand" - "=w,Un,w, w, ?r,?w,?r,?r, ?Us") + "=w,Un,w, w, ?r,?w,?r, ?Us") (match_operand:VDX 1 "general_operand" - " w,w, Dn,Uni, w, r, r, Usi,r"))] + " w,w, Dn,Uni, w, r, Usi,r"))] "TARGET_NEON && (register_operand (operands[0], <MODE>mode) || register_operand (operands[1], <MODE>mode))" @@ -61,12 +61,12 @@ } } [(set_attr "type" "neon_move<q>,neon_store1_1reg,neon_move<q>,\ - neon_load1_1reg, neon_to_gp<q>,neon_from_gp<q>,mov_reg,\ + neon_load1_1reg, neon_to_gp<q>,neon_from_gp<q>,\ neon_load1_2reg, neon_store1_2reg") - (set_attr "length" "4,4,4,4,4,4,8,8,8") - (set_attr "arm_pool_range" "*,*,*,1020,*,*,*,1020,*") - (set_attr "thumb2_pool_range" "*,*,*,1018,*,*,*,1018,*") - (set_attr "neg_pool_range" "*,*,*,1004,*,*,*,1004,*")]) + (set_attr "length" "4,4,4,4,4,4,8,8") + (set_attr "arm_pool_range" "*,*,*,1020,*,*,1020,*") + (set_attr "thumb2_pool_range" "*,*,*,1018,*,*,1018,*") + (set_attr "neg_pool_range" "*,*,*,1004,*,*,1004,*")]) (define_insn "*neon_mov<mode>" [(set (match_operand:VQXMOV 0 "nonimmediate_operand" @@ -113,6 +113,13 @@ (set_attr "thumb2_pool_range" "*,*,*,1018,*,*,*,1018,*") (set_attr "neg_pool_range" "*,*,*,996,*,*,*,996,*")]) +/* We define these mov expanders to match the standard mov$a optab to prevent + the mid-end from trying to do a subreg for these modes which is the most + inefficient way to expand the move. Also big-endian subreg's aren't + allowed for a subset of modes, See TARGET_CAN_CHANGE_MODE_CLASS. + Without these RTL generation patterns the mid-end would attempt to take a + sub-reg and may ICE if it can't. */ + (define_expand "movti" [(set (match_operand:TI 0 "nonimmediate_operand" "") (match_operand:TI 1 "general_operand" ""))] @@ -137,33 +144,15 @@ } }) -(define_expand "movv4hf" - [(set (match_operand:V4HF 0 "s_register_operand") - (match_operand:V4HF 1 "s_register_operand"))] - "TARGET_NEON && TARGET_FP16" +(define_expand "mov<mode>" + [(set (match_operand:VH 0 "s_register_operand") + (match_operand:VH 1 "s_register_operand"))] + "TARGET_NEON" { - /* We need to use force_reg to avoid TARGET_CAN_CHANGE_MODE_CLASS - causing an ICE on big-endian because it cannot extract subregs in - this case. */ - if (can_create_pseudo_p ()) - { - if (!REG_P (operands[0])) - operands[1] = force_reg (V4HFmode, operands[1]); - } -}) - -(define_expand "movv8hf" - [(set (match_operand:V8HF 0 "") - (match_operand:V8HF 1 ""))] - "TARGET_NEON && TARGET_FP16" -{ - /* We need to use force_reg to avoid TARGET_CAN_CHANGE_MODE_CLASS - causing an ICE on big-endian because it cannot extract subregs in - this case. */ if (can_create_pseudo_p ()) { if (!REG_P (operands[0])) - operands[1] = force_reg (V8HFmode, operands[1]); + operands[1] = force_reg (<MODE>mode, operands[1]); } }) diff --git a/gcc/config/i386/emmintrin.h b/gcc/config/i386/emmintrin.h index 6501638..7a6ff80 100644 --- a/gcc/config/i386/emmintrin.h +++ b/gcc/config/i386/emmintrin.h @@ -113,7 +113,7 @@ _mm_setzero_pd (void) extern __inline __m128d __attribute__((__gnu_inline__, __always_inline__, __artificial__)) _mm_move_sd (__m128d __A, __m128d __B) { - return __extension__ (__m128d) __builtin_shuffle((__v2df)__A, (__v2df)__B, (__v2di){2, 1}); + return __extension__ (__m128d) __builtin_shuffle ((__v2df)__A, (__v2df)__B, (__v2di){2, 1}); } /* Load two DPFP values from P. The address must be 16-byte aligned. */ diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 15a3caa..3548de2 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -75,7 +75,6 @@ along with GCC; see the file COPYING3. If not see #include "tree-iterator.h" #include "dbgcnt.h" #include "case-cfn-macros.h" -#include "regrename.h" #include "dojump.h" #include "fold-const-call.h" #include "tree-vrp.h" @@ -3135,15 +3134,6 @@ ix86_debug_options (void) return; } -/* Return true if T is one of the bytes we should avoid with - -mmitigate-rop. */ - -static bool -ix86_rop_should_change_byte_p (int t) -{ - return t == 0xc2 || t == 0xc3 || t == 0xca || t == 0xcb; -} - static const char *stringop_alg_names[] = { #define DEF_ENUM #define DEF_ALG(alg, name) #name, @@ -29110,98 +29100,6 @@ ix86_instantiate_decls (void) instantiate_decl_rtl (s->rtl); } -/* Return the number used for encoding REG, in the range 0..7. */ - -static int -reg_encoded_number (rtx reg) -{ - unsigned regno = REGNO (reg); - switch (regno) - { - case AX_REG: - return 0; - case CX_REG: - return 1; - case DX_REG: - return 2; - case BX_REG: - return 3; - case SP_REG: - return 4; - case BP_REG: - return 5; - case SI_REG: - return 6; - case DI_REG: - return 7; - default: - break; - } - if (IN_RANGE (regno, FIRST_STACK_REG, LAST_STACK_REG)) - return regno - FIRST_STACK_REG; - if (IN_RANGE (regno, FIRST_SSE_REG, LAST_SSE_REG)) - return regno - FIRST_SSE_REG; - if (IN_RANGE (regno, FIRST_MMX_REG, LAST_MMX_REG)) - return regno - FIRST_MMX_REG; - if (IN_RANGE (regno, FIRST_REX_SSE_REG, LAST_REX_SSE_REG)) - return regno - FIRST_REX_SSE_REG; - if (IN_RANGE (regno, FIRST_REX_INT_REG, LAST_REX_INT_REG)) - return regno - FIRST_REX_INT_REG; - if (IN_RANGE (regno, FIRST_MASK_REG, LAST_MASK_REG)) - return regno - FIRST_MASK_REG; - return -1; -} - -/* Given an insn INSN with NOPERANDS OPERANDS, return the modr/m byte used - in its encoding if it could be relevant for ROP mitigation, otherwise - return -1. If POPNO0 and POPNO1 are nonnull, store the operand numbers - used for calculating it into them. */ - -static int -ix86_get_modrm_for_rop (rtx_insn *insn, rtx *operands, int noperands, - int *popno0 = 0, int *popno1 = 0) -{ - if (asm_noperands (PATTERN (insn)) >= 0) - return -1; - int has_modrm = get_attr_modrm (insn); - if (!has_modrm) - return -1; - enum attr_modrm_class cls = get_attr_modrm_class (insn); - rtx op0, op1; - switch (cls) - { - case MODRM_CLASS_OP02: - gcc_assert (noperands >= 3); - if (popno0) - { - *popno0 = 0; - *popno1 = 2; - } - op0 = operands[0]; - op1 = operands[2]; - break; - case MODRM_CLASS_OP01: - gcc_assert (noperands >= 2); - if (popno0) - { - *popno0 = 0; - *popno1 = 1; - } - op0 = operands[0]; - op1 = operands[1]; - break; - default: - return -1; - } - if (REG_P (op0) && REG_P (op1)) - { - int enc0 = reg_encoded_number (op0); - int enc1 = reg_encoded_number (op1); - return 0xc0 + (enc1 << 3) + enc0; - } - return -1; -} - /* Check whether x86 address PARTS is a pc-relative address. */ bool @@ -42215,215 +42113,6 @@ ix86_seh_fixup_eh_fallthru (void) } } -/* Given a register number BASE, the lowest of a group of registers, update - regsets IN and OUT with the registers that should be avoided in input - and output operands respectively when trying to avoid generating a modr/m - byte for -mmitigate-rop. */ - -static void -set_rop_modrm_reg_bits (int base, HARD_REG_SET &in, HARD_REG_SET &out) -{ - SET_HARD_REG_BIT (out, base); - SET_HARD_REG_BIT (out, base + 1); - SET_HARD_REG_BIT (in, base + 2); - SET_HARD_REG_BIT (in, base + 3); -} - -/* Called if -mmitigate-rop is in effect. Try to rewrite instructions so - that certain encodings of modr/m bytes do not occur. */ -static void -ix86_mitigate_rop (void) -{ - HARD_REG_SET input_risky; - HARD_REG_SET output_risky; - HARD_REG_SET inout_risky; - - CLEAR_HARD_REG_SET (output_risky); - CLEAR_HARD_REG_SET (input_risky); - SET_HARD_REG_BIT (output_risky, AX_REG); - SET_HARD_REG_BIT (output_risky, CX_REG); - SET_HARD_REG_BIT (input_risky, BX_REG); - SET_HARD_REG_BIT (input_risky, DX_REG); - set_rop_modrm_reg_bits (FIRST_SSE_REG, input_risky, output_risky); - set_rop_modrm_reg_bits (FIRST_REX_INT_REG, input_risky, output_risky); - set_rop_modrm_reg_bits (FIRST_REX_SSE_REG, input_risky, output_risky); - set_rop_modrm_reg_bits (FIRST_EXT_REX_SSE_REG, input_risky, output_risky); - set_rop_modrm_reg_bits (FIRST_MASK_REG, input_risky, output_risky); - COPY_HARD_REG_SET (inout_risky, input_risky); - IOR_HARD_REG_SET (inout_risky, output_risky); - - df_note_add_problem (); - /* Fix up what stack-regs did. */ - df_insn_rescan_all (); - df_analyze (); - - regrename_init (true); - regrename_analyze (NULL); - - auto_vec<du_head_p> cands; - - for (rtx_insn *insn = get_insns (); insn; insn = NEXT_INSN (insn)) - { - if (!NONDEBUG_INSN_P (insn)) - continue; - - if (GET_CODE (PATTERN (insn)) == USE - || GET_CODE (PATTERN (insn)) == CLOBBER) - continue; - - extract_insn (insn); - - int opno0, opno1; - int modrm = ix86_get_modrm_for_rop (insn, recog_data.operand, - recog_data.n_operands, &opno0, - &opno1); - - if (!ix86_rop_should_change_byte_p (modrm)) - continue; - - insn_rr_info *info = &insn_rr[INSN_UID (insn)]; - - /* This happens when regrename has to fail a block. */ - if (!info->op_info) - continue; - - if (info->op_info[opno0].n_chains != 0) - { - gcc_assert (info->op_info[opno0].n_chains == 1); - du_head_p op0c; - op0c = regrename_chain_from_id (info->op_info[opno0].heads[0]->id); - if (op0c->target_data_1 + op0c->target_data_2 == 0 - && !op0c->cannot_rename) - cands.safe_push (op0c); - - op0c->target_data_1++; - } - if (info->op_info[opno1].n_chains != 0) - { - gcc_assert (info->op_info[opno1].n_chains == 1); - du_head_p op1c; - op1c = regrename_chain_from_id (info->op_info[opno1].heads[0]->id); - if (op1c->target_data_1 + op1c->target_data_2 == 0 - && !op1c->cannot_rename) - cands.safe_push (op1c); - - op1c->target_data_2++; - } - } - - int i; - du_head_p head; - FOR_EACH_VEC_ELT (cands, i, head) - { - int old_reg, best_reg; - HARD_REG_SET unavailable; - - CLEAR_HARD_REG_SET (unavailable); - if (head->target_data_1) - IOR_HARD_REG_SET (unavailable, output_risky); - if (head->target_data_2) - IOR_HARD_REG_SET (unavailable, input_risky); - - int n_uses; - reg_class superclass = regrename_find_superclass (head, &n_uses, - &unavailable); - old_reg = head->regno; - best_reg = find_rename_reg (head, superclass, &unavailable, - old_reg, false); - bool ok = regrename_do_replace (head, best_reg); - gcc_assert (ok); - if (dump_file) - fprintf (dump_file, "Chain %d renamed as %s in %s\n", head->id, - reg_names[best_reg], reg_class_names[superclass]); - - } - - regrename_finish (); - - df_analyze (); - - basic_block bb; - regset_head live; - - INIT_REG_SET (&live); - - FOR_EACH_BB_FN (bb, cfun) - { - rtx_insn *insn; - - COPY_REG_SET (&live, DF_LR_OUT (bb)); - df_simulate_initialize_backwards (bb, &live); - - FOR_BB_INSNS_REVERSE (bb, insn) - { - if (!NONDEBUG_INSN_P (insn)) - continue; - - df_simulate_one_insn_backwards (bb, insn, &live); - - if (GET_CODE (PATTERN (insn)) == USE - || GET_CODE (PATTERN (insn)) == CLOBBER) - continue; - - extract_insn (insn); - constrain_operands_cached (insn, reload_completed); - int opno0, opno1; - int modrm = ix86_get_modrm_for_rop (insn, recog_data.operand, - recog_data.n_operands, &opno0, - &opno1); - if (modrm < 0 - || !ix86_rop_should_change_byte_p (modrm) - || opno0 == opno1) - continue; - - rtx oldreg = recog_data.operand[opno1]; - preprocess_constraints (insn); - const operand_alternative *alt = which_op_alt (); - - int i; - for (i = 0; i < recog_data.n_operands; i++) - if (i != opno1 - && alt[i].earlyclobber - && reg_overlap_mentioned_p (recog_data.operand[i], - oldreg)) - break; - - if (i < recog_data.n_operands) - continue; - - if (dump_file) - fprintf (dump_file, - "attempting to fix modrm byte in insn %d:" - " reg %d class %s", INSN_UID (insn), REGNO (oldreg), - reg_class_names[alt[opno1].cl]); - - HARD_REG_SET unavailable; - REG_SET_TO_HARD_REG_SET (unavailable, &live); - SET_HARD_REG_BIT (unavailable, REGNO (oldreg)); - IOR_COMPL_HARD_REG_SET (unavailable, call_used_reg_set); - IOR_HARD_REG_SET (unavailable, fixed_reg_set); - IOR_HARD_REG_SET (unavailable, output_risky); - IOR_COMPL_HARD_REG_SET (unavailable, - reg_class_contents[alt[opno1].cl]); - - for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) - if (!TEST_HARD_REG_BIT (unavailable, i)) - break; - if (i == FIRST_PSEUDO_REGISTER) - { - if (dump_file) - fprintf (dump_file, ", none available\n"); - continue; - } - if (dump_file) - fprintf (dump_file, " -> %d\n", i); - rtx newreg = gen_rtx_REG (recog_data.operand_mode[opno1], i); - validate_change (insn, recog_data.operand_loc[opno1], newreg, false); - insn = emit_insn_before (gen_move_insn (newreg, oldreg), insn); - } - } -} - /* Implement machine specific optimizations. We implement padding of returns for K8 CPUs and pass to avoid 4 jumps in the single 16 byte window. */ static void @@ -42433,9 +42122,6 @@ ix86_reorg (void) with old MDEP_REORGS that are not CFG based. Recompute it now. */ compute_bb_for_insn (); - if (flag_mitigate_rop) - ix86_mitigate_rop (); - if (TARGET_SEH && current_function_has_exception_handlers ()) ix86_seh_fixup_eh_fallthru (); @@ -46157,9 +45843,8 @@ expand_vec_perm_movs (struct expand_vec_perm_d *d) if (d->one_operand_p) return false; - if (TARGET_SSE2 && (vmode == V2DFmode || vmode == V4SFmode)) - ; - else + if (!(TARGET_SSE && vmode == V4SFmode) + && !(TARGET_SSE2 && vmode == V2DFmode)) return false; /* Only the first element is changed. */ diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 10783d3..918241d 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -663,19 +663,6 @@ ] (const_int 1))) -(define_attr "modrm_class" "none,incdec,op0,op01,op02,pushpop,unknown" - (cond [(eq_attr "modrm" "0") - (const_string "none") - (eq_attr "type" "alu,imul,ishift") - (const_string "op02") - (eq_attr "type" "imov,imovx,lea,alu1,icmp") - (const_string "op01") - (eq_attr "type" "incdec") - (const_string "incdec") - (eq_attr "type" "push,pop") - (const_string "pushpop")] - (const_string "unknown"))) - ;; The (bounding maximum) length of an instruction in bytes. ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences. ;; Later we may want to split them and compute proper length as for @@ -1299,7 +1286,6 @@ ktest<mskmodesuffix>\t%0, %0" [(set_attr "type" "test,icmp,msklog") (set_attr "length_immediate" "0,1,*") - (set_attr "modrm_class" "op0,unknown,*") (set_attr "prefix" "*,*,vex") (set_attr "mode" "<MODE>")]) @@ -1313,7 +1299,6 @@ cmp{<imodesuffix>}\t{%1, %0|%0, %1}" [(set_attr "type" "test,icmp") (set_attr "length_immediate" "0,1") - (set_attr "modrm_class" "op0,unknown") (set_attr "mode" "<MODE>")]) (define_insn "*cmp<mode>_1" @@ -2028,7 +2013,6 @@ "reload_completed" "xor{l}\t%k0, %k0" [(set_attr "type" "alu1") - (set_attr "modrm_class" "op0") (set_attr "mode" "SI") (set_attr "length_immediate" "0")]) @@ -2913,7 +2897,6 @@ "reload_completed" "xor{<imodesuffix>}\t%0, %0" [(set_attr "type" "alu1") - (set_attr "modrm_class" "op0") (set_attr "mode" "<MODE>") (set_attr "length_immediate" "0")]) @@ -13585,7 +13568,6 @@ "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" @@ -18214,7 +18196,6 @@ "" "sbb{<imodesuffix>}\t%0, %0" [(set_attr "type" "alu1") - (set_attr "modrm_class" "op0") (set_attr "use_carry" "1") (set_attr "pent_pair" "pu") (set_attr "mode" "<MODE>") @@ -18230,7 +18211,6 @@ "" "sbb{<imodesuffix>}\t%0, %0" [(set_attr "type" "alu1") - (set_attr "modrm_class" "op0") (set_attr "use_carry" "1") (set_attr "pent_pair" "pu") (set_attr "mode" "<MODE>") @@ -18244,7 +18224,6 @@ "" "sbb{<imodesuffix>}\t%0, %0" [(set_attr "type" "alu1") - (set_attr "modrm_class" "op0") (set_attr "use_carry" "1") (set_attr "pent_pair" "pu") (set_attr "mode" "<MODE>") diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index a34d4ac..3724994 100644 --- a/gcc/config/i386/i386.opt +++ b/gcc/config/i386/i386.opt @@ -842,7 +842,7 @@ Target Report Mask(ISA_CLWB) Var(ix86_isa_flags) Save Support CLWB instruction. mpcommit -Target Undocumented Warn(%<-mpcommit%> was deprecated) +Target Ignore Warn(%qs was deprecated) ;; Deprecated mfxsr @@ -999,8 +999,8 @@ Target RejectNegative Joined Integer Var(ix86_stack_protector_guard_symbol_str) Use the given symbol for addressing the stack-protector guard. mmitigate-rop -Target Var(flag_mitigate_rop) -Attempt to avoid generating instruction sequences containing ret bytes. +Target Ignore Warn(%qs was deprecated) +;; Deprecated mgeneral-regs-only Target Report RejectNegative Mask(GENERAL_REGS_ONLY) Var(ix86_target_flags) Save diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c index aa707b2..97b922f 100644 --- a/gcc/config/rs6000/rs6000.c +++ b/gcc/config/rs6000/rs6000.c @@ -15122,7 +15122,6 @@ fold_mergehl_helper (gimple_stmt_iterator *gsi, gimple *stmt, int use_high) tree arg1 = gimple_call_arg (stmt, 1); tree lhs = gimple_call_lhs (stmt); tree lhs_type = TREE_TYPE (lhs); - tree lhs_type_type = TREE_TYPE (lhs_type); int n_elts = TYPE_VECTOR_SUBPARTS (lhs_type); int midpoint = n_elts / 2; int offset = 0; @@ -15130,12 +15129,29 @@ fold_mergehl_helper (gimple_stmt_iterator *gsi, gimple *stmt, int use_high) if (use_high == 1) offset = midpoint; - tree_vector_builder elts (lhs_type, VECTOR_CST_NELTS (arg0), 1); + /* The permute_type will match the lhs for integral types. For double and + float types, the permute type needs to map to the V2 or V4 type that + matches size. */ + tree permute_type; + if (INTEGRAL_TYPE_P (TREE_TYPE (lhs_type))) + permute_type = lhs_type; + else + { + if (TREE_TYPE (lhs_type) == TREE_TYPE (V2DF_type_node)) + permute_type = V2DI_type_node; + else if (TREE_TYPE (lhs_type) == TREE_TYPE (V4SF_type_node)) + permute_type = V4SI_type_node; + else + gcc_unreachable (); + } + tree_vector_builder elts (permute_type, VECTOR_CST_NELTS (arg0), 1); for (int i = 0; i < midpoint; i++) { - elts.safe_push (build_int_cst (lhs_type_type, offset + i)); - elts.safe_push (build_int_cst (lhs_type_type, offset + n_elts + i)); + elts.safe_push (build_int_cst (TREE_TYPE (permute_type), + offset + i)); + elts.safe_push (build_int_cst (TREE_TYPE (permute_type), + offset + n_elts + i)); } tree permute = elts.build (); @@ -15760,6 +15776,8 @@ rs6000_gimple_fold_builtin (gimple_stmt_iterator *gsi) case VSX_BUILTIN_XXMRGLW_4SI: case ALTIVEC_BUILTIN_VMRGLB: case VSX_BUILTIN_VEC_MERGEL_V2DI: + case VSX_BUILTIN_XXMRGLW_4SF: + case VSX_BUILTIN_VEC_MERGEL_V2DF: fold_mergehl_helper (gsi, stmt, 1); return true; /* vec_mergeh (integrals). */ @@ -15768,6 +15786,8 @@ rs6000_gimple_fold_builtin (gimple_stmt_iterator *gsi) case VSX_BUILTIN_XXMRGHW_4SI: case ALTIVEC_BUILTIN_VMRGHB: case VSX_BUILTIN_VEC_MERGEH_V2DI: + case VSX_BUILTIN_XXMRGHW_4SF: + case VSX_BUILTIN_VEC_MERGEH_V2DF: fold_mergehl_helper (gsi, stmt, 0); return true; diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 8e12371..0b69590 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,15 @@ +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * call.c: Include "gcc-rich-location.h". + (convert_like_real): Add range label for "invalid conversion" + diagnostic. + (perform_implicit_conversion_flags): Add type label to the + "could not convert" error. + * error.c: Include "gcc-rich-location.h". + (range_label_for_type_mismatch::get_text): New function. + * typeck.c (convert_for_assignment): Add type label to + the "cannot convert" error if a location is available. + 2018-08-15 Paolo Carlini <paolo.carlini@oracle.com> * decl.c (check_previous_goto_1): When decl_jump_unsafe returns 2 diff --git a/gcc/cp/call.c b/gcc/cp/call.c index 62654a9..16bb6bf 100644 --- a/gcc/cp/call.c +++ b/gcc/cp/call.c @@ -41,6 +41,7 @@ along with GCC; see the file COPYING3. If not see #include "internal-fn.h" #include "stringpool.h" #include "attribs.h" +#include "gcc-rich-location.h" /* The various kinds of conversion. */ @@ -6748,8 +6749,13 @@ convert_like_real (conversion *convs, tree expr, tree fn, int argnum, break; } if (!complained) - complained = permerror (loc, "invalid conversion from %qH to %qI", - TREE_TYPE (expr), totype); + { + range_label_for_type_mismatch label (TREE_TYPE (expr), totype); + gcc_rich_location richloc (loc, &label); + complained = permerror (&richloc, + "invalid conversion from %qH to %qI", + TREE_TYPE (expr), totype); + } if (complained && fn) inform (get_fndecl_argument_location (fn, argnum), " initializing argument %P of %qD", argnum, fn); @@ -10755,8 +10761,12 @@ perform_implicit_conversion_flags (tree type, tree expr, else if (invalid_nonstatic_memfn_p (loc, expr, complain)) /* We gave an error. */; else - error_at (loc, "could not convert %qE from %qH to %qI", expr, - TREE_TYPE (expr), type); + { + range_label_for_type_mismatch label (TREE_TYPE (expr), type); + gcc_rich_location rich_loc (loc, &label); + error_at (&rich_loc, "could not convert %qE from %qH to %qI", + expr, TREE_TYPE (expr), type); + } } expr = error_mark_node; } diff --git a/gcc/cp/error.c b/gcc/cp/error.c index cb8d932..4a2d2f6 100644 --- a/gcc/cp/error.c +++ b/gcc/cp/error.c @@ -31,6 +31,7 @@ along with GCC; see the file COPYING3. If not see #include "c-family/c-objc.h" #include "ubsan.h" #include "internal-fn.h" +#include "gcc-rich-location.h" #define pp_separate_with_comma(PP) pp_cxx_separate_with (PP, ',') #define pp_separate_with_semicolon(PP) pp_cxx_separate_with (PP, ';') @@ -4279,3 +4280,30 @@ qualified_name_lookup_error (tree scope, tree name, suggest_alternatives_for (location, name, true); } } + +/* C++-specific implementation of range_label::get_text () vfunc for + range_label_for_type_mismatch. + + Compare with print_template_differences above. */ + +label_text +range_label_for_type_mismatch::get_text () const +{ + if (m_labelled_type == NULL_TREE) + return label_text (NULL, false); + + const bool verbose = false; + const bool show_color = false; + + const char *result; + if (m_other_type + && comparable_template_types_p (m_labelled_type, m_other_type)) + result = type_to_string_with_compare (m_labelled_type, m_other_type, + verbose, show_color); + else + result = type_to_string (m_labelled_type, verbose, true, NULL, show_color); + + /* Both of the above return GC-allocated buffers, so the caller mustn't + free them. */ + return label_text (const_cast <char *> (result), false); +} diff --git a/gcc/cp/typeck.c b/gcc/cp/typeck.c index 1335da5..64b3d58 100644 --- a/gcc/cp/typeck.c +++ b/gcc/cp/typeck.c @@ -8805,7 +8805,16 @@ convert_for_assignment (tree type, tree rhs, } else if (fndecl) { - error_at (cp_expr_loc_or_loc (rhs, input_location), + location_t loc = cp_expr_location (rhs); + range_label_for_type_mismatch rhs_label (rhstype, type); + range_label *label = &rhs_label; + if (loc == UNKNOWN_LOCATION) + { + loc = input_location; + label = NULL; + } + gcc_rich_location richloc (loc, label); + error_at (&richloc, "cannot convert %qH to %qI", rhstype, type); inform (get_fndecl_argument_location (fndecl, parmnum), diff --git a/gcc/diagnostic-show-locus.c b/gcc/diagnostic-show-locus.c index 238c689..c9edaab 100644 --- a/gcc/diagnostic-show-locus.c +++ b/gcc/diagnostic-show-locus.c @@ -127,7 +127,8 @@ class layout_range layout_range (const expanded_location *start_exploc, const expanded_location *finish_exploc, bool show_caret_p, - const expanded_location *caret_exploc); + const expanded_location *caret_exploc, + const range_label *label); bool contains_point (linenum_type row, int column) const; bool intersects_line_p (linenum_type row) const; @@ -136,6 +137,7 @@ class layout_range layout_point m_finish; bool m_show_caret_p; layout_point m_caret; + const range_label *m_label; }; /* A struct for use by layout::print_source_line for telling @@ -253,6 +255,7 @@ class layout bool should_print_annotation_line_p (linenum_type row) const; void start_annotation_line () const; void print_annotation_line (linenum_type row, const line_bounds lbounds); + void print_any_labels (linenum_type row); void print_trailing_fixits (linenum_type row); bool annotation_line_showed_range_p (linenum_type line, int start_column, @@ -287,6 +290,7 @@ class layout expanded_location m_exploc; colorizer m_colorizer; bool m_colorize_source_p; + bool m_show_labels_p; bool m_show_line_numbers_p; auto_vec <layout_range> m_layout_ranges; auto_vec <const fixit_hint *> m_fixit_hints; @@ -408,11 +412,13 @@ colorizer::get_color_by_name (const char *name) layout_range::layout_range (const expanded_location *start_exploc, const expanded_location *finish_exploc, bool show_caret_p, - const expanded_location *caret_exploc) + const expanded_location *caret_exploc, + const range_label *label) : m_start (*start_exploc), m_finish (*finish_exploc), m_show_caret_p (show_caret_p), - m_caret (*caret_exploc) + m_caret (*caret_exploc), + m_label (label) { } @@ -539,7 +545,7 @@ make_range (int start_line, int start_col, int end_line, int end_col) const expanded_location finish_exploc = {"test.c", end_line, end_col, NULL, false}; return layout_range (&start_exploc, &finish_exploc, false, - &start_exploc); + &start_exploc, NULL); } /* Selftests for layout_range::contains_point and @@ -879,6 +885,7 @@ layout::layout (diagnostic_context * context, m_exploc (richloc->get_expanded_location (0)), m_colorizer (context, diagnostic_kind), m_colorize_source_p (context->colorize_source_p), + m_show_labels_p (context->show_labels_p), m_show_line_numbers_p (context->show_line_numbers_p), m_layout_ranges (richloc->get_num_locations ()), m_fixit_hints (richloc->get_num_fixit_hints ()), @@ -989,7 +996,8 @@ layout::maybe_add_location_range (const location_range *loc_range, /* Everything is now known to be in the correct source file, but it may require further sanitization. */ - layout_range ri (&start, &finish, loc_range->m_show_caret_p, &caret); + layout_range ri (&start, &finish, loc_range->m_show_caret_p, &caret, + loc_range->m_label); /* If we have a range that finishes before it starts (perhaps from something built via macro expansion), printing the @@ -1379,6 +1387,180 @@ layout::print_annotation_line (linenum_type row, const line_bounds lbounds) print_newline (); } +/* Implementation detail of layout::print_any_labels. + + A label within the given row of source. */ + +struct line_label +{ + line_label (int state_idx, int column, label_text text) + : m_state_idx (state_idx), m_column (column), + m_text (text), m_length (strlen (text.m_buffer)), + m_label_line (0) + {} + + /* Sorting is primarily by column, then by state index. */ + static int comparator (const void *p1, const void *p2) + { + const line_label *ll1 = (const line_label *)p1; + const line_label *ll2 = (const line_label *)p2; + int column_cmp = compare (ll1->m_column, ll2->m_column); + if (column_cmp) + return column_cmp; + return compare (ll1->m_state_idx, ll2->m_state_idx); + } + + int m_state_idx; + int m_column; + label_text m_text; + size_t m_length; + int m_label_line; +}; + +/* Print any labels in this row. */ +void +layout::print_any_labels (linenum_type row) +{ + int i; + auto_vec<line_label> labels; + + /* Gather the labels that are to be printed into "labels". */ + { + layout_range *range; + FOR_EACH_VEC_ELT (m_layout_ranges, i, range) + { + /* Most ranges don't have labels, so reject this first. */ + if (range->m_label == NULL) + continue; + + /* The range's caret must be on this line. */ + if (range->m_caret.m_line != row) + continue; + + /* Reject labels that aren't fully visible due to clipping + by m_x_offset. */ + if (range->m_caret.m_column <= m_x_offset) + continue; + + label_text text; + text = range->m_label->get_text (); + + /* Allow for labels that return NULL from their get_text + implementation (so e.g. such labels can control their own + visibility). */ + if (text.m_buffer == NULL) + continue; + + labels.safe_push (line_label (i, range->m_caret.m_column, text)); + } + } + + /* Bail out if there are no labels on this row. */ + if (labels.length () == 0) + return; + + /* Sort them. */ + labels.qsort(line_label::comparator); + + /* Figure out how many "label lines" we need, and which + one each label is printed in. + + For example, if the labels aren't too densely packed, + we can fit them on the same line, giving two "label lines": + + foo + bar + ~~~ ~~~ + | | : label line 0 + l0 l1 : label line 1 + + If they would touch each other or overlap, then we need + additional "label lines": + + foo + bar + ~~~ ~~~ + | | : label line 0 + | label 1 : label line 1 + label 0 : label line 2 + + Place the final label on label line 1, and work backwards, adding + label lines as needed. + + If multiple labels are at the same place, put them on separate + label lines: + + foo + bar + ^ : label line 0 + | : label line 1 + label 1 : label line 2 + label 0 : label line 3. */ + + int max_label_line = 1; + { + int next_column = INT_MAX; + line_label *label; + FOR_EACH_VEC_ELT_REVERSE (labels, i, label) + { + /* Would this label "touch" or overlap the next label? */ + if (label->m_column + label->m_length >= (size_t)next_column) + max_label_line++; + + label->m_label_line = max_label_line; + next_column = label->m_column; + } + } + + /* Print the "label lines". For each label within the line, print + either a vertical bar ('|') for the labels that are lower down, or the + labels themselves once we've reached their line. */ + { + /* Keep track of in which column we last printed a vertical bar. + This allows us to suppress duplicate vertical bars for the case + where multiple labels are on one column. */ + int last_vbar = 0; + for (int label_line = 0; label_line <= max_label_line; label_line++) + { + start_annotation_line (); + pp_space (m_pp); + int column = 1 + m_x_offset; + line_label *label; + FOR_EACH_VEC_ELT (labels, i, label) + { + if (label_line > label->m_label_line) + /* We've printed all the labels for this label line. */ + break; + + if (label_line == label->m_label_line) + { + gcc_assert (column <= label->m_column); + move_to_column (&column, label->m_column, true); + m_colorizer.set_range (label->m_state_idx); + pp_string (m_pp, label->m_text.m_buffer); + m_colorizer.set_normal_text (); + column += label->m_length; + } + else if (label->m_column != last_vbar) + { + gcc_assert (column <= label->m_column); + move_to_column (&column, label->m_column, true); + m_colorizer.set_range (label->m_state_idx); + pp_character (m_pp, '|'); + m_colorizer.set_normal_text (); + last_vbar = column; + column++; + } + } + print_newline (); + } + } + + /* Clean up. */ + { + line_label *label; + FOR_EACH_VEC_ELT (labels, i, label) + label->m_text.maybe_free (); + } +} + /* If there are any fixit hints inserting new lines before source line ROW, print them. @@ -2023,6 +2205,8 @@ layout::print_line (linenum_type row) print_source_line (row, line.get_buffer (), line.length (), &lbounds); if (should_print_annotation_line_p (row)) print_annotation_line (row, lbounds); + if (m_show_labels_p) + print_any_labels (row); print_trailing_fixits (row); } @@ -2429,6 +2613,157 @@ test_one_liner_many_fixits_2 () pp_formatted_text (dc.printer)); } +/* Test of labeling the ranges within a rich_location. */ + +static void +test_one_liner_labels () +{ + location_t foo + = make_location (linemap_position_for_column (line_table, 1), + linemap_position_for_column (line_table, 1), + linemap_position_for_column (line_table, 3)); + location_t bar + = make_location (linemap_position_for_column (line_table, 7), + linemap_position_for_column (line_table, 7), + linemap_position_for_column (line_table, 9)); + location_t field + = make_location (linemap_position_for_column (line_table, 11), + linemap_position_for_column (line_table, 11), + linemap_position_for_column (line_table, 15)); + + /* Example where all the labels fit on one line. */ + { + text_range_label label0 ("0"); + text_range_label label1 ("1"); + text_range_label label2 ("2"); + gcc_rich_location richloc (foo, &label0); + richloc.add_range (bar, false, &label1); + richloc.add_range (field, false, &label2); + + { + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~ ~~~ ~~~~~\n" + " | | |\n" + " 0 1 2\n", + pp_formatted_text (dc.printer)); + } + + /* Verify that we can disable label-printing. */ + { + test_diagnostic_context dc; + dc.show_labels_p = false; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~ ~~~ ~~~~~\n", + pp_formatted_text (dc.printer)); + } + } + + /* Example where the labels need extra lines. */ + { + text_range_label label0 ("label 0"); + text_range_label label1 ("label 1"); + text_range_label label2 ("label 2"); + gcc_rich_location richloc (foo, &label0); + richloc.add_range (bar, false, &label1); + richloc.add_range (field, false, &label2); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~ ~~~ ~~~~~\n" + " | | |\n" + " | | label 2\n" + " | label 1\n" + " label 0\n", + pp_formatted_text (dc.printer)); + } + + /* Example of boundary conditions: label 0 and 1 have just enough clearance, + but label 1 just touches label 2. */ + { + text_range_label label0 ("aaaaa"); + text_range_label label1 ("bbbb"); + text_range_label label2 ("c"); + gcc_rich_location richloc (foo, &label0); + richloc.add_range (bar, false, &label1); + richloc.add_range (field, false, &label2); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~ ~~~ ~~~~~\n" + " | | |\n" + " | | c\n" + " aaaaa bbbb\n", + pp_formatted_text (dc.printer)); + } + + /* Example of out-of-order ranges (thus requiring a sort). */ + { + text_range_label label0 ("0"); + text_range_label label1 ("1"); + text_range_label label2 ("2"); + gcc_rich_location richloc (field, &label0); + richloc.add_range (bar, false, &label1); + richloc.add_range (foo, false, &label2); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ~~~ ~~~ ^~~~~\n" + " | | |\n" + " 2 1 0\n", + pp_formatted_text (dc.printer)); + } + + /* Ensure we don't ICE if multiple ranges with labels are on + the same point. */ + { + text_range_label label0 ("label 0"); + text_range_label label1 ("label 1"); + text_range_label label2 ("label 2"); + gcc_rich_location richloc (bar, &label0); + richloc.add_range (bar, false, &label1); + richloc.add_range (bar, false, &label2); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~\n" + " |\n" + " label 2\n" + " label 1\n" + " label 0\n", + pp_formatted_text (dc.printer)); + } + + /* Verify that a NULL result from range_label::get_text is + handled gracefully. */ + { + text_range_label label (NULL); + gcc_rich_location richloc (bar, &label); + + test_diagnostic_context dc; + diagnostic_show_locus (&dc, &richloc, DK_ERROR); + ASSERT_STREQ ("\n" + " foo = bar.field;\n" + " ^~~\n", + pp_formatted_text (dc.printer)); + } + + /* TODO: example of formatted printing (needs to be in + gcc-rich-location.c due to Makefile.in issues). */ +} + /* Run the various one-liner tests. */ static void @@ -2465,6 +2800,7 @@ test_diagnostic_show_locus_one_liner (const line_table_case &case_) test_one_liner_fixit_validation_adhoc_locations (); test_one_liner_many_fixits_1 (); test_one_liner_many_fixits_2 (); + test_one_liner_labels (); } /* Verify that gcc_rich_location::add_location_if_nearby works. */ diff --git a/gcc/diagnostic.c b/gcc/diagnostic.c index e9d93d5..59477ce 100644 --- a/gcc/diagnostic.c +++ b/gcc/diagnostic.c @@ -175,6 +175,7 @@ diagnostic_initialize (diagnostic_context *context, int n_opts) context->lock = 0; context->inhibit_notes_p = false; context->colorize_source_p = false; + context->show_labels_p = false; context->show_line_numbers_p = false; context->show_ruler_p = false; context->parseable_fixits_p = false; diff --git a/gcc/diagnostic.h b/gcc/diagnostic.h index 744aec1..fe3130b 100644 --- a/gcc/diagnostic.h +++ b/gcc/diagnostic.h @@ -204,6 +204,9 @@ struct diagnostic_context a token, which would look strange). */ bool colorize_source_p; + /* When printing source code, should labelled ranges be printed? */ + bool show_labels_p; + /* When printing source code, should there be a left-hand margin showing line numbers? */ bool show_line_numbers_p; diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index d7fd0e1..d91e6c5 100644 --- a/gcc/doc/invoke.texi +++ b/gcc/doc/invoke.texi @@ -267,7 +267,7 @@ Objective-C and Objective-C++ Dialects}. -fdiagnostics-show-location=@r{[}once@r{|}every-line@r{]} @gol -fdiagnostics-color=@r{[}auto@r{|}never@r{|}always@r{]} @gol -fno-diagnostics-show-option -fno-diagnostics-show-caret @gol --fno-diagnostics-show-line-numbers @gol +-fno-diagnostics-show-labels -fno-diagnostics-show-line-numbers @gol -fdiagnostics-parseable-fixits -fdiagnostics-generate-patch @gol -fdiagnostics-show-template-tree -fno-elide-type @gol -fno-show-column} @@ -1292,7 +1292,7 @@ See RS/6000 and PowerPC Options. -malign-data=@var{type} -mstack-protector-guard=@var{guard} @gol -mstack-protector-guard-reg=@var{reg} @gol -mstack-protector-guard-offset=@var{offset} @gol --mstack-protector-guard-symbol=@var{symbol} -mmitigate-rop @gol +-mstack-protector-guard-symbol=@var{symbol} @gol -mgeneral-regs-only -mcall-ms2sysv-xlogues @gol -mindirect-branch=@var{choice} -mfunction-return=@var{choice} @gol -mindirect-branch-register} @@ -3711,6 +3711,23 @@ the @option{-fmessage-length=n} option is given. When the output is done to the terminal, the width is limited to the width given by the @env{COLUMNS} environment variable or, if not set, to the terminal width. +@item -fno-diagnostics-show-labels +@opindex fno-diagnostics-show-labels +@opindex fdiagnostics-show-labels +By default, when printing source code (via @option{-fdiagnostics-show-caret}), +diagnostics can label ranges of source code with pertinent information, such +as the types of expressions: + +@smallexample + printf ("foo %s bar", long_i + long_j); + ~^ ~~~~~~~~~~~~~~~ + | | + char * long int +@end smallexample + +This option suppresses the printing of these labels (in the example above, +the vertical bars and the ``char *'' and ``long int'' text). + @item -fno-diagnostics-show-line-numbers @opindex fno-diagnostics-show-line-numbers @opindex fdiagnostics-show-line-numbers @@ -27986,13 +28003,6 @@ which segment register (@code{%fs} or @code{%gs}) to use as base register for reading the canary, and from what offset from that base register. The default for those is as specified in the relevant ABI. -@item -mmitigate-rop -@opindex mmitigate-rop -Try to avoid generating code sequences that contain unintended return -opcodes, to mitigate against certain forms of attack. At the moment, -this option is limited in what it can do and should not be relied -on to provide serious protection. - @item -mgeneral-regs-only @opindex mgeneral-regs-only Generate code that uses only the general-purpose registers. This diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c index 9ed4730..5a74131 100644 --- a/gcc/dwarf2out.c +++ b/gcc/dwarf2out.c @@ -24247,6 +24247,7 @@ gen_producer_string (void) case OPT_fdiagnostics_show_location_: case OPT_fdiagnostics_show_option: case OPT_fdiagnostics_show_caret: + case OPT_fdiagnostics_show_labels: case OPT_fdiagnostics_show_line_numbers: case OPT_fdiagnostics_color_: case OPT_fverbose_asm: diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index e440352..dc4aa1a 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,7 @@ +2018-08-16 Nathan Sidwell <nathan@acm.org> + + * cpp.c (dump_macro): Use cpp_user_macro_p. + 2018-08-14 Janus Weil <janus@gcc.gnu.org> PR fortran/86116 diff --git a/gcc/gcc-rich-location.c b/gcc/gcc-rich-location.c index 0a0adf9..2576c73 100644 --- a/gcc/gcc-rich-location.c +++ b/gcc/gcc-rich-location.c @@ -38,24 +38,26 @@ along with GCC; see the file COPYING3. If not see #include "cpplib.h" #include "diagnostic.h" -/* Add a range to the rich_location, covering expression EXPR. */ +/* Add a range to the rich_location, covering expression EXPR, + using LABEL if non-NULL. */ void -gcc_rich_location::add_expr (tree expr) +gcc_rich_location::add_expr (tree expr, range_label *label) { gcc_assert (expr); if (CAN_HAVE_RANGE_P (expr)) - add_range (EXPR_LOCATION (expr), false); + add_range (EXPR_LOCATION (expr), false, label); } -/* If T is an expression, add a range for it to the rich_location. */ +/* If T is an expression, add a range for it to the rich_location, + using LABEL if non-NULL. */ void -gcc_rich_location::maybe_add_expr (tree t) +gcc_rich_location::maybe_add_expr (tree t, range_label *label) { if (EXPR_P (t)) - add_expr (t); + add_expr (t, label); } /* Add a fixit hint suggesting replacing the range at MISSPELLED_TOKEN_LOC diff --git a/gcc/gcc-rich-location.h b/gcc/gcc-rich-location.h index 9c705c8..dc11ee8 100644 --- a/gcc/gcc-rich-location.h +++ b/gcc/gcc-rich-location.h @@ -28,15 +28,17 @@ class gcc_rich_location : public rich_location /* Constructors. */ /* Constructing from a location. */ - gcc_rich_location (source_location loc) : - rich_location (line_table, loc) {} + gcc_rich_location (source_location loc, const range_label *label = NULL) + : rich_location (line_table, loc, label) + { + } /* Methods for adding ranges via gcc entities. */ void - add_expr (tree expr); + add_expr (tree expr, range_label *label); void - maybe_add_expr (tree t); + maybe_add_expr (tree t, range_label *label); void add_fixit_misspelled_id (location_t misspelled_token_loc, tree hint_id); @@ -99,4 +101,65 @@ class gcc_rich_location : public rich_location location_t indent); }; +/* Concrete subclass of libcpp's range_label. + Simple implementation using a string literal. */ + +class text_range_label : public range_label +{ + public: + text_range_label (const char *text) : m_text (text) {} + + label_text get_text () const FINAL OVERRIDE + { + return label_text (const_cast <char *> (m_text), false); + } + + private: + const char *m_text; +}; + +/* Concrete subclass of libcpp's range_label for use in + diagnostics involving mismatched types. + + Each frontend that uses this should supply its own implementation. + + Generate a label describing LABELLED_TYPE. The frontend may use + OTHER_TYPE where appropriate for highlighting the differences between + the two types (analogous to C++'s use of %H and %I with + template types). + + Either or both of LABELLED_TYPE and OTHER_TYPE may be NULL_TREE. + If LABELLED_TYPE is NULL_TREE, then there is no label. + + For example, this rich_location could use two instances of + range_label_for_type_mismatch: + + printf ("arg0: %i arg1: %s arg2: %i", + ^~ + | + const char * + 100, 101, 102); + ~~~ + | + int + + (a) the label for "%s" with LABELLED_TYPE for "const char*" and + (b) the label for "101" with LABELLED TYPE for "int" + where each one uses the other's type as OTHER_TYPE. */ + +class range_label_for_type_mismatch : public range_label +{ + public: + range_label_for_type_mismatch (tree labelled_type, tree other_type) + : m_labelled_type (labelled_type), m_other_type (other_type) + { + } + + label_text get_text () const OVERRIDE; + + protected: + tree m_labelled_type; + tree m_other_type; +}; + #endif /* GCC_RICH_LOCATION_H */ diff --git a/gcc/gimple-ssa-sprintf.c b/gcc/gimple-ssa-sprintf.c index c652c55..5213e17 100644 --- a/gcc/gimple-ssa-sprintf.c +++ b/gcc/gimple-ssa-sprintf.c @@ -601,8 +601,8 @@ fmtwarn (const substring_loc &fmt_loc, location_t param_loc, { va_list ap; va_start (ap, gmsgid); - bool warned = format_warning_va (fmt_loc, param_loc, corrected_substring, - opt, gmsgid, &ap); + bool warned = format_warning_va (fmt_loc, NULL, param_loc, NULL, + corrected_substring, opt, gmsgid, &ap); va_end (ap); return warned; @@ -616,7 +616,8 @@ fmtwarn_n (const substring_loc &fmt_loc, location_t param_loc, { va_list ap; va_start (ap, plural_gmsgid); - bool warned = format_warning_n_va (fmt_loc, param_loc, corrected_substring, + bool warned = format_warning_n_va (fmt_loc, NULL, param_loc, NULL, + corrected_substring, opt, n, singular_gmsgid, plural_gmsgid, &ap); va_end (ap); diff --git a/gcc/lto-wrapper.c b/gcc/lto-wrapper.c index 39d9f088..d446786 100644 --- a/gcc/lto-wrapper.c +++ b/gcc/lto-wrapper.c @@ -255,6 +255,7 @@ merge_and_complain (struct cl_decoded_option **decoded_options, /* Fallthru. */ case OPT_fdiagnostics_show_caret: + case OPT_fdiagnostics_show_labels: case OPT_fdiagnostics_show_line_numbers: case OPT_fdiagnostics_show_option: case OPT_fdiagnostics_show_location_: @@ -537,6 +538,7 @@ append_compiler_options (obstack *argv_obstack, struct cl_decoded_option *opts, switch (option->opt_index) { case OPT_fdiagnostics_show_caret: + case OPT_fdiagnostics_show_labels: case OPT_fdiagnostics_show_line_numbers: case OPT_fdiagnostics_show_option: case OPT_fdiagnostics_show_location_: @@ -584,6 +586,7 @@ append_diag_options (obstack *argv_obstack, struct cl_decoded_option *opts, { case OPT_fdiagnostics_color_: case OPT_fdiagnostics_show_caret: + case OPT_fdiagnostics_show_labels: case OPT_fdiagnostics_show_line_numbers: case OPT_fdiagnostics_show_option: case OPT_fdiagnostics_show_location_: @@ -2175,6 +2175,10 @@ common_handle_option (struct gcc_options *opts, dc->show_caret = value; break; + case OPT_fdiagnostics_show_labels: + dc->show_labels_p = value; + break; + case OPT_fdiagnostics_show_line_numbers: dc->show_line_numbers_p = value; break; diff --git a/gcc/selftest-diagnostic.c b/gcc/selftest-diagnostic.c index 837488b..f3c255e 100644 --- a/gcc/selftest-diagnostic.c +++ b/gcc/selftest-diagnostic.c @@ -37,6 +37,7 @@ test_diagnostic_context::test_diagnostic_context () { diagnostic_initialize (this, 0); show_caret = true; + show_labels_p = true; show_column = true; start_span = start_span_cb; } diff --git a/gcc/substring-locations.c b/gcc/substring-locations.c index 2d7f0c1..82f2f45 100644 --- a/gcc/substring-locations.c +++ b/gcc/substring-locations.c @@ -26,6 +26,7 @@ along with GCC; see the file COPYING3. If not see #include "tree.h" #include "langhooks.h" #include "substring-locations.h" +#include "gcc-rich-location.h" /* Emit a warning governed by option OPT, using SINGULAR_GMSGID as the format string (or if PLURAL_GMSGID is different from SINGULAR_GMSGID, @@ -89,6 +90,27 @@ along with GCC; see the file COPYING3. If not see printf(fmt, msg); ^~~ ~~~ + If non-NULL, then FMT_LABEL will be used to label the location within the + string for cases 1 and 2; if non-NULL, then PARAM_LABEL will be used to label + the parameter. For example with case 1: + + test.c:90:16: warning: '%s' here but arg 2 has 'long' type [-Wformat=] + printf ("foo %s bar", long_i + long_j); + ~^ ~~~~~~~~~~~~~~~ + | + int + + and with case 2: + + test.c:90:10: warning: problem with '%i' here [-Wformat=] + printf("hello " INT_FMT " world", msg); + ^~~~~~~~~~~~~~~~~~~~~~~~~ + test.c:19: note: format string is defined here + #define INT_FMT "%i" + ~^ + | + int + If CORRECTED_SUBSTRING is non-NULL, use it for cases 1 and 2 to provide a fix-it hint, suggesting that it should replace the text within the substring range. For example: @@ -102,7 +124,9 @@ along with GCC; see the file COPYING3. If not see bool format_warning_n_va (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, unsigned HOST_WIDE_INT n, const char *singular_gmsgid, @@ -138,10 +162,15 @@ format_warning_n_va (const substring_loc &fmt_loc, } } - rich_location richloc (line_table, primary_loc); + /* Only use fmt_label in the initial warning for case 1. */ + const range_label *primary_label = NULL; + if (substring_within_range) + primary_label = fmt_label; + + gcc_rich_location richloc (primary_loc, primary_label); if (param_loc != UNKNOWN_LOCATION) - richloc.add_range (param_loc, false); + richloc.add_range (param_loc, false, param_label); if (!err && corrected_substring && substring_within_range) richloc.add_fixit_replace (fmt_substring_range, corrected_substring); @@ -173,7 +202,9 @@ format_warning_n_va (const substring_loc &fmt_loc, /* Case 2. */ if (warned) { - rich_location substring_richloc (line_table, fmt_substring_loc); + /* Use fmt_label in the note for case 2. */ + rich_location substring_richloc (line_table, fmt_substring_loc, + fmt_label); if (corrected_substring) substring_richloc.add_fixit_replace (fmt_substring_range, corrected_substring); @@ -188,11 +219,14 @@ format_warning_n_va (const substring_loc &fmt_loc, bool format_warning_va (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, const char *gmsgid, va_list *ap) { - return format_warning_n_va (fmt_loc, param_loc, corrected_substring, opt, + return format_warning_n_va (fmt_loc, fmt_label, param_loc, param_label, + corrected_substring, opt, 0, gmsgid, gmsgid, ap); } @@ -200,14 +234,16 @@ format_warning_va (const substring_loc &fmt_loc, bool format_warning_at_substring (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, const char *gmsgid, ...) { va_list ap; va_start (ap, gmsgid); - bool warned = format_warning_va (fmt_loc, param_loc, corrected_substring, - opt, gmsgid, &ap); + bool warned = format_warning_va (fmt_loc, fmt_label, param_loc, param_label, + corrected_substring, opt, gmsgid, &ap); va_end (ap); return warned; @@ -217,7 +253,9 @@ format_warning_at_substring (const substring_loc &fmt_loc, bool format_warning_at_substring_n (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, unsigned HOST_WIDE_INT n, const char *singular_gmsgid, @@ -225,7 +263,8 @@ format_warning_at_substring_n (const substring_loc &fmt_loc, { va_list ap; va_start (ap, plural_gmsgid); - bool warned = format_warning_n_va (fmt_loc, param_loc, corrected_substring, + bool warned = format_warning_n_va (fmt_loc, fmt_label, param_loc, param_label, + corrected_substring, opt, n, singular_gmsgid, plural_gmsgid, &ap); va_end (ap); diff --git a/gcc/substring-locations.h b/gcc/substring-locations.h index fca6fd3..919fdf0 100644 --- a/gcc/substring-locations.h +++ b/gcc/substring-locations.h @@ -77,32 +77,40 @@ class substring_loc /* Functions for emitting a warning about a format string. */ extern bool format_warning_va (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, const char *gmsgid, va_list *ap) - ATTRIBUTE_GCC_DIAG (5, 0); + ATTRIBUTE_GCC_DIAG (7, 0); extern bool format_warning_n_va (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, unsigned HOST_WIDE_INT n, const char *singular_gmsgid, const char *plural_gmsgid, va_list *ap) - ATTRIBUTE_GCC_DIAG (6, 0) ATTRIBUTE_GCC_DIAG (7, 0); + ATTRIBUTE_GCC_DIAG (8, 0) ATTRIBUTE_GCC_DIAG (9, 0); extern bool format_warning_at_substring (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, const char *gmsgid, ...) - ATTRIBUTE_GCC_DIAG (5, 6); + ATTRIBUTE_GCC_DIAG (7, 8); extern bool format_warning_at_substring_n (const substring_loc &fmt_loc, + const range_label *fmt_label, location_t param_loc, + const range_label *param_label, const char *corrected_substring, int opt, unsigned HOST_WIDE_INT n, const char *singular_gmsgid, const char *plural_gmsgid, ...) - ATTRIBUTE_GCC_DIAG (6, 8) ATTRIBUTE_GCC_DIAG (7, 8); + ATTRIBUTE_GCC_DIAG (8, 10) ATTRIBUTE_GCC_DIAG (9, 10); /* Implementation detail, for use when implementing LANG_HOOKS_GET_SUBSTRING_LOCATION. */ diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 18bb966..6311e0b 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,93 @@ +2018-08-16 Iain Sandoe <iain@sandoe.co.uk> + + * gcc.dg/memcmp-1.c (lib_memcmp): Apply __USER_LABEL_PREFIX__. + (lib_strncmp): Likewise. + +2018-08-16 Iain Sandoe <iain@sandoe.co.uk> + + * c-c++-common/asan/pointer-subtract-3.c: Skip for Darwin. + * c-c++-common/asan/pointer-subtract-4.c: Likewise. + * g++.dg/torture/pr44295.C : Likewise. + +2018-08-16 Iain Sandoe <iain@sandoe.co.uk> + + PR testsuite/78544 + * gcc.dg/tree-prof/section-attr-1.c: Add Darwin-specific section + attributes and matching. + * gcc.dg/tree-prof/section-attr-2.c: Likewise. + * gcc.dg/tree-prof/section-attr-3.c: Likewise. + +2018-08-16 Iain Sandoe <iain@sandoe.co.uk> + + * gcc.dg/asan/pr81923.c: Stringify __USER_LABEL_PREFIX__. + +2018-08-15 Uros Bizjak <ubizjak@gmail.com> + + * gcc.target/i386/rop1.c: Remove. + * gcc.target/i386/pr83554 (dg-options): Remove -mmitigate-rop. + +2018-08-15 Will Schmidt <will_schmidt@vnet.ibm.com> + + * gcc.target/powerpc/fold-vec-splat-char.c: New. + * gcc.target/powerpc/fold-vec-splat-floatdouble.c: New. + * gcc.target/powerpc/fold-vec-splat-int.c: New. + * gcc.target/powerpc/fold-vec-splat-longlong.c: New. + * gcc.target/powerpc/fold-vec-splat-pixel.c: New. + * gcc.target/powerpc/fold-vec-splat-short.c: New. + +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * g++.dg/diagnostic/aka3.C: New test. + * g++.dg/diagnostic/param-type-mismatch-2.C: Update expected + output to show range labels. + * g++.dg/diagnostic/param-type-mismatch.C: Likewise. + * g++.dg/plugin/plugin.exp (plugin_test_list): Add... + * g++.dg/plugin/show-template-tree-color-labels.C: New test. + * gcc.dg/bad-binary-ops.c: Update expected output to show range + labels. Add an "aka" example. + * gcc.dg/cpp/pr66415-1.c: Update expected output to show range + labels. + * gcc.dg/format/diagnostic-ranges.c: Likewise. + * gcc.dg/format/pr72858.c: Likewise. + * gcc.dg/format/pr78498.c: Likewise. + * gcc.dg/param-type-mismatch.c: Add "-Wpointer-sign" to options. + Update expected output to show range labels. Add examples of + -Wincompatible-pointer-types and -Wpointer-sign for parameters. + * gcc.dg/plugin/diagnostic-test-show-locus-bw-line-numbers.c: + Update expected output to show range labels. + * gcc.dg/plugin/diagnostic-test-show-locus-bw.c: Likewise. + (test_very_wide_line): Adjust so that label is at left-clipping + boundary. + (test_very_wide_line_2): New test. + * gcc.dg/plugin/diagnostic-test-show-locus-color-line-numbers.c: + Update expected output to show range labels. + * gcc.dg/plugin/diagnostic-test-show-locus-color.c: Likewise. + * gcc.dg/plugin/diagnostic-test-show-locus-no-labels.c: New test. + * gcc.dg/plugin/diagnostic_plugin_show_trees.c (show_tree): Update + for new param to gcc_rich_location::add_expr. + * gcc.dg/plugin/diagnostic_plugin_test_show_locus.c (add_range): + Add "label" param. + (test_show_locus): Add examples of labels to various tests. Tweak + the "very wide_line" test case and duplicate it, to cover the + boundary values for clipping of labels against the left-margin. + * gcc.dg/plugin/plugin.exp (plugin_test_list): Add + diagnostic-test-show-locus-no-labels.c. + * gcc.dg/pr69554-1.c: Update expected output to show range labels. + Update line numbers of dg-locus directives. + * gcc.dg/pr69627.c: Update expected output to show range labels. + * lib/multiline.exp (proc _build_multiline_regex): Remove + special-case handling of lines with trailing '|'. + +2018-08-15 Qing Zhao <qing.zhao@oracle.com> + + PR testsuite/86519 + * gcc.dg/strcmpopt_6.c: Scan the assembly file instead of + the .expand file. + +2018-08-15 Prathamesh Kulkarni <prathamesh.kulkarni@linaro.org> + + * gcc.dg/wmain.c: New test. + 2018-08-15 Iain Sandoe <iain@sandoe.co.uk> PR c/19315 @@ -7,7 +97,7 @@ 2018-08-15 Martin Liska <mliska@suse.cz> - PR tree-optimization/86925 + PR tree-optimization/86925 * gcc.dg/predict-20.c: New test. * gcc.dg/predict-21.c: New test. @@ -15,7 +105,7 @@ * g++.dg/init/goto3.C: Adjust for error instead of permerror. -2018-08-14 Allan Sandfeld Jensen <allan.jensen@qt.io> +2018-08-14 Allan Sandfeld Jensen <allan.jensen@qt.io> * gcc.target/i386/sse2-movs.c: New test. @@ -110,14 +200,14 @@ 2018-08-10 Martin Liska <mliska@suse.cz> - PR target/83610 + PR target/83610 * gcc.dg/predict-17.c: New test. * gcc.dg/predict-18.c: New test. * gcc.dg/predict-19.c: New test. 2018-08-10 Martin Liska <mliska@suse.cz> - PR tree-optimization/85799 + PR tree-optimization/85799 * gcc.dg/pr85799.c: New test. 2018-08-09 Jeff Law <law@redhat.com> @@ -286,7 +376,7 @@ 2018-08-07 Martin Liska <mliska@suse.cz> - PR middle-end/83023 + PR middle-end/83023 * gcc.dg/predict-16.c: New test. * g++.dg/predict-1.C: New test. @@ -1907,7 +1997,7 @@ * gcc.target/vsx-vector-abss.c: New file to test vec_abss. -2018-06-27 Tamar Christina <tamar.christina@arm.com> +2018-06-27 Tamar Christina <tamar.christina@arm.com> PR target/85769 * gcc.target/aarch64/f16_mov_immediate_3.c: New. diff --git a/gcc/testsuite/c-c++-common/asan/pointer-subtract-3.c b/gcc/testsuite/c-c++-common/asan/pointer-subtract-3.c index 7cae91b..b434aaa 100644 --- a/gcc/testsuite/c-c++-common/asan/pointer-subtract-3.c +++ b/gcc/testsuite/c-c++-common/asan/pointer-subtract-3.c @@ -1,4 +1,5 @@ /* { dg-do run { target pthread_h } } */ +/* { dg-skip-if "no pthread_barrier" { *-*-darwin* } } */ /* { dg-set-target-env-var ASAN_OPTIONS "detect_invalid_pointer_pairs=2:halt_on_error=1" } */ /* { dg-options "-fsanitize=address,pointer-subtract" } */ /* { dg-additional-options "-pthread" { target pthread } } */ diff --git a/gcc/testsuite/c-c++-common/asan/pointer-subtract-4.c b/gcc/testsuite/c-c++-common/asan/pointer-subtract-4.c index af65c59..4931c21 100644 --- a/gcc/testsuite/c-c++-common/asan/pointer-subtract-4.c +++ b/gcc/testsuite/c-c++-common/asan/pointer-subtract-4.c @@ -1,4 +1,5 @@ /* { dg-do run { target pthread_h } } */ +/* { dg-skip-if "no pthread_barrier" { *-*-darwin* } } */ /* { dg-shouldfail "asan" } */ /* { dg-set-target-env-var ASAN_OPTIONS "detect_invalid_pointer_pairs=2:halt_on_error=1" } */ /* { dg-options "-fsanitize=address,pointer-subtract" } */ diff --git a/gcc/testsuite/g++.dg/diagnostic/aka3.C b/gcc/testsuite/g++.dg/diagnostic/aka3.C new file mode 100644 index 0000000..1eb4fb2 --- /dev/null +++ b/gcc/testsuite/g++.dg/diagnostic/aka3.C @@ -0,0 +1,25 @@ +/* Verify the "aka" descriptions for typedefs are correctly + quoted and shown within labels. */ + +/* { dg-options "-fdiagnostics-show-caret" } */ + +typedef struct s1 t1; +typedef struct s2 {int i;} t2; + +int foo(t1 *); + +void test_1 () { + t2 pos; + + foo (&pos); // { dg-error "cannot convert 't2\\*' {aka 's2\\*'} to 't1\\*' {aka 's1\\*'}" } + /* { dg-begin-multiline-output "" } + foo (&pos); + ^~~~ + | + t2* {aka s2*} + { dg-end-multiline-output "" } */ + /* { dg-begin-multiline-output "" } + int foo(t1 *); + ^~~~ + { dg-end-multiline-output "" } */ +} diff --git a/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch-2.C b/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch-2.C index c3b6f00..8cf2dab 100644 --- a/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch-2.C +++ b/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch-2.C @@ -12,6 +12,8 @@ int test_1 (int first, const char *second, float third) /* { dg-begin-multiline-output "" } return callee_1 (first, second, third); ^~~~~~ + | + const char* { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_1\\(int, const char\\*\\*, float\\)'" "" { target *-*-* } callee_1 } /* { dg-begin-multiline-output "" } @@ -30,6 +32,8 @@ int test_2 (int first, const char *second, float third) /* { dg-begin-multiline-output "" } return callee_2 (first, second, third); ^~~~~~ + | + const char* { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_2\\(int, const char\\*\\*, float\\)'" "" { target *-*-* } callee_2 } /* { dg-begin-multiline-output "" } @@ -51,6 +55,8 @@ int test_3 (int first, const char *second, float third) /* { dg-begin-multiline-output "" } return callee_3 (first, second, third); ^~~~~~ + | + const char* { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_3\\(int, const char\\*\\*, float\\)'" "" { target *-*-* } callee_3 } /* { dg-begin-multiline-output "" } diff --git a/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch.C b/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch.C index 5fcde0b..50bbd4a 100644 --- a/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch.C +++ b/gcc/testsuite/g++.dg/diagnostic/param-type-mismatch.C @@ -12,6 +12,8 @@ int test_1 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_1\\(int, const char\\*, float\\)'" "" { target *-*-* } callee_1 } /* { dg-begin-multiline-output "" } @@ -30,6 +32,8 @@ int test_2 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_2 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_2\\(int, const char\\*, float\\)'" "" { target *-*-* } callee_2 } /* { dg-begin-multiline-output "" } @@ -51,6 +55,8 @@ int test_3 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_3 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_3\\(int, const char\\*, float\\)'" "" { target *-*-* } callee_3 } /* { dg-begin-multiline-output "" } @@ -69,6 +75,8 @@ int test_4 (int first, int second, float third) /* { dg-begin-multiline-output "" } return s4::member_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } struct s4 { static int member_1 (int one, const char *two, float three); }; @@ -87,6 +95,8 @@ int test_5 (int first, int second, float third) /* { dg-begin-multiline-output "" } return inst.member_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } struct s5 { int member_1 (int one, const char *two, float three); }; @@ -104,6 +114,8 @@ int test_6 (int first, int second, float third, s6 *ptr) /* { dg-begin-multiline-output "" } return ptr->member_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } struct s6 { int member_1 (int one, const char *two, float three); }; @@ -144,6 +156,8 @@ int test_8 (int first, int second, float third) /* { dg-begin-multiline-output "" } return s8 <const char *>::member_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } struct s8 { static int member_1 (int one, T two, float three); }; @@ -163,6 +177,8 @@ int test_9 (int first, int second, float third) /* { dg-begin-multiline-output "" } return inst.member_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } struct s9 { int member_1 (int one, T two, float three); }; @@ -180,6 +196,8 @@ int test_10 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_10 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_10\\(int, int \\(\\*\\)\\(int, int\\), float\\)'" "" { target *-*-* } callee_10 } /* { dg-begin-multiline-output "" } @@ -198,6 +216,8 @@ int test_11 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_11 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ // { dg-message "initializing argument 2 of 'int callee_11\\(int, int \\(\\*\\)\\(int, int\\), float\\)'" "" { target *-*-* } callee_11 } /* { dg-begin-multiline-output "" } diff --git a/gcc/testsuite/g++.dg/plugin/plugin.exp b/gcc/testsuite/g++.dg/plugin/plugin.exp index 451c4a9..d9f54ab 100644 --- a/gcc/testsuite/g++.dg/plugin/plugin.exp +++ b/gcc/testsuite/g++.dg/plugin/plugin.exp @@ -69,6 +69,7 @@ set plugin_test_list [list \ diagnostic-test-inlining-1.C } \ { show_template_tree_color_plugin.c \ show-template-tree-color.C \ + show-template-tree-color-labels.C \ show-template-tree-color-no-elide-type.C } \ { comment_plugin.c comments-1.C } \ ] diff --git a/gcc/testsuite/g++.dg/plugin/show-template-tree-color-labels.C b/gcc/testsuite/g++.dg/plugin/show-template-tree-color-labels.C new file mode 100644 index 0000000..462e1bd --- /dev/null +++ b/gcc/testsuite/g++.dg/plugin/show-template-tree-color-labels.C @@ -0,0 +1,38 @@ +/* Verify colorization of the labels in diagnostic-show-locus.c + for template comparisons. + Doing so requires a plugin; see the comments in the plugin for the + rationale. */ + +// { dg-options "-fdiagnostics-color=always -fdiagnostics-show-caret" } + +template<typename> struct vector {}; +template<typename, typename> struct map {}; + +void fn_1(vector<int>); +void fn_2(map<int, int>); + +void test_1 (vector<double> vec) +{ + fn_1 (vec); + /* { dg-begin-multiline-output "" } +could not convert '[01m[Kvec[m[K' from '[01m[Kvector<[01;32m[Kdouble[m[K>[m[K' to '[01m[Kvector<[01;32m[Kint[m[K>[m[K' + fn_1 ([01;31m[Kvec[m[K); + [01;31m[K^~~[m[K + [01;31m[K|[m[K + [01;31m[Kvector<double>[m[K + { dg-end-multiline-output "" } */ + // TODO: we don't yet highlight the mismatching part with color +} + +void test_2 (const map<int, double> &m) +{ + fn_2 (m); + /* { dg-begin-multiline-output "" } +could not convert '[01m[Km[m[K' from '[01m[Kmap<[...],[01;32m[Kdouble[m[K>[m[K' to '[01m[Kmap<[...],[01;32m[Kint[m[K>[m[K' + fn_2 ([01;31m[Km[m[K); + [01;31m[K^[m[K + [01;31m[K|[m[K + [01;31m[Kmap<[...],double>[m[K + { dg-end-multiline-output "" } */ + // TODO: we don't yet highlight the mismatching part with color +} diff --git a/gcc/testsuite/g++.dg/torture/pr44295.C b/gcc/testsuite/g++.dg/torture/pr44295.C index 7525dc4..a2edf63 100644 --- a/gcc/testsuite/g++.dg/torture/pr44295.C +++ b/gcc/testsuite/g++.dg/torture/pr44295.C @@ -1,5 +1,6 @@ /* { dg-do compile } */ /* { dg-additional-options "-Wno-return-type" } */ +/* { dg-skip-if "no pthread_barrier" { *-*-darwin* } } */ extern "C" { typedef __SIZE_TYPE__ size_t; diff --git a/gcc/testsuite/gcc.dg/asan/pr81923.c b/gcc/testsuite/gcc.dg/asan/pr81923.c index f81d512..dd9db72 100644 --- a/gcc/testsuite/gcc.dg/asan/pr81923.c +++ b/gcc/testsuite/gcc.dg/asan/pr81923.c @@ -1,7 +1,10 @@ /* PR sanitizer/81923 */ /* { dg-do link } */ -int foobar __asm (__USER_LABEL_PREFIX__ "barbaz") = 34; +#define STR1(X) #X +#define STR2(X) STR1(X) + +int foobar __asm (STR2(__USER_LABEL_PREFIX__) "barbaz") = 34; int main () diff --git a/gcc/testsuite/gcc.dg/bad-binary-ops.c b/gcc/testsuite/gcc.dg/bad-binary-ops.c index e1da4d6..46c158e 100644 --- a/gcc/testsuite/gcc.dg/bad-binary-ops.c +++ b/gcc/testsuite/gcc.dg/bad-binary-ops.c @@ -13,6 +13,8 @@ void test_1 () { dg-begin-multiline-output "" } myvec[1]/ptr; ~~~~~~~~^ + | + __m128 { dg-end-multiline-output "" } */ @@ -31,8 +33,12 @@ int test_2 (void) /* { dg-begin-multiline-output "" } return (some_function () ~~~~~~~~~~~~~~~~ + | + struct s + some_other_function ()); ^ ~~~~~~~~~~~~~~~~~~~~~~ + | + struct t { dg-end-multiline-output "" } */ } @@ -46,3 +52,23 @@ int test_3 (struct s param_s, struct t param_t) { dg-end-multiline-output "" } */ /* TODO: ideally we'd underline both params here. */ } + +typedef struct s S; +typedef struct t T; + +extern S callee_4a (void); +extern T callee_4b (void); + +int test_4 (void) +{ + return callee_4a () + callee_4b (); /* { dg-error "invalid operands to binary \+" } */ + +/* { dg-begin-multiline-output "" } + return callee_4a () + callee_4b (); + ~~~~~~~~~~~~ ^ ~~~~~~~~~~~~ + | | + | T {aka struct t} + S {aka struct s} + { dg-end-multiline-output "" } */ +} + diff --git a/gcc/testsuite/gcc.dg/cpp/pr66415-1.c b/gcc/testsuite/gcc.dg/cpp/pr66415-1.c index 515252c..cc4e417 100644 --- a/gcc/testsuite/gcc.dg/cpp/pr66415-1.c +++ b/gcc/testsuite/gcc.dg/cpp/pr66415-1.c @@ -11,6 +11,8 @@ fn1 (void) /* { dg-begin-multiline-output "" } __builtin_printf ("xxxxxxxxxxxxxxxxx%dxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"); ~^ + | + int { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/format/diagnostic-ranges.c b/gcc/testsuite/gcc.dg/format/diagnostic-ranges.c index e56e159..84535f0 100644 --- a/gcc/testsuite/gcc.dg/format/diagnostic-ranges.c +++ b/gcc/testsuite/gcc.dg/format/diagnostic-ranges.c @@ -11,6 +11,8 @@ void test_mismatching_types (const char *msg) /* { dg-begin-multiline-output "" } printf("hello %i", msg); ~^ ~~~ + | | + int const char * %s { dg-end-multiline-output "" } */ @@ -19,6 +21,9 @@ void test_mismatching_types (const char *msg) /* { dg-begin-multiline-output "" } printf("hello %s", 42); ~^ ~~ + | | + | int + char * %d { dg-end-multiline-output "" } */ @@ -26,6 +31,8 @@ void test_mismatching_types (const char *msg) /* { dg-begin-multiline-output "" } printf("hello %i", (long)0); ~^ ~~~~~~~ + | | + int long int %li { dg-end-multiline-output "" } */ } @@ -37,9 +44,13 @@ void test_multiple_arguments (void) /* { dg-begin-multiline-output "" } printf ("arg0: %i arg1: %s arg 2: %i", ~^ + | + char * %d 100, 101, 102); ~~~ + | + int { dg-end-multiline-output "" } */ } @@ -50,9 +61,13 @@ void test_multiple_arguments_2 (int i, int j) /* { dg-begin-multiline-output "" } printf ("arg0: %i arg1: %s arg 2: %i", ~^ + | + char * %d 100, i + j, 102); ~~~~~ + | + int { dg-end-multiline-output "" } */ } @@ -72,6 +87,8 @@ void multiline_format_string (void) { ~~ "d" ~^ + | + int { dg-end-multiline-output "" } */ } @@ -84,6 +101,8 @@ void test_hex (const char *msg) /* { dg-begin-multiline-output "" } printf("hello \x25\x69", msg); ~~~~^~~~ ~~~ + | | + int const char * \x25s { dg-end-multiline-output "" } */ } @@ -97,6 +116,8 @@ void test_oct (const char *msg) /* { dg-begin-multiline-output "" } printf("hello \045\151", msg); ~~~~^~~~ ~~~ + | | + int const char * \045s { dg-end-multiline-output "" } */ } @@ -112,11 +133,15 @@ void test_multiple (const char *msg) ^~~~~~~~ msg); ~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } printf("prefix" "\x25" "\151" "suffix", ~~~~~~~~^~~~ + | + int \x25" "s { dg-end-multiline-output "" } */ } @@ -127,6 +152,8 @@ void test_u8 (const char *msg) /* { dg-begin-multiline-output "" } printf(u8"hello %i", msg); ~^ ~~~ + | | + int const char * %s { dg-end-multiline-output "" } */ } @@ -137,6 +164,8 @@ void test_param (long long_i, long long_j) /* { dg-begin-multiline-output "" } printf ("foo %s bar", long_i + long_j); ~^ ~~~~~~~~~~~~~~~ + | | + char * long int %ld { dg-end-multiline-output "" } */ } @@ -147,6 +176,8 @@ void test_field_width_specifier (long l, int i1, int i2) /* { dg-begin-multiline-output "" } printf (" %*.*d ", l, i1, i2); ~^~~~ ~ + | | + int long int { dg-end-multiline-output "" } */ } @@ -158,12 +189,16 @@ void test_field_width_specifier_2 (char *d, long foo, long bar) /* { dg-begin-multiline-output "" } __builtin_sprintf (d, " %*ld ", foo, foo); ~^~~ ~~~ + | | + int long int { dg-end-multiline-output "" } */ __builtin_sprintf (d, " %*ld ", foo + bar, foo); /* { dg-warning "28: field width specifier '\\*' expects argument of type 'int', but argument 3 has type 'long int'" } */ /* { dg-begin-multiline-output "" } __builtin_sprintf (d, " %*ld ", foo + bar, foo); ~^~~ ~~~~~~~~~ + | | + int long int { dg-end-multiline-output "" } */ } @@ -173,12 +208,16 @@ void test_field_precision_specifier (char *d, long foo, long bar) /* { dg-begin-multiline-output "" } __builtin_sprintf (d, " %.*ld ", foo, foo); ~~^~~ ~~~ + | | + int long int { dg-end-multiline-output "" } */ __builtin_sprintf (d, " %.*ld ", foo + bar, foo); /* { dg-warning "29: field precision specifier '\\.\\*' expects argument of type 'int', but argument 3 has type 'long int'" } */ /* { dg-begin-multiline-output "" } __builtin_sprintf (d, " %.*ld ", foo + bar, foo); ~~^~~ ~~~~~~~~~ + | | + int long int { dg-end-multiline-output "" } */ } @@ -241,10 +280,14 @@ void test_macro (const char *msg) /* { dg-begin-multiline-output "" } printf("hello " INT_FMT " world", msg); ^~~~~~~~ ~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } #define INT_FMT "%i" ~^ + | + int %s { dg-end-multiline-output "" } */ #undef INT_FMT @@ -257,10 +300,14 @@ void test_macro_2 (const char *msg) /* { dg-begin-multiline-output "" } printf("hello %" PRIu32 " world", msg); ^~~~~~~~~ ~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } #define PRIu32 "u" ^ + | + unsigned int { dg-end-multiline-output "" } */ #undef PRIu32 } @@ -295,6 +342,8 @@ void test_macro_4 (const char *msg) /* { dg-begin-multiline-output "" } #define FMT_STRING "hello %i world" ~^ + | + int %s { dg-end-multiline-output "" } */ #undef FMT_STRING @@ -307,10 +356,14 @@ void test_non_contiguous_strings (void) /* { dg-begin-multiline-output "" } __builtin_printf(" %" "d ", 0.5); ^~~~ ~~~ + | + double { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } __builtin_printf(" %" "d ", 0.5); ~~~~^ + | + int %" "f { dg-end-multiline-output "" } */ } @@ -324,5 +377,7 @@ void test_const_arrays (void) /* { dg-begin-multiline-output "" } __builtin_printf(a, 0.5); ^ ~~~ + | + double { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/format/pr72858.c b/gcc/testsuite/gcc.dg/format/pr72858.c index b8c5829..7726094 100644 --- a/gcc/testsuite/gcc.dg/format/pr72858.c +++ b/gcc/testsuite/gcc.dg/format/pr72858.c @@ -28,12 +28,18 @@ test_x (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", lexpr); ~~~^ ~~~~~ + | | + | long int + unsigned int %-8lx { dg-end-multiline-output "" } */ sprintf (d, " %-8x ", ulexpr); /* { dg-warning "20: format '%x' expects argument of type 'unsigned int', but argument 3 has type 'long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", ulexpr); ~~~^ ~~~~~~ + | | + | long unsigned int + unsigned int %-8lx { dg-end-multiline-output "" } */ @@ -41,12 +47,18 @@ test_x (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", llexpr); ~~~^ ~~~~~~ + | | + | long long int + unsigned int %-8llx { dg-end-multiline-output "" } */ sprintf (d, " %-8x ", ullexpr); /* { dg-warning "20: format '%x' expects argument of type 'unsigned int', but argument 3 has type 'long long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", ullexpr); ~~~^ ~~~~~~~ + | | + | long long unsigned int + unsigned int %-8llx { dg-end-multiline-output "" } */ @@ -56,18 +68,27 @@ test_x (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", fexpr); ~~~^ ~~~~~ + | | + | double + unsigned int %-8f { dg-end-multiline-output "" } */ sprintf (d, " %-8x ", dexpr); /* { dg-warning "20: format '%x' expects argument of type 'unsigned int', but argument 3 has type 'double'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", dexpr); ~~~^ ~~~~~ + | | + | double + unsigned int %-8f { dg-end-multiline-output "" } */ sprintf (d, " %-8x ", ldexpr); /* { dg-warning "20: format '%x' expects argument of type 'unsigned int', but argument 3 has type 'long double'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", ldexpr); ~~~^ ~~~~~~ + | | + | long double + unsigned int %-8Lf { dg-end-multiline-output "" } */ @@ -76,6 +97,9 @@ test_x (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", ptr); ~~~^ ~~~ + | | + | void * + unsigned int %-8p { dg-end-multiline-output "" } */ @@ -86,6 +110,9 @@ test_x (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8x ", s); ~~~^ ~ + | | + | struct s + unsigned int { dg-end-multiline-output "" } */ } @@ -105,12 +132,18 @@ test_lx (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", iexpr); ~~~~^ ~~~~~ + | | + | int + long unsigned int %-8x { dg-end-multiline-output "" } */ sprintf (d, " %-8lx ", uiexpr); /* { dg-warning "21: format '%lx' expects argument of type 'long unsigned int', but argument 3 has type 'unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", uiexpr); ~~~~^ ~~~~~~ + | | + | unsigned int + long unsigned int %-8x { dg-end-multiline-output "" } */ @@ -121,12 +154,18 @@ test_lx (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", llexpr); ~~~~^ ~~~~~~ + | | + | long long int + long unsigned int %-8llx { dg-end-multiline-output "" } */ sprintf (d, " %-8lx ", ullexpr); /* { dg-warning "21: format '%lx' expects argument of type 'long unsigned int', but argument 3 has type 'long long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", ullexpr); ~~~~^ ~~~~~~~ + | | + | long long unsigned int + long unsigned int %-8llx { dg-end-multiline-output "" } */ @@ -136,18 +175,27 @@ test_lx (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", fexpr); ~~~~^ ~~~~~ + | | + | double + long unsigned int %-8f { dg-end-multiline-output "" } */ sprintf (d, " %-8lx ", dexpr); /* { dg-warning "21: format '%lx' expects argument of type 'long unsigned int', but argument 3 has type 'double'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", dexpr); ~~~~^ ~~~~~ + | | + | double + long unsigned int %-8f { dg-end-multiline-output "" } */ sprintf (d, " %-8lx ", ldexpr); /* { dg-warning "21: format '%lx' expects argument of type 'long unsigned int', but argument 3 has type 'long double'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lx ", ldexpr); ~~~~^ ~~~~~~ + | | + | long double + long unsigned int %-8Lf { dg-end-multiline-output "" } */ } @@ -170,12 +218,18 @@ test_o (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8o ", lexpr); ~~~^ ~~~~~ + | | + | long int + unsigned int %-8lo { dg-end-multiline-output "" } */ sprintf (d, " %-8o ", ulexpr); /* { dg-warning "20: format '%o' expects argument of type 'unsigned int', but argument 3 has type 'long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8o ", ulexpr); ~~~^ ~~~~~~ + | | + | long unsigned int + unsigned int %-8lo { dg-end-multiline-output "" } */ @@ -183,12 +237,18 @@ test_o (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8o ", llexpr); ~~~^ ~~~~~~ + | | + | long long int + unsigned int %-8llo { dg-end-multiline-output "" } */ sprintf (d, " %-8o ", ullexpr); /* { dg-warning "20: format '%o' expects argument of type 'unsigned int', but argument 3 has type 'long long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8o ", ullexpr); ~~~^ ~~~~~~~ + | | + | long long unsigned int + unsigned int %-8llo { dg-end-multiline-output "" } */ } @@ -208,12 +268,18 @@ test_lo (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8lo ", iexpr); ~~~~^ ~~~~~ + | | + | int + long unsigned int %-8o { dg-end-multiline-output "" } */ sprintf (d, " %-8lo ", uiexpr); /* { dg-warning "21: format '%lo' expects argument of type 'long unsigned int', but argument 3 has type 'unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lo ", uiexpr); ~~~~^ ~~~~~~ + | | + | unsigned int + long unsigned int %-8o { dg-end-multiline-output "" } */ @@ -224,12 +290,18 @@ test_lo (char *d, /* { dg-begin-multiline-output "" } sprintf (d, " %-8lo ", llexpr); ~~~~^ ~~~~~~ + | | + | long long int + long unsigned int %-8llo { dg-end-multiline-output "" } */ sprintf (d, " %-8lo ", ullexpr); /* { dg-warning "21: format '%lo' expects argument of type 'long unsigned int', but argument 3 has type 'long long unsigned int'" } */ /* { dg-begin-multiline-output "" } sprintf (d, " %-8lo ", ullexpr); ~~~~^ ~~~~~~~ + | | + | long long unsigned int + long unsigned int %-8llo { dg-end-multiline-output "" } */ } @@ -246,6 +318,9 @@ test_e (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8e ", iexpr); ~~~^ ~~~~~ + | | + | int + double %-8d { dg-end-multiline-output "" } */ @@ -257,6 +332,9 @@ test_e (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8e ", ldexpr); ~~~^ ~~~~~~ + | | + | long double + double %-8Le { dg-end-multiline-output "" } */ } @@ -273,6 +351,9 @@ test_Le (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8Le ", iexpr); ~~~~^ ~~~~~ + | | + | int + long double %-8d { dg-end-multiline-output "" } */ @@ -282,6 +363,9 @@ test_Le (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8Le ", fexpr); ~~~~^ ~~~~~ + | | + | double + long double %-8e { dg-end-multiline-output "" } */ @@ -289,6 +373,9 @@ test_Le (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8Le ", dexpr); ~~~~^ ~~~~~ + | | + | double + long double %-8e { dg-end-multiline-output "" } */ @@ -307,6 +394,9 @@ test_E (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8E ", iexpr); ~~~^ ~~~~~ + | | + | int + double %-8d { dg-end-multiline-output "" } */ @@ -318,6 +408,9 @@ test_E (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8E ", ldexpr); ~~~^ ~~~~~~ + | | + | long double + double %-8LE { dg-end-multiline-output "" } */ } @@ -334,6 +427,9 @@ test_LE (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8LE ", iexpr); ~~~~^ ~~~~~ + | | + | int + long double %-8d { dg-end-multiline-output "" } */ @@ -341,6 +437,9 @@ test_LE (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8LE ", fexpr); ~~~~^ ~~~~~ + | | + | double + long double %-8E { dg-end-multiline-output "" } */ @@ -348,6 +447,9 @@ test_LE (char *d, int iexpr, float fexpr, double dexpr, long double ldexpr) /* { dg-begin-multiline-output "" } sprintf (d, " %-8LE ", dexpr); ~~~~^ ~~~~~ + | | + | double + long double %-8E { dg-end-multiline-output "" } */ @@ -367,18 +469,24 @@ test_everything (char *d, long lexpr) /* { dg-begin-multiline-output "" } sprintf (d, "before %-+*.*lld after", lexpr, lexpr, lexpr); ~~~^~~~~~ ~~~~~ + | | + int long int { dg-end-multiline-output "" } */ /* { dg-warning "28: field precision specifier '\\.\\*' expects argument of type 'int', but argument 4 has type 'long int'" "" { target *-*-* } test_everything_sprintf } */ /* { dg-begin-multiline-output "" } sprintf (d, "before %-+*.*lld after", lexpr, lexpr, lexpr); ~~~~~^~~~ ~~~~~ + | | + int long int { dg-end-multiline-output "" } */ /* { dg-warning "31: format '%lld' expects argument of type 'long long int', but argument 5 has type 'long int'" "" { target *-*-* } test_everything_sprintf } */ /* { dg-begin-multiline-output "" } sprintf (d, "before %-+*.*lld after", lexpr, lexpr, lexpr); ~~~~~~~~^ ~~~~~ + | | + long long int long int %-+*.*ld { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/format/pr78498.c b/gcc/testsuite/gcc.dg/format/pr78498.c index 4b53a68..b911b04 100644 --- a/gcc/testsuite/gcc.dg/format/pr78498.c +++ b/gcc/testsuite/gcc.dg/format/pr78498.c @@ -7,6 +7,8 @@ void f (void) /* { dg-begin-multiline-output "" } __builtin_printf ("%i", ""); ~^ ~~ + | | + int char * %s { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/memcmp-1.c b/gcc/testsuite/gcc.dg/memcmp-1.c index a79db51..619cf9b 100644 --- a/gcc/testsuite/gcc.dg/memcmp-1.c +++ b/gcc/testsuite/gcc.dg/memcmp-1.c @@ -8,8 +8,13 @@ #include <string.h> #include <stdint.h> -int lib_memcmp(const void *a, const void *b, size_t n) asm("memcmp"); -int lib_strncmp(const char *a, const char *b, size_t n) asm("strncmp"); +#define STR1(X) #X +#define STR2(X) STR1(X) + +int lib_memcmp(const void *a, const void *b, size_t n) + asm(STR2(__USER_LABEL_PREFIX__) "memcmp"); +int lib_strncmp(const char *a, const char *b, size_t n) + asm(STR2(__USER_LABEL_PREFIX__) "strncmp"); #ifndef NRAND #ifdef TEST_ALL diff --git a/gcc/testsuite/gcc.dg/param-type-mismatch.c b/gcc/testsuite/gcc.dg/param-type-mismatch.c index 9498a74..9e654a9 100644 --- a/gcc/testsuite/gcc.dg/param-type-mismatch.c +++ b/gcc/testsuite/gcc.dg/param-type-mismatch.c @@ -1,4 +1,4 @@ -/* { dg-options "-fdiagnostics-show-caret" } */ +/* { dg-options "-fdiagnostics-show-caret -Wpointer-sign" } */ /* A collection of calls where argument 2 is of the wrong type. */ @@ -12,6 +12,8 @@ int test_1 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_1 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_1 } */ /* { dg-begin-multiline-output "" } @@ -30,6 +32,8 @@ int test_2 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_2 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_2 } */ /* { dg-begin-multiline-output "" } @@ -51,6 +55,8 @@ int test_3 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_3 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_3 } */ /* { dg-begin-multiline-output "" } @@ -69,6 +75,8 @@ int test_4 (int first, const char *second, float third) /* { dg-begin-multiline-output "" } return callee_4 (first, second, third); ^~~~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-message "expected 'float' but argument is of type 'const char \\*'" "" { target *-*-* } callee_4 } */ /* { dg-begin-multiline-output "" } @@ -87,6 +95,8 @@ int test_5 (int first, const char *second, float third) /* { dg-begin-multiline-output "" } return callee_5 (first, second, third); ^~~~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-message "expected 'float' but argument is of type 'const char \\*'" "" { target *-*-* } callee_5 } */ /* { dg-begin-multiline-output "" } @@ -105,6 +115,8 @@ int test_6 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_6 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-message " expected 'int \\(\\*\\)\\(int, int\\)' but argument is of type 'int'" "" { target *-*-* } callee_6 } */ /* { dg-begin-multiline-output "" } @@ -123,6 +135,8 @@ int test_7 (int first, int second, float third) /* { dg-begin-multiline-output "" } return callee_7 (first, second, third); ^~~~~~ + | + int { dg-end-multiline-output "" } */ /* { dg-message " expected 'int \\(\\*\\)\\(int, int\\)' but argument is of type 'int'" "" { target *-*-* } callee_7 } */ /* { dg-begin-multiline-output "" } @@ -130,3 +144,43 @@ int test_7 (int first, int second, float third) ^~~~~~~~~~~~~~~~~ { dg-end-multiline-output "" } */ } + +/* -Wincompatible-pointer-types for a parameter. */ + +extern int callee_8 (int one, float *two, float (three)); /* { dg-line callee_8 } */ + +int test_8 (int first, int *second, float third) +{ + return callee_8 (first, second, third); /* { dg-warning "passing argument 2 of 'callee_8' from incompatible pointer type" } */ + /* { dg-begin-multiline-output "" } + return callee_8 (first, second, third); + ^~~~~~ + | + int * + { dg-end-multiline-output "" } */ + /* { dg-message "expected 'float \\*' but argument is of type 'int \\*'" "" { target *-*-* } callee_8 } */ + /* { dg-begin-multiline-output "" } + extern int callee_8 (int one, float *two, float (three)); + ~~~~~~~^~~ + { dg-end-multiline-output "" } */ +} + +/* -Wpointer-sign for a parameter. */ + +extern int callee_9 (int one, int *two, float (three)); /* { dg-line callee_9 } */ + +int test_9 (int first, unsigned int *second, float third) +{ + return callee_9 (first, second, third); /* { dg-warning "pointer targets in passing argument 2 of 'callee_9' differ in signedness" } */ + /* { dg-begin-multiline-output "" } + return callee_9 (first, second, third); + ^~~~~~ + | + unsigned int * + { dg-end-multiline-output "" } */ + /* { dg-message "expected 'int \\*' but argument is of type 'unsigned int \\*'" "" { target *-*-* } callee_9 } */ + /* { dg-begin-multiline-output "" } + extern int callee_9 (int one, int *two, float (three)); + ~~~~~^~~ + { dg-end-multiline-output "" } */ +} diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw-line-numbers.c b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw-line-numbers.c index 66a2faa..89213eb 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw-line-numbers.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw-line-numbers.c @@ -31,6 +31,8 @@ void test_multiline (void) | ~~~~~~~~~~~~~~~~~ 27 | + second_function ()); | ^ ~~~~~~~~~~~~~~~~~~ + | | + | label { dg-end-multiline-output "" } */ #endif } @@ -43,8 +45,10 @@ void test_very_wide_line (void) | 0 0 0 0 0 0 1 | 4 5 6 7 8 9 0 | 0123456789012345678901234567890123456789012345678901234567890123456789 -41 | float f = foo * bar; +43 | float f = foo * bar; | ~~~~^~~~~ + | | + | label | bar * foo { dg-end-multiline-output "" } */ #endif @@ -58,7 +62,7 @@ void test_fixit_insert (void) #if 0 int a[2][2] = { 0, 1 , 2, 3 }; /* { dg-warning "insertion hints" } */ /* { dg-begin-multiline-output "" } -59 | int a[2][2] = { 0, 1 , 2, 3 }; +63 | int a[2][2] = { 0, 1 , 2, 3 }; | ^~~~ | { } { dg-end-multiline-output "" } */ @@ -72,7 +76,7 @@ void test_fixit_remove (void) #if 0 int a;; /* { dg-warning "example of a removal hint" } */ /* { dg-begin-multiline-output "" } -73 | int a;; +77 | int a;; | ^ | - { dg-end-multiline-output "" } */ @@ -86,7 +90,7 @@ void test_fixit_replace (void) #if 0 gtk_widget_showall (dlg); /* { dg-warning "example of a replacement hint" } */ /* { dg-begin-multiline-output "" } -87 | gtk_widget_showall (dlg); +91 | gtk_widget_showall (dlg); | ^~~~~~~~~~~~~~~~~~ | gtk_widget_show_all { dg-end-multiline-output "" } */ @@ -108,7 +112,7 @@ void test_fixit_insert_newline (void) } /* { dg-begin-multiline-output "" } |+ break; -106 | case 'b': +110 | case 'b': | ^~~~~~~~ { dg-end-multiline-output "" } */ #endif diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw.c b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw.c index 513c0af..bdfa420 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-bw.c @@ -44,6 +44,8 @@ void test_multiline (void) ~~~~~~~~~~~~~~~~~ + second_function ()); ^ ~~~~~~~~~~~~~~~~~~ + | + label { dg-end-multiline-output "" } */ #endif } @@ -66,6 +68,8 @@ void test_many_lines (void) /* { dg-begin-multiline-output "" } x = (first_function_with_a_very_long_name (lorem, ipsum, dolor, sit, amet, ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + | + label 1 consectetur, adipiscing, elit, ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ sed, eiusmod, tempor, @@ -76,6 +80,9 @@ void test_many_lines (void) ~~~~~~~~~~~~~~~~~~~~~~ + second_function_with_a_very_long_name (lorem, ipsum, dolor, sit, ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + | | + | label 2 + label 0 amet, consectetur, ~~~~~~~~~~~~~~~~~~ adipiscing, elit, sed, @@ -115,13 +122,32 @@ void test_caret_within_proper_range (void) void test_very_wide_line (void) { #if 0 - float f = foo * bar; /* { dg-warning "95: test" } */ + float x = foo * bar; /* { dg-warning "95: test" } */ /* { dg-begin-multiline-output "" } 0 0 0 0 0 0 1 4 5 6 7 8 9 0 6789012345678901234567890123456789012345678901234567890123456789012345 - float f = foo * bar; + x = foo * bar; + ~ ~~~~^~~~~ + | | + label 1 label 0 + bar * foo + { dg-end-multiline-output "" } */ +#endif +} + +void test_very_wide_line_2 (void) +{ +#if 0 + float x = foo * bar; /* { dg-warning "95: test" } */ +/* { dg-begin-multiline-output "" } + 0 0 0 0 0 0 1 + 4 5 6 7 8 9 0 + 6789012345678901234567890123456789012345678901234567890123456789012345 + = foo * bar; ~~~~^~~~~ + | + label 0 bar * foo { dg-end-multiline-output "" } */ #endif @@ -226,27 +252,69 @@ void test_many_nested_locations (void) ^ Lorem ipsum dolor sit amet, consectetur adipiscing elit, ^~~~~ ^~~~~ ^~~~~ ^~~ ^~~~ ^~~~~~~~~~~ ^~~~~~~~~~ ^~~~ + | | | | | | | | + | | | | label label label label + label label label label LOREM IPSUM DOLOR SIT AMET CONSECTETUR ADIPISCING ELIT sed do eiusmod tempor incididunt ut labore et dolore magna ^~~ ^~ ^~~~~~~ ^~~~~~ ^~~~~~~~~~ ^~ ^~~~~~ ^~ ^~~~~~ ^~~~~ + | | | | | | | | | | + | | | | | | | | label label + | | | | | | label label + | | label label label label + | label + label SED DO EIUSMOD TEMPOR INCIDIDUNT UT LABORE ET DOLORE MAGNA aliqua. Ut enim ad minim veniam, quis nostrud exercitation ^~~~~~ ^~ ^~~~ ^~ ^~~~~ ^~~~~~ ^~~~ ^~~~~~~ ^~~~~~~~~~~~ + | | | | | | | | | + | | | | | | | label label + | | | | label label label + | | | label + | | label + label label ALIQUA UT ENIM AD MINIM VENIAM QUIS NOSTRUD EXERCITATION ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis ^~~~~~~ ^~~~~~~ ^~~~ ^~ ^~~~~~~ ^~ ^~ ^~~~~~~ ^~~~~~~~~ ^~~~ + | | | | | | | | | | + | | | | | | | label label label + | | | | | | label + | | | | label label + | | | label + label label label ULLAMCO LABORIS NISI UT ALIQUIP EX EA COMMODO CONSEQUAT DUIS aute irure dolor in reprehenderit in voluptate velit esse cillum ^~~~ ^~~~~ ^~~~~ ^~ ^~~~~~~~~~~~~ ^~ ^~~~~~~~~ ^~~~~ ^~~~ ^~~~~~ + | | | | | | | | | | + | | | | | | | | | label + | | | | | | label label label + | | | | label label + | label label label + label AUTE IRURE DOLOR IN REPREHENDERIT IN VOLUPTATE VELIT ESSE CILLUM dolore eu fugiat nulla pariatur. Excepteur sint occaecat ^~~~~~ ^~ ^~~~~~ ^~~~~ ^~~~~~~~ ^~~~~~~~~ ^~~~ ^~~~~~~~ + | | | | | | | | + | | | | | | | label + | | label label label label label + label label DOLORE EU FUGIAT NULLA PARIATUR EXCEPTEUR SINT OCCAECAT cupidatat non proident, sunt in culpa qui officia deserunt ^~~~~~~~~ ^~~ ^~~~~~~~ ^~~~ ^~ ^~~~~ ^~~ ^~~~~~~ ^~~~~~~~ + | | | | | | | | | + | | | | | | | label label + | | | | | label label + | | | | label + | | label label + label label CUPIDATAT NON PROIDENT SUNT IN CULPA QUI OFFICIA DESERUNT mollit anim id est laborum. ^~~~~~ ^~~~ ^~ ^~~ ^~~~~~~ + | | | | | + | | | | label + | | | label + | | label + label label MOLLIT ANIM ID EST LABORUM { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color-line-numbers.c b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color-line-numbers.c index a80b6de..0453c52 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color-line-numbers.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color-line-numbers.c @@ -19,6 +19,8 @@ void test_multiline (void) | [32m[K~~~~~~~~~~~~~~~~~[m[K 15 | [01;35m[K+[m[K [34m[Ksecond_function ()[m[K); | [01;35m[K^[m[K [34m[K~~~~~~~~~~~~~~~~~~[m[K + | [01;35m[K|[m[K + | [01;35m[Klabel[m[K { dg-end-multiline-output "" } */ #endif } diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color.c b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color.c index 4cc406d..094bc65 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-color.c @@ -44,6 +44,8 @@ void test_multiline (void) [32m[K~~~~~~~~~~~~~~~~~[m[K [01;35m[K+[m[K [34m[Ksecond_function ()[m[K); [01;35m[K^[m[K [34m[K~~~~~~~~~~~~~~~~~~[m[K + [01;35m[K|[m[K + [01;35m[Klabel[m[K { dg-end-multiline-output "" } */ #endif } @@ -66,6 +68,8 @@ void test_many_lines (void) /* { dg-begin-multiline-output "" } x = ([32m[Kfirst_function_with_a_very_long_name (lorem, ipsum, dolor, sit, amet,[m[K [32m[K~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~[m[K + [32m[K|[m[K + [32m[Klabel 1[m[K [32m[K consectetur, adipiscing, elit,[m[K [32m[K~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~[m[K [32m[K sed, eiusmod, tempor,[m[K @@ -76,6 +80,9 @@ void test_many_lines (void) [32m[K~~~~~~~~~~~~~~~~~~~~~~[m[K [01;35m[K+[m[K [34m[Ksecond_function_with_a_very_long_name (lorem, ipsum, dolor, sit, [01;35m[K^[m[K [34m[K~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~[m[K + [01;35m[K|[m[K [34m[K|[m[K + [01;35m[K|[m[K [34m[Klabel 2[m[K + [01;35m[Klabel 0[m[K [34m[K amet, consectetur,[m[K [34m[K~~~~~~~~~~~~~~~~~~[m[K [34m[K adipiscing, elit, sed,[m[K @@ -115,13 +122,15 @@ void test_caret_within_proper_range (void) void test_very_wide_line (void) { #if 0 - float f = foo * bar; /* { dg-warning "95: test" } */ + float x = foo * bar; /* { dg-warning "95: test" } */ /* { dg-begin-multiline-output "" } 0 0 0 0 0 0 1 4 5 6 7 8 9 0 6789012345678901234567890123456789012345678901234567890123456789012345 - float f = [01;35m[Kfoo * bar[m[K; - [01;35m[K~~~~^~~~~[m[K + [32m[Kx[m[K = [01;35m[Kfoo * bar[m[K; + [32m[K~[m[K [01;35m[K~~~~^~~~~[m[K + [32m[K|[m[K [01;35m[K|[m[K + [32m[Klabel 1[m[K [01;35m[Klabel 0[m[K [32m[Kbar * foo[m[K { dg-end-multiline-output "" } */ #endif diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-no-labels.c b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-no-labels.c new file mode 100644 index 0000000..4c06368 --- /dev/null +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic-test-show-locus-no-labels.c @@ -0,0 +1,27 @@ +/* { dg-do compile } */ +/* { dg-options "-O -fdiagnostics-show-caret -fno-diagnostics-show-labels" } */ + +/* Verify that -fno-diagnostics-show-labels works. */ + +/* This is a collection of unittests for diagnostic_show_locus; + see the overview in diagnostic_plugin_test_show_locus.c. + + In particular, note the discussion of why we need a very long line here: +01234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789 + and that we can't use macros in this file. */ + +void test_multiline (void) +{ +#if 0 + x = (first_function () + + second_function ()); /* { dg-warning "test" } */ + + /* This shouldn't have a label. */ + /* { dg-begin-multiline-output "" } + x = (first_function () + ~~~~~~~~~~~~~~~~~ + + second_function ()); + ^ ~~~~~~~~~~~~~~~~~~ + { dg-end-multiline-output "" } */ +#endif +} diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_show_trees.c b/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_show_trees.c index 0bdd877..71e6740 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_show_trees.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_show_trees.c @@ -41,7 +41,7 @@ show_tree (tree node) return; gcc_rich_location richloc (EXPR_LOCATION (node)); - richloc.add_expr (node); + richloc.add_expr (node, NULL); if (richloc.get_num_locations () < 2) { diff --git a/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_test_show_locus.c b/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_test_show_locus.c index 1d340aa..3d78538 100644 --- a/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_test_show_locus.c +++ b/gcc/testsuite/gcc.dg/plugin/diagnostic_plugin_test_show_locus.c @@ -145,9 +145,10 @@ custom_diagnostic_finalizer (diagnostic_context *context, static void add_range (rich_location *richloc, location_t start, location_t finish, - bool show_caret_p) + bool show_caret_p, const range_label *label = NULL) { - richloc->add_range (make_location (start, start, finish), show_caret_p); + richloc->add_range (make_location (start, start, finish), show_caret_p, + label); } /* Exercise the diagnostic machinery to emit various warnings, @@ -192,7 +193,8 @@ test_show_locus (function *fun) if (0 == strcmp (fnname, "test_multiline")) { const int line = fnstart_line + 2; - rich_location richloc (line_table, get_loc (line + 1, 7)); + text_range_label label ("label"); + rich_location richloc (line_table, get_loc (line + 1, 7), &label); add_range (&richloc, get_loc (line, 7), get_loc (line, 23), false); add_range (&richloc, get_loc (line + 1, 9), get_loc (line + 1, 26), false); @@ -202,10 +204,14 @@ test_show_locus (function *fun) if (0 == strcmp (fnname, "test_many_lines")) { const int line = fnstart_line + 2; - rich_location richloc (line_table, get_loc (line + 5, 7)); - add_range (&richloc, get_loc (line, 7), get_loc (line + 4, 65), false); + text_range_label label0 ("label 0"); + text_range_label label1 ("label 1"); + text_range_label label2 ("label 2"); + rich_location richloc (line_table, get_loc (line + 5, 7), &label0); + add_range (&richloc, get_loc (line, 7), get_loc (line + 4, 65), false, + &label1); add_range (&richloc, get_loc (line + 5, 9), get_loc (line + 10, 61), - false); + false, &label2); warning_at (&richloc, 0, "test"); } @@ -231,16 +237,40 @@ test_show_locus (function *fun) } /* Example of a very wide line, where the information of interest - is beyond the width of the terminal (hardcoded above). */ + is beyond the width of the terminal (hardcoded above), with + a secondary location that exactly fits on the left-margin. */ if (0 == strcmp (fnname, "test_very_wide_line")) { const int line = fnstart_line + 2; global_dc->show_ruler_p = true; + text_range_label label0 ("label 0"); + text_range_label label1 ("label 1"); + rich_location richloc (line_table, + make_location (get_loc (line, 94), + get_loc (line, 90), + get_loc (line, 98)), + &label0); + richloc.add_range (get_loc (line, 35), false, &label1); + richloc.add_fixit_replace ("bar * foo"); + warning_at (&richloc, 0, "test"); + global_dc->show_ruler_p = false; + } + + /* Likewise, but with a secondary location that's immediately before + the left margin; the location and label should be gracefully dropped. */ + if (0 == strcmp (fnname, "test_very_wide_line_2")) + { + const int line = fnstart_line + 2; + global_dc->show_ruler_p = true; + text_range_label label0 ("label 0"); + text_range_label label1 ("label 1"); rich_location richloc (line_table, make_location (get_loc (line, 94), get_loc (line, 90), - get_loc (line, 98))); + get_loc (line, 98)), + &label0); richloc.add_fixit_replace ("bar * foo"); + richloc.add_range (get_loc (line, 34), false, &label1); warning_at (&richloc, 0, "test"); global_dc->show_ruler_p = false; } @@ -391,13 +421,14 @@ test_show_locus (function *fun) /* Example of many locations and many fixits. Underline (separately) every word in a comment, and convert them - to upper case. */ + to upper case. Give all of the ranges labels (sharing one label). */ if (0 == strcmp (fnname, "test_many_nested_locations")) { const char *file = LOCATION_FILE (fnstart); const int start_line = fnstart_line + 2; const int finish_line = start_line + 7; location_t loc = get_loc (start_line - 1, 2); + text_range_label label ("label"); rich_location richloc (line_table, loc); for (int line = start_line; line <= finish_line; line++) { @@ -418,7 +449,7 @@ test_show_locus (function *fun) location_t word = make_location (start_of_word, start_of_word, end_of_word); - richloc.add_range (word, true); + richloc.add_range (word, true, &label); /* Add a fixit, converting to upper case. */ char_span word_span = content.subspan (start_idx, idx - start_idx); diff --git a/gcc/testsuite/gcc.dg/plugin/plugin.exp b/gcc/testsuite/gcc.dg/plugin/plugin.exp index b2f8507..86ab1dd 100644 --- a/gcc/testsuite/gcc.dg/plugin/plugin.exp +++ b/gcc/testsuite/gcc.dg/plugin/plugin.exp @@ -72,6 +72,7 @@ set plugin_test_list [list \ { diagnostic_plugin_test_show_locus.c \ diagnostic-test-show-locus-bw.c \ diagnostic-test-show-locus-color.c \ + diagnostic-test-show-locus-no-labels.c \ diagnostic-test-show-locus-bw-line-numbers.c \ diagnostic-test-show-locus-color-line-numbers.c \ diagnostic-test-show-locus-parseable-fixits.c \ diff --git a/gcc/testsuite/gcc.dg/pr69554-1.c b/gcc/testsuite/gcc.dg/pr69554-1.c index 07ad0db..b979b55 100644 --- a/gcc/testsuite/gcc.dg/pr69554-1.c +++ b/gcc/testsuite/gcc.dg/pr69554-1.c @@ -12,6 +12,9 @@ int test_1 (const char *p, const char *q) /* { dg-begin-multiline-output "" } return (p + 1) + (q + 1); ~~~~~~~ ^ ~~~~~~~ + | | + | const char * + const char * { dg-end-multiline-output "" } */ } @@ -26,10 +29,14 @@ int test_2 (const char *p, const char *q) /* { dg-begin-multiline-output "" } return (p + 1) ~~~~~~~ + | + const char * + ^ (q + 1); ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ } @@ -43,16 +50,20 @@ int test_3 (const char *p, const char *q) + /* { dg-error "invalid operands" } */ (q + 1); -/* { dg-locus "12" "" { target *-*-* } "44" } */ +/* { dg-locus "12" "" { target *-*-* } "51" } */ /* { dg-begin-multiline-output "" } return (p + 1) ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } + ^ (q + 1); ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ } @@ -68,12 +79,16 @@ int test_4 (const char *p, const char *q) /* { dg-begin-multiline-output "" } return (p + 1) ~~~~~~~ + | + const char * + ^ { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } (q + 1); ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ } @@ -88,10 +103,12 @@ int test_5 (const char *p, const char *q) + /* { dg-error "invalid operands" } */ (q + 1); /* { dg-locus "14" } */ -/* { dg-locus "12" "" { target *-*-* } "88" } */ +/* { dg-locus "12" "" { target *-*-* } "103" } */ /* { dg-begin-multiline-output "" } return (p + 1) ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } + @@ -100,6 +117,8 @@ int test_5 (const char *p, const char *q) /* { dg-begin-multiline-output "" } (q + 1); ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ } @@ -136,10 +155,12 @@ int test_6 (const char *p, const char *q) fringilla sapien elit vitae nisl. Fusce mattis commodo risus nec convallis. */ (q + 1); /* { dg-locus "14" } */ -/* { dg-locus "12" "" { target *-*-* } "125" } */ +/* { dg-locus "12" "" { target *-*-* } "144" } */ /* { dg-begin-multiline-output "" } return (p + 1) ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ /* { dg-begin-multiline-output "" } + @@ -148,5 +169,7 @@ int test_6 (const char *p, const char *q) /* { dg-begin-multiline-output "" } (q + 1); ~~~~~~~ + | + const char * { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/pr69627.c b/gcc/testsuite/gcc.dg/pr69627.c index b7f56cd..bc48bb1 100644 --- a/gcc/testsuite/gcc.dg/pr69627.c +++ b/gcc/testsuite/gcc.dg/pr69627.c @@ -11,6 +11,8 @@ foo () /* { dg-begin-multiline-output "" } t[1] / s; ~~~~ ^ + | + float { dg-end-multiline-output "" } */ } @@ -23,5 +25,7 @@ bar () /* { dg-begin-multiline-output "" } t[1] / s[0]; ~~~~ ^ ~~~~ + | | + float const int * { dg-end-multiline-output "" } */ } diff --git a/gcc/testsuite/gcc.dg/strcmpopt_6.c b/gcc/testsuite/gcc.dg/strcmpopt_6.c index 964b9e4..4c6de02 100644 --- a/gcc/testsuite/gcc.dg/strcmpopt_6.c +++ b/gcc/testsuite/gcc.dg/strcmpopt_6.c @@ -1,7 +1,7 @@ /* When the specified length exceeds one of the arguments of the call to memcmp, the call to memcmp should NOT be inlined. */ -/* { dg-do run } */ -/* { dg-options "-O2 -fdump-rtl-expand -Wno-stringop-overflow" } */ +/* { dg-do compile } */ +/* { dg-options "-O2 -Wno-stringop-overflow" } */ typedef struct { char s[8]; int x; } S; @@ -33,4 +33,4 @@ int main (void) } -/* { dg-final { scan-rtl-dump-times "__builtin_memcmp" 6 "expand" } } */ +/* { dg-final { scan-assembler-times "memcmp" 2 } } */ diff --git a/gcc/testsuite/gcc.dg/tree-prof/section-attr-1.c b/gcc/testsuite/gcc.dg/tree-prof/section-attr-1.c index ee6662e..1f99b31 100644 --- a/gcc/testsuite/gcc.dg/tree-prof/section-attr-1.c +++ b/gcc/testsuite/gcc.dg/tree-prof/section-attr-1.c @@ -13,7 +13,11 @@ const char *buf_cold; void foo (int path); +#ifdef __APPLE__ +__attribute__ ((section ("__TEXT,__text"))) +#else __attribute__((section(".text"))) +#endif int main (int argc, char *argv[]) { @@ -43,3 +47,4 @@ foo (int path) } /* { dg-final-use { scan-assembler "\.section\[\t \]*\.text\.unlikely\[\\n\\r\]+\[\t \]*\.size\[\t \]*foo\.cold\.0" { target *-*-linux* *-*-gnu* } } } */ +/* { dg-final-use { scan-assembler "\.section\[\t \]*__TEXT,__text_cold\.\*\[\\n\\r\]+_foo\.cold\.0" { target *-*-darwin* } } } */ diff --git a/gcc/testsuite/gcc.dg/tree-prof/section-attr-2.c b/gcc/testsuite/gcc.dg/tree-prof/section-attr-2.c index 898a395..9bdc63a 100644 --- a/gcc/testsuite/gcc.dg/tree-prof/section-attr-2.c +++ b/gcc/testsuite/gcc.dg/tree-prof/section-attr-2.c @@ -28,7 +28,11 @@ main (int argc, char *argv[]) void NOINLINE foo (int path) { +#ifdef __APPLE__ + static int i __attribute__ ((section ("__DATA,__data"))); +#else static int i __attribute__((section(".data"))); +#endif if (path) { for (i = 0; i < SIZE; i++) @@ -42,3 +46,4 @@ foo (int path) } /* { dg-final-use { scan-assembler "\.section\[\t \]*\.text\.unlikely\[\\n\\r\]+\[\t \]*\.size\[\t \]*foo\.cold\.0" { target *-*-linux* *-*-gnu* } } } */ +/* { dg-final-use { scan-assembler "\.section\[\t \]*__TEXT,__text_cold\.\*\[\\n\\r\]+_foo\.cold\.0:" { target *-*-darwin* } } } */ diff --git a/gcc/testsuite/gcc.dg/tree-prof/section-attr-3.c b/gcc/testsuite/gcc.dg/tree-prof/section-attr-3.c index 36829dc..29eee45 100644 --- a/gcc/testsuite/gcc.dg/tree-prof/section-attr-3.c +++ b/gcc/testsuite/gcc.dg/tree-prof/section-attr-3.c @@ -9,7 +9,11 @@ #define NOINLINE __attribute__((noinline)) __attribute__ ((noclone)) const char *sarr[SIZE]; +#ifdef __APPLE__ +const char *buf_hot __attribute__ ((section ("__DATA,__data"))); +#else const char *buf_hot __attribute__ ((section (".data"))); +#endif const char *buf_cold; void foo (int path); @@ -43,3 +47,4 @@ foo (int path) } /* { dg-final-use { scan-assembler "\.section\[\t \]*\.text\.unlikely\[\\n\\r\]+\[\t \]*\.size\[\t \]*foo\.cold\.0" { target *-*-linux* *-*-gnu* } } } */ +/* { dg-final-use { scan-assembler "\.section\[\t \]*__TEXT,__text_cold\.\*\[\\n\\r\]+_foo\.cold\.0:" { target *-*-darwin* } } } */ diff --git a/gcc/testsuite/gcc.dg/wmain.c b/gcc/testsuite/gcc.dg/wmain.c new file mode 100644 index 0000000..06fc26f --- /dev/null +++ b/gcc/testsuite/gcc.dg/wmain.c @@ -0,0 +1,10 @@ +/* { dg-do compile } */ +/* { dg-options "-Wall" } */ + +int main; /* { dg-warning "'main' is usually a function" } */ + +int foo() +{ + int main = 1; /* { dg-bogus "'main' is usually a function" } */ + return main; +} diff --git a/gcc/testsuite/gcc.target/i386/pr83554.c b/gcc/testsuite/gcc.target/i386/pr83554.c index 63ab366..6159715 100644 --- a/gcc/testsuite/gcc.target/i386/pr83554.c +++ b/gcc/testsuite/gcc.target/i386/pr83554.c @@ -1,6 +1,6 @@ /* PR target/83554 */ /* { dg-do compile { target int128 } } */ -/* { dg-options "-Os -mmitigate-rop" } */ +/* { dg-options "-Os" } */ unsigned a; unsigned __int128 diff --git a/gcc/testsuite/gcc.target/i386/rop1.c b/gcc/testsuite/gcc.target/i386/rop1.c deleted file mode 100644 index 0b37267..0000000 --- a/gcc/testsuite/gcc.target/i386/rop1.c +++ /dev/null @@ -1,7 +0,0 @@ -/* { dg-do compile } */ -/* { dg-require-effective-target lp64 } */ -/* { dg-options "-mcmodel=medium -mmitigate-rop" } */ -void -foo (void) -{ -} diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-char.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-char.c new file mode 100644 index 0000000..d50d073 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-char.c @@ -0,0 +1,55 @@ +/* Verify that overloaded built-ins for vec_splat with char + inputs produce the right code. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec -O2" } */ + +#include <altivec.h> + +vector bool char testb_0 (vector bool char x) { return vec_splat (x, 0b00000); } +vector bool char testb_1 (vector bool char x) { return vec_splat (x, 0b00001); } +vector bool char testb_2 (vector bool char x) { return vec_splat (x, 0b00010); } +vector bool char testb_4 (vector bool char x) { return vec_splat (x, 0b00100); } +vector bool char testb_8 (vector bool char x) { return vec_splat (x, 0b01000); } +vector bool char testb_10 (vector bool char x) { return vec_splat (x, 0b10000); } +vector bool char testb_1e (vector bool char x) { return vec_splat (x, 0b11110); } +vector bool char testb_1f (vector bool char x) { return vec_splat (x, 0b11111); } + +vector signed char tests_0 (vector signed char x) { return vec_splat (x, 0b00000); } +vector signed char tests_1 (vector signed char x) { return vec_splat (x, 0b00001); } +vector signed char tests_2 (vector signed char x) { return vec_splat (x, 0b00010); } +vector signed char tests_4 (vector signed char x) { return vec_splat (x, 0b00100); } +vector signed char tests_8 (vector signed char x) { return vec_splat (x, 0b01000); } +vector signed char tests_10 (vector signed char x) { return vec_splat (x, 0b10000); } +vector signed char tests_1e (vector signed char x) { return vec_splat (x, 0b11110); } +vector signed char tests_1f (vector signed char x) { return vec_splat (x, 0b11111); } + +vector unsigned char testu_0 (vector unsigned char x) { return vec_splat (x, 0b00000); } +vector unsigned char testu_1 (vector unsigned char x) { return vec_splat (x, 0b00001); } +vector unsigned char testu_2 (vector unsigned char x) { return vec_splat (x, 0b00010); } +vector unsigned char testu_4 (vector unsigned char x) { return vec_splat (x, 0b00100); } +vector unsigned char testu_8 (vector unsigned char x) { return vec_splat (x, 0b01000); } +vector unsigned char testu_10 (vector unsigned char x) { return vec_splat (x, 0b10000); } +vector unsigned char testu_1e (vector unsigned char x) { return vec_splat (x, 0b11110); } +vector unsigned char testu_1f (vector unsigned char x) { return vec_splat (x, 0b11111); } + +/* Similar tests as above, but the source vector is a known constant. */ +const vector bool char by = {'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p'}; +const vector signed char sy = {'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p'}; +const vector unsigned char uy = {'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p'}; + +vector bool char test_bc (vector bool char x) { return vec_splat (by, 0b00010); } +vector signed char test_sc (vector signed char x) { return vec_splat (sy, 0b00011); } +vector unsigned char test_uc (vector unsigned char x) { return vec_splat (uy, 0b00110); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector bool char test_obc (vector bool char x) { return vec_splat (by, 0b10010); } +vector signed char test_osc (vector signed char x) { return vec_splat (sy, 0b10011); } +vector unsigned char test_ouc (vector unsigned char x) { return vec_splat (uy, 0b10110); } + +// vec_splat() using variable vectors should generate the vspltb instruction. +/* { dg-final { scan-assembler-times "vspltb" 24 } } */ +// vec_splat() using a constant vector should generate a load. +/* { dg-final { scan-assembler-times {\mlvx\M|\mlxvw4x\M} 6 } } */ diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-floatdouble.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-floatdouble.c new file mode 100644 index 0000000..fd74002 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-floatdouble.c @@ -0,0 +1,46 @@ +/* Verify that overloaded built-ins for vec_splat with float and + double inputs produce the right code. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_vsx_ok } */ +/* { dg-options "-mvsx -O2" } */ + +#include <altivec.h> + +vector float testf_00 (vector float x) { return vec_splat (x, 0b00000); } +vector float testf_01 (vector float x) { return vec_splat (x, 0b00001); } +vector float testf_02 (vector float x) { return vec_splat (x, 0b00010); } +vector float testf_04 (vector float x) { return vec_splat (x, 0b00100); } +vector float testf_08 (vector float x) { return vec_splat (x, 0b01000); } +vector float testf_0f (vector float x) { return vec_splat (x, 0b01111); } +vector float testf_10 (vector float x) { return vec_splat (x, 0b10000); } +vector float testf_1e (vector float x) { return vec_splat (x, 0b11110); } +vector float testf_1f (vector float x) { return vec_splat (x, 0b11111); } + +vector double testd_00 (vector double x) { return vec_splat (x, 0b00000); } +vector double testd_01 (vector double x) { return vec_splat (x, 0b00001); } +vector double testd_02 (vector double x) { return vec_splat (x, 0b00010); } +vector double testd_04 (vector double x) { return vec_splat (x, 0b00100); } +vector double testd_08 (vector double x) { return vec_splat (x, 0b01000); } +vector double testd_0f (vector double x) { return vec_splat (x, 0b01111); } +vector double testd_10 (vector double x) { return vec_splat (x, 0b10000); } +vector double testd_1e (vector double x) { return vec_splat (x, 0b11110); } +vector double testd_1f (vector double x) { return vec_splat (x, 0b11111); } + +/* Similar tests as above, but the source vector is a known constant. */ +vector float test_fc () { const vector float y = { 7.1, 8.2, 9.3, 10.4}; return vec_splat (y, 0b00010); } +vector double test_dc () { const vector double y = { 3.0, 5.0 }; return vec_splat (y, 0b00010); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector float test_ofc () { const vector float y = { 7.1, 8.2, 9.3, 10.4}; return vec_splat (y, 0b10010); } +vector double test_odc () { const vector double y = { 3.0, 5.0 }; return vec_splat (y, 0b10010); } + +/* lvx or lxvd2x for loading of the constants. */ +/* vspltw or xxspltw for non-constants with the float type. */ +/* xxpermdi for non-constants with the double type. */ + +/* { dg-final { scan-assembler-times {\mlvx\M|\mlxvd2x\M} 4 } } */ +/* { dg-final { scan-assembler-times "vspltw|xxspltw" 9 } } */ +/* { dg-final { scan-assembler-times "xxpermdi" 9 } } */ + diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-int.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-int.c new file mode 100644 index 0000000..7697853 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-int.c @@ -0,0 +1,50 @@ +/* Verify that overloaded built-ins for vec_splat with int + inputs produce the right code. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec -O2" } */ + +#include <altivec.h> + +vector bool int testb_0 (vector bool int x) { return vec_splat (x, 0b00000); } +vector bool int testb_1 (vector bool int x) { return vec_splat (x, 0b00001); } +vector bool int testb_2 (vector bool int x) { return vec_splat (x, 0b00010); } +vector bool int testb_4 (vector bool int x) { return vec_splat (x, 0b00100); } +vector bool int testb_8 (vector bool int x) { return vec_splat (x, 0b01000); } +vector bool int testb_10 (vector bool int x) { return vec_splat (x, 0b10000); } +vector bool int testb_1e (vector bool int x) { return vec_splat (x, 0b11110); } +vector bool int testb_1f (vector bool int x) { return vec_splat (x, 0b11111); } + +vector signed int tests_0 (vector signed int x) { return vec_splat (x, 0b00000); } +vector signed int tests_1 (vector signed int x) { return vec_splat (x, 0b00001); } +vector signed int tests_2 (vector signed int x) { return vec_splat (x, 0b00010); } +vector signed int tests_4 (vector signed int x) { return vec_splat (x, 0b00100); } +vector signed int tests_8 (vector signed int x) { return vec_splat (x, 0b01000); } +vector signed int tests_10 (vector signed int x) { return vec_splat (x, 0b10000); } +vector signed int tests_1e (vector signed int x) { return vec_splat (x, 0b11110); } +vector signed int tests_1f (vector signed int x) { return vec_splat (x, 0b11111); } + +vector unsigned int testu_0 (vector unsigned int x) { return vec_splat (x, 0b00000); } +vector unsigned int testu_1 (vector unsigned int x) { return vec_splat (x, 0b00001); } +vector unsigned int testu_2 (vector unsigned int x) { return vec_splat (x, 0b00010); } +vector unsigned int testu_4 (vector unsigned int x) { return vec_splat (x, 0b00100); } +vector unsigned int testu_8 (vector unsigned int x) { return vec_splat (x, 0b01000); } +vector unsigned int testu_10 (vector unsigned int x) { return vec_splat (x, 0b10000); } +vector unsigned int testu_1e (vector unsigned int x) { return vec_splat (x, 0b11110); } +vector unsigned int testu_1f (vector unsigned int x) { return vec_splat (x, 0b11111); } + +/* Similar test as above, but the source vector is a known constant. */ +vector bool int test_bic () { const vector bool int y = { 1,2,3,4}; return vec_splat (y, 0b00010); } +vector signed int test_sic () { const vector signed int y = { 1,2,3,4}; return vec_splat (y, 0b00010); } +vector unsigned int test_uic () { const vector unsigned int y = { 1,2,3,4}; return vec_splat (y, 0b00010); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector bool int test_obic () { const vector bool int y = { 1,2,3,4}; return vec_splat (y, 0b10010); } +vector signed int test_osic () { const vector signed int y = { 1,2,3,4}; return vec_splat (y, 0b10010); } +vector unsigned int test_ouic () { const vector unsigned int y = { 1,2,3,4}; return vec_splat (y, 0b10010); } + +/* { dg-final { scan-assembler-times "vspltisw" 6 } } */ +/* { dg-final { scan-assembler-times "vspltw|xxspltw" 24 } } */ + diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-longlong.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-longlong.c new file mode 100644 index 0000000..0720e20 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-longlong.c @@ -0,0 +1,60 @@ +/* Verify that overloaded built-ins for vec_splat with long long + inputs produce the right code. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_vsx_ok } */ +/* { dg-options "-mvsx -O2" } */ + +#include <altivec.h> + +vector bool long long testb_00 (vector bool long long x) { return vec_splat (x, 0b00000); } +vector bool long long testb_01 (vector bool long long x) { return vec_splat (x, 0b00001); } +vector bool long long testb_02 (vector bool long long x) { return vec_splat (x, 0b00010); } +vector bool long long testb_04 (vector bool long long x) { return vec_splat (x, 0b00100); } +vector bool long long testb_08 (vector bool long long x) { return vec_splat (x, 0b01000); } +vector bool long long testb_10 (vector bool long long x) { return vec_splat (x, 0b10000); } +vector bool long long testb_1e (vector bool long long x) { return vec_splat (x, 0b11110); } +vector bool long long testb_1f (vector bool long long x) { return vec_splat (x, 0b11111); } + +vector signed long long tests_00 (vector signed long long x) { return vec_splat (x, 0b00000); } +vector signed long long tests_01 (vector signed long long x) { return vec_splat (x, 0b00001); } +vector signed long long tests_02 (vector signed long long x) { return vec_splat (x, 0b00010); } +vector signed long long tests_04 (vector signed long long x) { return vec_splat (x, 0b00100); } +vector signed long long tests_08 (vector signed long long x) { return vec_splat (x, 0b01000); } +vector signed long long tests_10 (vector signed long long x) { return vec_splat (x, 0b10000); } +vector signed long long tests_1e (vector signed long long x) { return vec_splat (x, 0b11110); } +vector signed long long tests_1f (vector signed long long x) { return vec_splat (x, 0b11111); } + +vector unsigned long long testu_00 (vector unsigned long long x) { return vec_splat (x, 0b00000); } +vector unsigned long long testu_01 (vector unsigned long long x) { return vec_splat (x, 0b00001); } +vector unsigned long long testu_02 (vector unsigned long long x) { return vec_splat (x, 0b00010); } +vector unsigned long long testu_04 (vector unsigned long long x) { return vec_splat (x, 0b00100); } +vector unsigned long long testu_08 (vector unsigned long long x) { return vec_splat (x, 0b01000); } +vector unsigned long long testu_10 (vector unsigned long long x) { return vec_splat (x, 0b10000); } +vector unsigned long long testu_1e (vector unsigned long long x) { return vec_splat (x, 0b11110); } +vector unsigned long long testu_1f (vector unsigned long long x) { return vec_splat (x, 0b11111); } + +/* Similar test as above, but the source vector is a known constant. */ +vector bool long long test_bll () { const vector bool long long y = {12, 23}; return vec_splat (y, 0b00010); } +vector signed long long test_sll () { const vector signed long long y = {34, 45}; return vec_splat (y, 0b00010); } +vector unsigned long long test_ull () { const vector unsigned long long y = {56, 67}; return vec_splat (y, 0b00010); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector bool long long test_obll () { const vector bool long long y = {12, 23}; return vec_splat (y, 0b10010); } +vector signed long long test_osll () { const vector signed long long y = {34, 45}; return vec_splat (y, 0b10010); } +vector unsigned long long test_oull () { const vector unsigned long long y = {56, 67}; return vec_splat (y, 0b10010); } + +/* lvx for the initialization with known constants. */ +/* { dg-final { scan-assembler-times {\mlvx\M|\mlxvd2x\M} 6 } } */ + +/* xxpermdi for vec_splat of long long vectors. + At the time of this writing, the number of xxpermdi instructions + generated could be 24 or 26 or 27, ultimately depending on the + platform and whether or not folding is enabled. + Roughly: + 24 occurrences on older targets (power5) regardless of folding state. + 26 occurrences with gimple folding enabled (through power9). + 27 occurrences with gimple folding disabled (through power9). + So, ensure we have at least one hit. */ +/* { dg-final { scan-assembler "xxpermdi" } } */ diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-pixel.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-pixel.c new file mode 100644 index 0000000..7170588 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-pixel.c @@ -0,0 +1,27 @@ +/* Verify that overloaded built-ins for vec_splat with pixel + inputs produce the right code. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_vsx_ok } */ +/* { dg-options "-mvsx -O2" } */ + +#include <altivec.h> + +vector pixel test1_00 (vector pixel x) { return vec_splat (x, 0b00000); } +vector pixel test1_01 (vector pixel x) { return vec_splat (x, 0b00001); } +vector pixel test1_02 (vector pixel x) { return vec_splat (x, 0b00010); } +vector pixel test1_04 (vector pixel x) { return vec_splat (x, 0b00100); } +vector pixel test1_08 (vector pixel x) { return vec_splat (x, 0b01000); } +vector pixel test1_10 (vector pixel x) { return vec_splat (x, 0b10000); } +vector pixel test1_1e (vector pixel x) { return vec_splat (x, 0b11110); } +vector pixel test1_1f (vector pixel x) { return vec_splat (x, 0b11111); } + +/* Similar test as above, but the source vector is a known constant. */ +vector pixel test_p () { const vector pixel y = { 1,2,3,4}; return vec_splat (y, 0b00010); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector pixel test_op () { const vector pixel y = { 1,2,3,4}; return vec_splat (y, 0b10010); } + +/* { dg-final { scan-assembler-times "vspltish" 2 } } */ +/* { dg-final { scan-assembler-times "vsplth" 8 } } */ diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-short.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-short.c new file mode 100644 index 0000000..96c553f --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-splat-short.c @@ -0,0 +1,49 @@ +/* Verify that overloaded built-ins for vec_splat with short + inputs produce the right results. */ + +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec -O2" } */ + +#include <altivec.h> + +vector bool short testb_00 (vector bool short x) { return vec_splat (x, 0b00000); } +vector bool short testb_01 (vector bool short x) { return vec_splat (x, 0b00001); } +vector bool short testb_02 (vector bool short x) { return vec_splat (x, 0b00010); } +vector bool short testb_04 (vector bool short x) { return vec_splat (x, 0b00100); } +vector bool short testb_08 (vector bool short x) { return vec_splat (x, 0b01000); } +vector bool short testb_10 (vector bool short x) { return vec_splat (x, 0b10000); } +vector bool short testb_1e (vector bool short x) { return vec_splat (x, 0b11110); } +vector bool short testb_1f (vector bool short x) { return vec_splat (x, 0b11111); } + +vector signed short tests_00 (vector signed short x) { return vec_splat (x, 0b00000); } +vector signed short tests_01 (vector signed short x) { return vec_splat (x, 0b00001); } +vector signed short tests_02 (vector signed short x) { return vec_splat (x, 0b00010); } +vector signed short tests_04 (vector signed short x) { return vec_splat (x, 0b00100); } +vector signed short tests_08 (vector signed short x) { return vec_splat (x, 0b01000); } +vector signed short tests_10 (vector signed short x) { return vec_splat (x, 0b10000); } +vector signed short tests_1e (vector signed short x) { return vec_splat (x, 0b11110); } +vector signed short tests_1f (vector signed short x) { return vec_splat (x, 0b11111); } + +vector unsigned short testu_00 (vector unsigned short x) { return vec_splat (x, 0b00000); } +vector unsigned short testu_01 (vector unsigned short x) { return vec_splat (x, 0b00001); } +vector unsigned short testu_02 (vector unsigned short x) { return vec_splat (x, 0b00010); } +vector unsigned short testu_04 (vector unsigned short x) { return vec_splat (x, 0b00100); } +vector unsigned short testu_08 (vector unsigned short x) { return vec_splat (x, 0b01000); } +vector unsigned short testu_10 (vector unsigned short x) { return vec_splat (x, 0b10000); } +vector unsigned short testu_1e (vector unsigned short x) { return vec_splat (x, 0b11110); } +vector unsigned short testu_1f (vector unsigned short x) { return vec_splat (x, 0b11111); } + +/* Similar test as above, but the source vector is a known constant. */ +vector bool short test_bs () { const vector bool short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b00010); } +vector signed short test_ss () { const vector signed short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b00010); } +vector unsigned short test_us () { const vector unsigned short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b00010); } + +/* Similar tests as above, mask is greater than number of elements in the + source vector. */ +vector bool short test_obs () { const vector bool short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b10010); } +vector signed short test_oss () { const vector signed short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b10010); } +vector unsigned short test_ous () { const vector unsigned short y = {1, 2, 3, 4, 5, 6, 7, 8}; return vec_splat (y, 0b10010); } + +/* { dg-final { scan-assembler-times "vspltish" 6 } } */ +/* { dg-final { scan-assembler-times "vsplth" 24 } } */ diff --git a/gcc/testsuite/lib/multiline.exp b/gcc/testsuite/lib/multiline.exp index 84c59e1..5f8b62f 100644 --- a/gcc/testsuite/lib/multiline.exp +++ b/gcc/testsuite/lib/multiline.exp @@ -202,26 +202,6 @@ proc _build_multiline_regex { multiline index } { if {[string match "*^" $line] || [string match "*~" $line]} { # Assume a line containing a caret/range. This must be # an exact match. - } elseif {[string match "*\\|" $line]} { - # Assume a source line with a right-margin. Support - # arbitrary text in place of any whitespace before the - # right-margin, to deal with comments containing containing - # DejaGnu directives. - - # Remove final "\|": - set rexp [string range $rexp 0 [expr [string length $rexp] - 3]] - - # Trim off trailing whitespace: - set old_length [string length $rexp] - set rexp [string trimright $rexp] - set new_length [string length $rexp] - - # Replace the trimmed whitespace with "." chars to match anything: - set ws [string repeat "." [expr $old_length - $new_length]] - set rexp "${rexp}${ws}" - - # Add back the trailing '\|': - set rexp "${rexp}\\|" } else { # Assume that we have a quoted source line. if {![string equal "" $line] } { diff --git a/gcc/toplev.c b/gcc/toplev.c index aa943a8..2789d71 100644 --- a/gcc/toplev.c +++ b/gcc/toplev.c @@ -1112,6 +1112,8 @@ general_init (const char *argv0, bool init_signals) global_dc->show_caret = global_options_init.x_flag_diagnostics_show_caret; + global_dc->show_labels_p + = global_options_init.x_flag_diagnostics_show_labels; global_dc->show_line_numbers_p = global_options_init.x_flag_diagnostics_show_line_numbers; global_dc->show_option_requested diff --git a/libcpp/ChangeLog b/libcpp/ChangeLog index 3eaebfd..2bab8a7 100644 --- a/libcpp/ChangeLog +++ b/libcpp/ChangeLog @@ -1,3 +1,43 @@ +2018-08-16 Nathan Sidwell <nathan@acm.org> + + libcpp/ + * include/cpplib.h (cpp_user_macro_p, cpp_builtin_macro_p) + (cpp_macro_p): New inlines. + * directives.c (do_pragma_poison): Use cpp_macro_p. + (do_ifdef, do_ifndef): Likewise. Use _cpp_maybe_notify_macro_use. + (cpp_pop_definition): Use cpp_macro_p. Move _cpp_free_definition + earlier. Don't zap node directly. + * expr.c (parse_defined): Use _cpp_maybe_notify_macro_use & + cpp_macro_p. + * files.c (should_stack_file): Use cpp_macro_p. + * identifiers.c (cpp_defined): Likewise. + * internal.h (_cpp_mark_macro): Use cpp_user_macro_p. + (_cpp_notify_macro_use): Declare. + (_cpp_maybe_notify_macro_use): New inline. + * lex.c (is_macro): Use cpp_macro_p. + * macro.c (_cpp_warn_if_unused_macro): Use cpp_user_macro_p. + (enter_macro_context): Likewise. + (_cpp_create_definition): Use cpp_builtin_macro_p, + cpp_user_macro_p. Move _cpp_free_definition earlier. + (_cpp_notify_macro_use): New, broken out of multiple call sites. + * traditional.c (fun_like_macro_p): Use cpp_builtin_macro_p. + (maybe_start_funlike, _cpp_scan_out_logical_line) + (push_replacement_text): Likewise. + +2018-08-15 David Malcolm <dmalcolm@redhat.com> + + * include/line-map.h (struct location_range): Add "m_label" field. + (class rich_location): Add description of labels to leading + comment. + (rich_location::rich_location): Add "label" param, defaulting to + NULL. + (rich_location::add_range): Likewise. + (struct label_text): New struct. + (class range_label): New abstract base class. + * line-map.c (rich_location::rich_location): Add "label" param; + use it. + (rich_location::add_range): Likewise. + 2018-08-08 Nathan Sidwell <nathan@acm.org> Make linemap::included_from a location diff --git a/libcpp/include/line-map.h b/libcpp/include/line-map.h index 45ca9ad..fa6f93f 100644 --- a/libcpp/include/line-map.h +++ b/libcpp/include/line-map.h @@ -1274,8 +1274,11 @@ typedef struct bool sysp; } expanded_location; +class range_label; + /* A location within a rich_location: a caret&range, with - the caret potentially flagged for display. */ + the caret potentially flagged for display, and an optional + label. */ struct location_range { @@ -1291,6 +1294,9 @@ struct location_range where "1" and "2" are notionally carets. */ bool m_show_caret_p; + + /* If non-NULL, the label for this range. */ + const range_label *m_label; }; /* A partially-embedded vec for use within rich_location for storing @@ -1432,6 +1438,8 @@ class fixit_hint; Additional ranges may be added to help the user identify other pertinent clauses in a diagnostic. + Ranges can (optionally) be given labels via class range_label. + rich_location instances are intended to be allocated on the stack when generating diagnostics, and to be short-lived. @@ -1477,18 +1485,22 @@ class fixit_hint; equal to their caret point. The frontend overrides the diagnostic context's default caret character for these ranges. - Example E - ********* + Example E (range labels) + ************************ printf ("arg0: %i arg1: %s arg2: %i", ^~ + | + const char * 100, 101, 102); ~~~ + | + int This rich location has two ranges: - range 0 is at the "%s" with start = caret = "%" and finish at - the "s". + the "s". It has a range_label ("const char *"). - range 1 has start/finish covering the "101" and is not flagged for - caret printing; it is perhaps at the start of "101". - + caret printing. The caret is at the start of "101", where its + range_label is printed ("int"). Fix-it hints ------------ @@ -1580,7 +1592,8 @@ class rich_location /* Constructors. */ /* Constructing from a location. */ - rich_location (line_maps *set, source_location loc); + rich_location (line_maps *set, source_location loc, + const range_label *label = NULL); /* Destructor. */ ~rich_location (); @@ -1590,7 +1603,8 @@ class rich_location source_location get_loc (unsigned int idx) const; void - add_range (source_location loc, bool show_caret_p); + add_range (source_location loc, bool show_caret_p, + const range_label *label = NULL); void set_range (unsigned int idx, source_location loc, bool show_caret_p); @@ -1714,6 +1728,54 @@ protected: bool m_fixits_cannot_be_auto_applied; }; +/* A struct for the result of range_label::get_text: a NUL-terminated buffer + of localized text, and a flag to determine if the caller should "free" the + buffer. */ + +struct label_text +{ + label_text () + : m_buffer (NULL), m_caller_owned (false) + {} + + label_text (char *buffer, bool caller_owned) + : m_buffer (buffer), m_caller_owned (caller_owned) + {} + + void maybe_free () + { + if (m_caller_owned) + free (m_buffer); + } + + char *m_buffer; + bool m_caller_owned; +}; + +/* Abstract base class for labelling a range within a rich_location + (e.g. for labelling expressions with their type). + + Generating the text could require non-trivial work, so this work + is delayed (via the "get_text" virtual function) until the diagnostic + printing code "knows" it needs it, thus avoiding doing it e.g. for + warnings that are filtered by command-line flags. This virtual + function also isolates libcpp and the diagnostics subsystem from + the front-end and middle-end-specific code for generating the text + for the labels. + + Like the rich_location instances they annotate, range_label instances + are intended to be allocated on the stack when generating diagnostics, + and to be short-lived. */ + +class range_label +{ + public: + virtual ~range_label () {} + + /* Get localized text for the label. */ + virtual label_text get_text () const = 0; +}; + /* A fix-it hint: a suggested insertion, replacement, or deletion of text. We handle these three types of edit with one class, by representing them as replacement of a half-open range: diff --git a/libcpp/line-map.c b/libcpp/line-map.c index 59dbcfe..fde8c36 100644 --- a/libcpp/line-map.c +++ b/libcpp/line-map.c @@ -1999,7 +1999,8 @@ line_table_dump (FILE *stream, struct line_maps *set, unsigned int num_ordinary, /* Construct a rich_location with location LOC as its initial range. */ -rich_location::rich_location (line_maps *set, source_location loc) : +rich_location::rich_location (line_maps *set, source_location loc, + const range_label *label) : m_line_table (set), m_ranges (), m_column_override (0), @@ -2008,7 +2009,7 @@ rich_location::rich_location (line_maps *set, source_location loc) : m_seen_impossible_fixit (false), m_fixits_cannot_be_auto_applied (false) { - add_range (loc, true); + add_range (loc, true, label); } /* The destructor for class rich_location. */ @@ -2084,11 +2085,13 @@ rich_location::override_column (int column) /* Add the given range. */ void -rich_location::add_range (source_location loc, bool show_caret_p) +rich_location::add_range (source_location loc, bool show_caret_p, + const range_label *label) { location_range range; range.m_loc = loc; range.m_show_caret_p = show_caret_p; + range.m_label = label; m_ranges.push (range); } diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 15d2eb5..ce8ccaf 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,5 +1,58 @@ 2018-08-15 Jonathan Wakely <jwakely@redhat.com> + * include/experimental/regex: Remove begin/end macros for namespace. + * include/experimental/string: Likewise. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_deque.cc: + New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_forward_list.cc: New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_list.cc: + New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_map.cc: + New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_match.cc: + New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_multimap.cc: New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_multiset.cc: New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_set.cc: + New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_string.cc: + New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_unordered_map.cc: New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_unordered_multimap.cc: New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_unordered_multiset.cc: New test. + * testsuite/experimental/polymorphic_allocator/ + pmr_typedefs_unordered_set.cc: New test. + * testsuite/experimental/polymorphic_allocator/pmr_typedefs_vector.cc: + New test. + + * include/bits/uses_allocator.h (__uses_allocator_construct): Qualify + calls to __uses_allocator_construct_impl and __use_alloc. + * include/experimental/memory_resource + (polymorphic_allocator::_M_construct): Remove. + (polymorphic_allocator::construct): Call __uses_allocator_construct. + Qualify calls to __use_alloc. + * include/std/memory_resource (polymorphic_allocator::construct): Fix + type in SFINAE constraint. Use constexpr if instead of tag dispatching + to _S_construct overloads. + (polymorphic_allocator::construct(pair<T1, T2>*, ...)): Fix order of + arguments to _S_construct_p. + (polymorphic_allocator::_S_construct): Remove. + (polymorphic_allocator::_S_construct_p): Return allocators by value + not by reference. + * include/std/scoped_allocator (scoped_allocator_adaptor::construct): + Qualify calls to __use_alloc. + * testsuite/20_util/polymorphic_allocator/construct_pair.cc: New test, + copied from testsuite/20_util/scoped_allocator/construct_pair.cc. + * testsuite/experimental/polymorphic_allocator/1.cc: New test. + * testsuite/experimental/polymorphic_allocator/construct_pair.cc: + New test. + * src/c++17/memory_resource.cc [!_GLIBCXX_HAS_GTHREADS] (atomic_mem_res): Add unsynchronized definition for single-threaded. diff --git a/libstdc++-v3/include/bits/uses_allocator.h b/libstdc++-v3/include/bits/uses_allocator.h index 3ef2830..1d313b7 100644 --- a/libstdc++-v3/include/bits/uses_allocator.h +++ b/libstdc++-v3/include/bits/uses_allocator.h @@ -179,8 +179,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION void __uses_allocator_construct(const _Alloc& __a, _Tp* __ptr, _Args&&... __args) { - __uses_allocator_construct_impl(__use_alloc<_Tp, _Alloc, _Args...>(__a), - __ptr, std::forward<_Args>(__args)...); + std::__uses_allocator_construct_impl( + std::__use_alloc<_Tp, _Alloc, _Args...>(__a), __ptr, + std::forward<_Args>(__args)...); } _GLIBCXX_END_NAMESPACE_VERSION diff --git a/libstdc++-v3/include/experimental/memory_resource b/libstdc++-v3/include/experimental/memory_resource index 61c9ce0..ccb45bf 100644 --- a/libstdc++-v3/include/experimental/memory_resource +++ b/libstdc++-v3/include/experimental/memory_resource @@ -123,27 +123,6 @@ namespace pmr { template<typename _Tp> class polymorphic_allocator { - using __uses_alloc1_ = __uses_alloc1<memory_resource*>; - using __uses_alloc2_ = __uses_alloc2<memory_resource*>; - - template<typename _Tp1, typename... _Args> - void - _M_construct(__uses_alloc0, _Tp1* __p, _Args&&... __args) - { ::new(__p) _Tp1(std::forward<_Args>(__args)...); } - - template<typename _Tp1, typename... _Args> - void - _M_construct(__uses_alloc1_, _Tp1* __p, _Args&&... __args) - { - ::new(__p) _Tp1(allocator_arg, this->resource(), - std::forward<_Args>(__args)...); - } - - template<typename _Tp1, typename... _Args> - void - _M_construct(__uses_alloc2_, _Tp1* __p, _Args&&... __args) - { ::new(__p) _Tp1(std::forward<_Args>(__args)..., this->resource()); } - public: using value_type = _Tp; @@ -178,10 +157,8 @@ namespace pmr { void construct(_Tp1* __p, _Args&&... __args) { - memory_resource* const __resource = this->resource(); - auto __use_tag - = __use_alloc<_Tp1, memory_resource*, _Args...>(__resource); - _M_construct(__use_tag, __p, std::forward<_Args>(__args)...); + std::__uses_allocator_construct(this->resource(), __p, + std::forward<_Args>(__args)...); } // Specializations for pair using piecewise construction @@ -193,9 +170,9 @@ namespace pmr { { memory_resource* const __resource = this->resource(); auto __x_use_tag = - __use_alloc<_Tp1, memory_resource*, _Args1...>(__resource); + std::__use_alloc<_Tp1, memory_resource*, _Args1...>(__resource); auto __y_use_tag = - __use_alloc<_Tp2, memory_resource*, _Args2...>(__resource); + std::__use_alloc<_Tp2, memory_resource*, _Args2...>(__resource); ::new(__p) std::pair<_Tp1, _Tp2>(piecewise_construct, _M_construct_p(__x_use_tag, __x), @@ -247,6 +224,9 @@ namespace pmr { memory_resource* resource() const { return _M_resource; } private: + using __uses_alloc1_ = __uses_alloc1<memory_resource*>; + using __uses_alloc2_ = __uses_alloc2<memory_resource*>; + template<typename _Tuple> _Tuple&& _M_construct_p(__uses_alloc0, _Tuple& __t) diff --git a/libstdc++-v3/include/experimental/regex b/libstdc++-v3/include/experimental/regex index 253231f..eb2af15 100644 --- a/libstdc++-v3/include/experimental/regex +++ b/libstdc++-v3/include/experimental/regex @@ -46,8 +46,6 @@ inline namespace fundamentals_v2 { namespace pmr { -_GLIBCXX_BEGIN_NAMESPACE_CXX11 - template<typename _BidirectionalIterator> using match_results = std::match_results<_BidirectionalIterator, polymorphic_allocator< @@ -58,7 +56,6 @@ _GLIBCXX_BEGIN_NAMESPACE_CXX11 typedef match_results<string::const_iterator> smatch; typedef match_results<wstring::const_iterator> wsmatch; -_GLIBCXX_END_NAMESPACE_CXX11 } // namespace pmr } // namespace fundamentals_v2 diff --git a/libstdc++-v3/include/experimental/string b/libstdc++-v3/include/experimental/string index b340e2b..f101255 100644 --- a/libstdc++-v3/include/experimental/string +++ b/libstdc++-v3/include/experimental/string @@ -62,9 +62,8 @@ inline namespace fundamentals_v2 __cont.end()); } - namespace pmr { - _GLIBCXX_BEGIN_NAMESPACE_CXX11 - + namespace pmr + { // basic_string using polymorphic allocator in namespace pmr template<typename _CharT, typename _Traits = char_traits<_CharT>> using basic_string = @@ -77,7 +76,6 @@ inline namespace fundamentals_v2 typedef basic_string<char32_t> u32string; typedef basic_string<wchar_t> wstring; - _GLIBCXX_END_NAMESPACE_CXX11 } // namespace pmr } // namespace fundamentals_v2 } // namespace experimental diff --git a/libstdc++-v3/include/std/memory_resource b/libstdc++-v3/include/std/memory_resource index bb4e315..7dc35ae 100644 --- a/libstdc++-v3/include/std/memory_resource +++ b/libstdc++-v3/include/std/memory_resource @@ -163,14 +163,20 @@ namespace pmr template<typename _Tp1, typename... _Args> __attribute__((__nonnull__)) - typename __not_pair<_Tp>::type + typename __not_pair<_Tp1>::type construct(_Tp1* __p, _Args&&... __args) { // _GLIBCXX_RESOLVE_LIB_DEFECTS // 2969. polymorphic_allocator::construct() shouldn't pass resource() - auto __use_tag - = __use_alloc<_Tp1, polymorphic_allocator, _Args...>(*this); - _S_construct(__use_tag, __p, std::forward<_Args>(__args)...); + using __use_tag + = std::__uses_alloc_t<_Tp1, polymorphic_allocator, _Args...>; + if constexpr (is_base_of_v<__uses_alloc0, __use_tag>) + ::new(__p) _Tp1(std::forward<_Args>(__args)...); + else if constexpr (is_base_of_v<__uses_alloc1_, __use_tag>) + ::new(__p) _Tp1(allocator_arg, *this, + std::forward<_Args>(__args)...); + else + ::new(__p) _Tp1(std::forward<_Args>(__args)..., *this); } template<typename _Tp1, typename _Tp2, @@ -188,8 +194,8 @@ namespace pmr index_sequence_for<_Args2...> __y_i; ::new(__p) pair<_Tp1, _Tp2>(piecewise_construct, - _S_construct_p(__x_tag, __x, __x_i), - _S_construct_p(__y_tag, __y, __y_i)); + _S_construct_p(__x_tag, __x_i, __x), + _S_construct_p(__y_tag, __y_i, __y)); } template<typename _Tp1, typename _Tp2> @@ -247,31 +253,13 @@ namespace pmr using __uses_alloc1_ = __uses_alloc1<polymorphic_allocator>; using __uses_alloc2_ = __uses_alloc2<polymorphic_allocator>; - template<typename _Tp1, typename... _Args> - static void - _S_construct(__uses_alloc0, _Tp1* __p, _Args&&... __args) - { ::new(__p) _Tp1(std::forward<_Args>(__args)...); } - - template<typename _Tp1, typename... _Args> - static void - _S_construct(__uses_alloc1_ __ua, _Tp1* __p, _Args&&... __args) - { - ::new(__p) _Tp1(allocator_arg, *__ua._M_a, - std::forward<_Args>(__args)...); - } - - template<typename _Tp1, typename... _Args> - static void - _S_construct(__uses_alloc2_ __ua, _Tp1* __p, _Args&&... __args) - { ::new(__p) _Tp1(std::forward<_Args>(__args)..., *__ua._M_a); } - template<typename _Ind, typename... _Args> static tuple<_Args&&...> _S_construct_p(__uses_alloc0, _Ind, tuple<_Args...>& __t) { return std::move(__t); } template<size_t... _Ind, typename... _Args> - static tuple<allocator_arg_t, polymorphic_allocator&, _Args&&...> + static tuple<allocator_arg_t, polymorphic_allocator, _Args&&...> _S_construct_p(__uses_alloc1_ __ua, index_sequence<_Ind...>, tuple<_Args...>& __t) { @@ -281,7 +269,7 @@ namespace pmr } template<size_t... _Ind, typename... _Args> - static tuple<_Args&&..., polymorphic_allocator&> + static tuple<_Args&&..., polymorphic_allocator> _S_construct_p(__uses_alloc2_ __ua, index_sequence<_Ind...>, tuple<_Args...>& __t) { return { std::get<_Ind>(std::move(__t))..., *__ua._M_a }; } diff --git a/libstdc++-v3/include/std/scoped_allocator b/libstdc++-v3/include/std/scoped_allocator index ea62f11..f1f5dd9 100644 --- a/libstdc++-v3/include/std/scoped_allocator +++ b/libstdc++-v3/include/std/scoped_allocator @@ -361,7 +361,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION { auto& __inner = inner_allocator(); auto __use_tag - = __use_alloc<_Tp, inner_allocator_type, _Args...>(__inner); + = std::__use_alloc<_Tp, inner_allocator_type, _Args...>(__inner); _M_construct(__use_tag, __p, std::forward<_Args>(__args)...); } @@ -375,9 +375,9 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION // 2203. wrong argument types for piecewise construction auto& __inner = inner_allocator(); auto __x_use_tag - = __use_alloc<_T1, inner_allocator_type, _Args1...>(__inner); + = std::__use_alloc<_T1, inner_allocator_type, _Args1...>(__inner); auto __y_use_tag - = __use_alloc<_T2, inner_allocator_type, _Args2...>(__inner); + = std::__use_alloc<_T2, inner_allocator_type, _Args2...>(__inner); typename _Build_index_tuple<sizeof...(_Args1)>::__type __x_indices; typename _Build_index_tuple<sizeof...(_Args2)>::__type __y_indices; typedef __outermost_alloc_traits<scoped_allocator_adaptor> _O_traits; diff --git a/libstdc++-v3/testsuite/20_util/polymorphic_allocator/construct_pair.cc b/libstdc++-v3/testsuite/20_util/polymorphic_allocator/construct_pair.cc new file mode 100644 index 0000000..d9cab04 --- /dev/null +++ b/libstdc++-v3/testsuite/20_util/polymorphic_allocator/construct_pair.cc @@ -0,0 +1,110 @@ +// Copyright (C) 2016-2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-options "-std=gnu++17" } +// { dg-do run { target c++17 } } + +#include <memory_resource> +#include <utility> +#include <tuple> + +struct do_not_copy { + do_not_copy() = default; + do_not_copy(const do_not_copy&) { throw 1; } +}; + +void +test01() +{ + struct X { + X(do_not_copy&&) { } + }; + + using pair = std::pair<X, int>; + std::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<do_not_copy>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +void +test02() +{ + struct X { + using allocator_type = std::pmr::polymorphic_allocator<int>; + X(do_not_copy&&, const allocator_type&) { } + }; + + using pair = std::pair<X, int>; + std::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<do_not_copy>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +void +test03() +{ + struct X { + using allocator_type = std::pmr::polymorphic_allocator<int>; + X(std::allocator_arg_t, const allocator_type&, do_not_copy&&) { } + }; + + using pair = std::pair<X, int>; + std::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<do_not_copy>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +void +test04() +{ + struct X + { + using allocator_type = std::pmr::polymorphic_allocator<int>; + X() = default; + X(const X&) { throw 1; } + X(const X&, const allocator_type&) { } + }; + + struct Y + { + using allocator_type = std::pmr::polymorphic_allocator<int>; + Y() = default; + Y(const Y&) = delete; + Y(std::allocator_arg_t, const allocator_type&, const Y&) { } + }; + + using pair_type = std::pair<X, Y>; + std::pmr::polymorphic_allocator<pair_type> a; + auto ptr = a.allocate(1); + /* not const */ pair_type p; + a.construct(ptr, p); // LWG 2975 + a.deallocate(ptr, 1); +} + +int main() +{ + test01(); + test02(); + test03(); + test04(); +} diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/1.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/1.cc new file mode 100644 index 0000000..9046347 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/1.cc @@ -0,0 +1,37 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/memory_resource> + +struct X { int i = 0; }; + +using test_type = std::experimental::pmr::polymorphic_allocator<X>; + +static_assert(std::is_default_constructible<test_type>{}, ""); +static_assert(std::is_destructible<test_type>{}, ""); +static_assert(std::is_copy_constructible<test_type>{}, ""); +// N.B. std::pmr::polymorphic_allocator is not assignable, see p0337r0 +static_assert(std::is_copy_assignable<test_type>{}, ""); +static_assert(std::is_constructible<test_type, + std::experimental::pmr::memory_resource*>{}, ""); + +static_assert(std::is_same<test_type::value_type, X>{}, ""); + +static_assert(!std::is_polymorphic<test_type>{}, ""); +static_assert(!std::is_final<test_type>{}, ""); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/construct_pair.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/construct_pair.cc new file mode 100644 index 0000000..1708f5e --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/construct_pair.cc @@ -0,0 +1,78 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do run { target c++14 } } + +#include <experimental/memory_resource> +#include <utility> +#include <tuple> + +struct A { }; + +void +test01() +{ + struct X { + X(A&&) { } + }; + + using pair = std::pair<X, int>; + std::experimental::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<A>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +void +test02() +{ + struct X { + using allocator_type = std::experimental::pmr::polymorphic_allocator<int>; + X(A&&, const allocator_type&) { } + }; + + using pair = std::pair<X, int>; + std::experimental::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<A>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +void +test03() +{ + struct X { + using allocator_type = std::experimental::pmr::polymorphic_allocator<int>; + X(std::allocator_arg_t, const allocator_type&, A&&) { } + }; + + using pair = std::pair<X, int>; + std::experimental::pmr::polymorphic_allocator<pair> a; + auto ptr = a.allocate(1); + a.construct(ptr, std::piecewise_construct, + std::tuple<A>{}, std::make_tuple(1)); + a.deallocate(ptr, 1); +} + +int main() +{ + test01(); + test02(); + test03(); +} diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_deque.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_deque.cc new file mode 100644 index 0000000..2b47579 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_deque.cc @@ -0,0 +1,28 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/deque> + +namespace xpmr = std::experimental::pmr; + +struct X { }; + +static_assert(std::is_same<xpmr::deque<X>, + std::deque<X, xpmr::polymorphic_allocator<X>>>::value, + "pmr::deque"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_forward_list.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_forward_list.cc new file mode 100644 index 0000000..ac2dd52 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_forward_list.cc @@ -0,0 +1,28 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/forward_list> + +namespace xpmr = std::experimental::pmr; + +struct X { }; + +static_assert(std::is_same<xpmr::forward_list<X>, + std::forward_list<X, xpmr::polymorphic_allocator<X>>>::value, + "pmr::forward_list"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_list.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_list.cc new file mode 100644 index 0000000..aea5c80 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_list.cc @@ -0,0 +1,28 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/list> + +namespace xpmr = std::experimental::pmr; + +struct X { }; + +static_assert(std::is_same<xpmr::list<X>, + std::list<X, xpmr::polymorphic_allocator<X>>>::value, + "pmr::list"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_map.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_map.cc new file mode 100644 index 0000000..2074022 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_map.cc @@ -0,0 +1,35 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/map> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Y { }; +struct Cmp { bool operator()(X, X) const { return false; } }; + +static_assert(std::is_same<xpmr::map<X, Y>, + std::map<X, Y, std::less<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::map"); +static_assert(std::is_same<xpmr::map<X, Y, Cmp>, + std::map<X, Y, Cmp, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::map"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_match.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_match.cc new file mode 100644 index 0000000..c237f1e --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_match.cc @@ -0,0 +1,49 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/regex> + +namespace xpmr = std::experimental::pmr; + +struct X; +static_assert(std::is_same<xpmr::match_results<X*>, + std::match_results<X*, + xpmr::polymorphic_allocator<std::sub_match<X*>>>>::value, + "pmr::match_results"); + +static_assert(std::is_same<xpmr::cmatch, + std::match_results<const char*, + xpmr::polymorphic_allocator<std::sub_match<const char*>>>>::value, + "pmr::cmatch"); +static_assert(std::is_same<xpmr::smatch, + std::match_results<xpmr::string::const_iterator, + xpmr::polymorphic_allocator< + std::sub_match<xpmr::string::const_iterator>>>>::value, + "pmr::smatch"); +#ifdef _GLIBCXX_USE_WCHAR_T +static_assert(std::is_same<xpmr::wcmatch, + std::match_results<const wchar_t*, + xpmr::polymorphic_allocator<std::sub_match<const wchar_t*>>>>::value, + "pmr::wcmatch"); +static_assert(std::is_same<xpmr::wsmatch, + std::match_results<xpmr::wstring::const_iterator, + xpmr::polymorphic_allocator< + std::sub_match<xpmr::wstring::const_iterator>>>>::value, + "pmr::wsmatch"); +#endif diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multimap.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multimap.cc new file mode 100644 index 0000000..e6acaf4 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multimap.cc @@ -0,0 +1,35 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/map> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Y { }; +struct Cmp { bool operator()(X, X) const { return false; } }; + +static_assert(std::is_same<xpmr::multimap<X, Y>, + std::multimap<X, Y, std::less<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::multimap"); +static_assert(std::is_same<xpmr::multimap<X, Y, Cmp>, + std::multimap<X, Y, Cmp, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::multimap"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multiset.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multiset.cc new file mode 100644 index 0000000..e98c556 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_multiset.cc @@ -0,0 +1,32 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/set> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Cmp { bool operator()(X, X) const { return false; } }; + +static_assert(std::is_same<xpmr::multiset<X>, + std::multiset<X, std::less<X>, xpmr::polymorphic_allocator<X>>>::value, + "pmr::multiset"); +static_assert(std::is_same<xpmr::multiset<X, Cmp>, + std::multiset<X, Cmp, xpmr::polymorphic_allocator<X>>>::value, + "pmr::multiset"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_set.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_set.cc new file mode 100644 index 0000000..182a11e --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_set.cc @@ -0,0 +1,32 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/set> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Cmp { bool operator()(X, X) const { return false; } }; + +static_assert(std::is_same<xpmr::set<X>, + std::set<X, std::less<X>, xpmr::polymorphic_allocator<X>>>::value, + "pmr::set"); +static_assert(std::is_same<xpmr::set<X, Cmp>, + std::set<X, Cmp, xpmr::polymorphic_allocator<X>>>::value, + "pmr::set"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_string.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_string.cc new file mode 100644 index 0000000..3cf8c94 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_string.cc @@ -0,0 +1,60 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/string> + +namespace xpmr = std::experimental::pmr; + +struct T : std::char_traits<char> { }; + +static_assert(std::is_same<xpmr::basic_string<char>, + std::basic_string<char, std::char_traits<char>, + xpmr::polymorphic_allocator<char>>>::value, + "pmr::basic_string"); +static_assert(std::is_same<xpmr::basic_string<char, T>, + std::basic_string<char, T, xpmr::polymorphic_allocator<char>>>::value, + "pmr::basic_string"); + +static_assert(std::is_same<xpmr::string, + std::basic_string<char, std::char_traits<char>, + xpmr::polymorphic_allocator<char>>>::value, + "pmr::string"); +static_assert(std::is_same<xpmr::u16string, + std::basic_string<char16_t, std::char_traits<char16_t>, + xpmr::polymorphic_allocator<char16_t>>>::value, + "pmr::u16string"); +static_assert(std::is_same<xpmr::u32string, + std::basic_string<char32_t, std::char_traits<char32_t>, + xpmr::polymorphic_allocator<char32_t>>>::value, + "pmr::u32string"); + +#ifdef _GLIBCXX_USE_WCHAR_T +static_assert(std::is_same<xpmr::basic_string<wchar_t>, + std::basic_string<wchar_t, std::char_traits<wchar_t>, + xpmr::polymorphic_allocator<wchar_t>>>::value, + "pmr::basic_string<wchar_t>"); +static_assert(std::is_same<xpmr::basic_string<wchar_t, T>, + std::basic_string<wchar_t, T, xpmr::polymorphic_allocator<wchar_t>>>::value, + "pmr::basic_string<wchar_t>"); + +static_assert(std::is_same<xpmr::wstring, + std::basic_string<wchar_t, std::char_traits<wchar_t>, + xpmr::polymorphic_allocator<wchar_t>>>::value, + "pmr::wstring"); +#endif diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_map.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_map.cc new file mode 100644 index 0000000..15e00e7 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_map.cc @@ -0,0 +1,40 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/unordered_map> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Y { }; +struct Hash { std::size_t operator()(X) const { return 0; } }; +struct Eq { bool operator()(X, X) const { return true; } }; + +static_assert(std::is_same<xpmr::unordered_map<X, Y>, + std::unordered_map<X, Y, std::hash<X>, std::equal_to<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_map"); +static_assert(std::is_same<xpmr::unordered_map<X, Y, Hash>, + std::unordered_map<X, Y, Hash, std::equal_to<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_map"); +static_assert(std::is_same<xpmr::unordered_map<X, Y, Hash, Eq>, + std::unordered_map<X, Y, Hash, Eq, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_map"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multimap.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multimap.cc new file mode 100644 index 0000000..67054ff --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multimap.cc @@ -0,0 +1,40 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/unordered_map> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Y { }; +struct Hash { std::size_t operator()(X) const { return 0; } }; +struct Eq { bool operator()(X, X) const { return true; } }; + +static_assert(std::is_same<xpmr::unordered_multimap<X, Y>, + std::unordered_multimap<X, Y, std::hash<X>, std::equal_to<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_multimap"); +static_assert(std::is_same<xpmr::unordered_multimap<X, Y, Hash>, + std::unordered_multimap<X, Y, Hash, std::equal_to<X>, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_multimap"); +static_assert(std::is_same<xpmr::unordered_multimap<X, Y, Hash, Eq>, + std::unordered_multimap<X, Y, Hash, Eq, + xpmr::polymorphic_allocator<std::pair<const X, Y>>>>::value, + "pmr::unordered_multimap"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multiset.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multiset.cc new file mode 100644 index 0000000..aaba4d3 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_multiset.cc @@ -0,0 +1,39 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/unordered_set> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Hash { std::size_t operator()(X) const { return 0; } }; +struct Eq { bool operator()(X, X) const { return true; } }; + +static_assert(std::is_same<xpmr::unordered_multiset<X>, + std::unordered_multiset<X, std::hash<X>, std::equal_to<X>, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_multiset"); +static_assert(std::is_same<xpmr::unordered_multiset<X, Hash>, + std::unordered_multiset<X, Hash, std::equal_to<X>, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_multiset"); +static_assert(std::is_same<xpmr::unordered_multiset<X, Hash, Eq>, + std::unordered_multiset<X, Hash, Eq, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_multiset"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_set.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_set.cc new file mode 100644 index 0000000..b90051e --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_unordered_set.cc @@ -0,0 +1,39 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/unordered_set> + +namespace xpmr = std::experimental::pmr; + +struct X { }; +struct Hash { std::size_t operator()(X) const { return 0; } }; +struct Eq { bool operator()(X, X) const { return true; } }; + +static_assert(std::is_same<xpmr::unordered_set<X>, + std::unordered_set<X, std::hash<X>, std::equal_to<X>, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_set"); +static_assert(std::is_same<xpmr::unordered_set<X, Hash>, + std::unordered_set<X, Hash, std::equal_to<X>, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_set"); +static_assert(std::is_same<xpmr::unordered_set<X, Hash, Eq>, + std::unordered_set<X, Hash, Eq, + xpmr::polymorphic_allocator<X>>>::value, + "pmr::unordered_set"); diff --git a/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_vector.cc b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_vector.cc new file mode 100644 index 0000000..f780aa5 --- /dev/null +++ b/libstdc++-v3/testsuite/experimental/polymorphic_allocator/pmr_typedefs_vector.cc @@ -0,0 +1,28 @@ +// Copyright (C) 2018 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library 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. + +// This library 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 this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// { dg-do compile { target c++14 } } + +#include <experimental/vector> + +namespace xpmr = std::experimental::pmr; + +struct X { }; + +static_assert(std::is_same<xpmr::vector<X>, + std::vector<X, xpmr::polymorphic_allocator<X>>>::value, + "pmr::vector"); |