From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 108176 invoked by alias); 8 Oct 2018 10:34:57 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Received: (qmail 108161 invoked by uid 89); 8 Oct 2018 10:34:57 -0000 Authentication-Results: sourceware.org; auth=none X-Spam-SWARE-Status: No, score=-26.9 required=5.0 tests=BAYES_00,GIT_PATCH_0,GIT_PATCH_1,GIT_PATCH_2,GIT_PATCH_3,SPF_PASS autolearn=ham version=3.3.2 spammy=architectural, closely, Extension, attaching X-HELO: mx1.suse.de Received: from mx2.suse.de (HELO mx1.suse.de) (195.135.220.15) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Mon, 08 Oct 2018 10:34:54 +0000 Received: from relay2.suse.de (unknown [195.135.220.254]) by mx1.suse.de (Postfix) with ESMTP id 79B47AEAF; Mon, 8 Oct 2018 10:34:52 +0000 (UTC) Subject: Re: [PATCH] Provide extension hint for aarch64 target (PR driver/83193). To: Kyrill Tkachov , "gcc-patches@gcc.gnu.org" Cc: Ramana Radhakrishnan , "Richard Earnshaw (lists)" , James Greenhalgh References: <37fcbcb3-eab3-9929-b84f-110c1646a717@suse.cz> <5BB5DD87.5080503@foss.arm.com> From: =?UTF-8?Q?Martin_Li=c5=a1ka?= Message-ID: <09de624a-ee68-1106-f92e-e856b060ee1e@suse.cz> Date: Mon, 08 Oct 2018 10:53:00 -0000 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:60.0) Gecko/20100101 Thunderbird/60.0 MIME-Version: 1.0 In-Reply-To: <5BB5DD87.5080503@foss.arm.com> Content-Type: multipart/mixed; boundary="------------3292220C9863C2B03A090946" X-IsSubscribed: yes X-SW-Source: 2018-10/txt/msg00409.txt.bz2 This is a multi-part message in MIME format. --------------3292220C9863C2B03A090946 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit Content-length: 57 Hi. I'm attaching updated version of the patch. Martin --------------3292220C9863C2B03A090946 Content-Type: text/x-patch; name="0001-Provide-extension-hint-for-aarch64-target-PR-driver-.patch" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename*0="0001-Provide-extension-hint-for-aarch64-target-PR-driver-.pa"; filename*1="tch" Content-length: 14752 >From d36974540cda9fb0e159103fdcf92d26ef2f1b94 Mon Sep 17 00:00:00 2001 From: marxin Date: Thu, 4 Oct 2018 16:31:49 +0200 Subject: [PATCH] Provide extension hint for aarch64 target (PR driver/83193). gcc/ChangeLog: 2018-10-05 Martin Liska PR driver/83193 * common/config/aarch64/aarch64-common.c (aarch64_parse_extension): Add new argument invalid_extension. (aarch64_get_all_extension_candidates): New function. (aarch64_rewrite_selected_cpu): Add NULL to function call. * config/aarch64/aarch64-protos.h (aarch64_parse_extension): Add new argument. (aarch64_get_all_extension_candidates): New function. * config/aarch64/aarch64.c (aarch64_parse_arch): Add new argument invalid_extension. (aarch64_parse_cpu): Likewise. (aarch64_print_hint_for_extensions): New function. (aarch64_validate_mcpu): Provide hint about invalid extension. (aarch64_validate_march): Likewise. (aarch64_handle_attr_arch): Pass new argument. (aarch64_handle_attr_cpu): Provide hint about invalid extension. (aarch64_handle_attr_isa_flags): Likewise. gcc/testsuite/ChangeLog: 2018-10-05 Martin Liska PR driver/83193 * gcc.target/aarch64/spellcheck_7.c: New test. * gcc.target/aarch64/spellcheck_8.c: New test. * gcc.target/aarch64/spellcheck_9.c: New test. --- gcc/common/config/aarch64/aarch64-common.c | 24 +++++- gcc/config/aarch64/aarch64-protos.h | 4 +- gcc/config/aarch64/aarch64.c | 75 +++++++++++++++---- .../gcc.target/aarch64/spellcheck_7.c | 12 +++ .../gcc.target/aarch64/spellcheck_8.c | 13 ++++ .../gcc.target/aarch64/spellcheck_9.c | 13 ++++ 6 files changed, 121 insertions(+), 20 deletions(-) create mode 100644 gcc/testsuite/gcc.target/aarch64/spellcheck_7.c create mode 100644 gcc/testsuite/gcc.target/aarch64/spellcheck_8.c create mode 100644 gcc/testsuite/gcc.target/aarch64/spellcheck_9.c diff --git a/gcc/common/config/aarch64/aarch64-common.c b/gcc/common/config/aarch64/aarch64-common.c index ffddc4d16d8..2bebe70c021 100644 --- a/gcc/common/config/aarch64/aarch64-common.c +++ b/gcc/common/config/aarch64/aarch64-common.c @@ -220,10 +220,13 @@ static const struct arch_to_arch_name all_architectures[] = /* Parse the architecture extension string STR and update ISA_FLAGS with the architecture features turned on or off. Return a - aarch64_parse_opt_result describing the result. */ + aarch64_parse_opt_result describing the result. + When the STR string contains an invalid extension, + a copy of the string is created and stored to INVALID_EXTENSION. */ enum aarch64_parse_opt_result -aarch64_parse_extension (const char *str, unsigned long *isa_flags) +aarch64_parse_extension (const char *str, unsigned long *isa_flags, + char **invalid_extension) { /* The extension string is parsed left to right. */ const struct aarch64_option_extension *opt = NULL; @@ -274,6 +277,11 @@ aarch64_parse_extension (const char *str, unsigned long *isa_flags) if (opt->name == NULL) { /* Extension not found in list. */ + if (invalid_extension) + { + *invalid_extension = xstrdup (str); + (*invalid_extension)[len] = '\0'; + } return AARCH64_PARSE_INVALID_FEATURE; } @@ -283,6 +291,16 @@ aarch64_parse_extension (const char *str, unsigned long *isa_flags) return AARCH64_PARSE_OK; } +/* Append all architecture extension candidates to the CANDIDATES vector. */ + +void +aarch64_get_all_extension_candidates (auto_vec *candidates) +{ + const struct aarch64_option_extension *opt; + for (opt = all_extensions; opt->name != NULL; opt++) + candidates->safe_push (opt->name); +} + /* Return a string representation of ISA_FLAGS. DEFAULT_ARCH_FLAGS gives the default set of flags which are implied by whatever -march we'd put out. Our job is to figure out the minimal set of "+" and @@ -370,7 +388,7 @@ aarch64_rewrite_selected_cpu (const char *name) fatal_error (input_location, "unknown value %qs for -mcpu", name); unsigned long extensions = p_to_a->flags; - aarch64_parse_extension (extension_str.c_str (), &extensions); + aarch64_parse_extension (extension_str.c_str (), &extensions, NULL); std::string outstr = a_to_an->arch_name + aarch64_get_extension_string_for_isa_flags (extensions, diff --git a/gcc/config/aarch64/aarch64-protos.h b/gcc/config/aarch64/aarch64-protos.h index 5f18837418e..2f1b0b10250 100644 --- a/gcc/config/aarch64/aarch64-protos.h +++ b/gcc/config/aarch64/aarch64-protos.h @@ -616,7 +616,9 @@ bool aarch64_handle_option (struct gcc_options *, struct gcc_options *, const struct cl_decoded_option *, location_t); const char *aarch64_rewrite_selected_cpu (const char *name); enum aarch64_parse_opt_result aarch64_parse_extension (const char *, - unsigned long *); + unsigned long *, + char **); +void aarch64_get_all_extension_candidates (auto_vec *candidates); std::string aarch64_get_extension_string_for_isa_flags (unsigned long, unsigned long); diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c index d385b246a74..39895c7ede3 100644 --- a/gcc/config/aarch64/aarch64.c +++ b/gcc/config/aarch64/aarch64.c @@ -10513,11 +10513,13 @@ static void initialize_aarch64_code_model (struct gcc_options *); /* Parse the TO_PARSE string and put the architecture struct that it selects into RES and the architectural features into ISA_FLAGS. Return an aarch64_parse_opt_result describing the parse result. - If there is an error parsing, RES and ISA_FLAGS are left unchanged. */ + If there is an error parsing, RES and ISA_FLAGS are left unchanged. + When the TO_PARSE string contains an invalid extension, + a copy of the string is created and stored to INVALID_EXTENSION. */ static enum aarch64_parse_opt_result aarch64_parse_arch (const char *to_parse, const struct processor **res, - unsigned long *isa_flags) + unsigned long *isa_flags, char **invalid_extension) { char *ext; const struct processor *arch; @@ -10548,7 +10550,7 @@ aarch64_parse_arch (const char *to_parse, const struct processor **res, { /* TO_PARSE string contains at least one extension. */ enum aarch64_parse_opt_result ext_res - = aarch64_parse_extension (ext, &isa_temp); + = aarch64_parse_extension (ext, &isa_temp, invalid_extension); if (ext_res != AARCH64_PARSE_OK) return ext_res; @@ -10568,11 +10570,13 @@ aarch64_parse_arch (const char *to_parse, const struct processor **res, /* Parse the TO_PARSE string and put the result tuning in RES and the architecture flags in ISA_FLAGS. Return an aarch64_parse_opt_result describing the parse result. If there is an error parsing, RES and - ISA_FLAGS are left unchanged. */ + ISA_FLAGS are left unchanged. + When the TO_PARSE string contains an invalid extension, + a copy of the string is created and stored to INVALID_EXTENSION. */ static enum aarch64_parse_opt_result aarch64_parse_cpu (const char *to_parse, const struct processor **res, - unsigned long *isa_flags) + unsigned long *isa_flags, char **invalid_extension) { char *ext; const struct processor *cpu; @@ -10604,7 +10608,7 @@ aarch64_parse_cpu (const char *to_parse, const struct processor **res, { /* TO_PARSE string contains at least one extension. */ enum aarch64_parse_opt_result ext_res - = aarch64_parse_extension (ext, &isa_temp); + = aarch64_parse_extension (ext, &isa_temp, invalid_extension); if (ext_res != AARCH64_PARSE_OK) return ext_res; @@ -11086,6 +11090,26 @@ aarch64_print_hint_for_arch (const char *str) aarch64_print_hint_for_core_or_arch (str, true); } + +/* Print a hint with a suggestion for an extension name + that most closely resembles what the user passed in STR. */ + +void +aarch64_print_hint_for_extensions (const char *str) +{ + auto_vec candidates; + aarch64_get_all_extension_candidates (&candidates); + char *s; + const char *hint = candidates_list_and_hint (str, s, candidates); + if (hint) + inform (input_location, "valid arguments are: %s;" + " did you mean %qs?", s, hint); + else + inform (input_location, "valid arguments are: %s;", s); + + XDELETEVEC (s); +} + /* Validate a command-line -mcpu option. Parse the cpu and extensions (if any) specified in STR and throw errors if appropriate. Put the results if they are valid in RES and ISA_FLAGS. Return whether the option is @@ -11095,8 +11119,9 @@ static bool aarch64_validate_mcpu (const char *str, const struct processor **res, unsigned long *isa_flags) { + char *invalid_extension; enum aarch64_parse_opt_result parse_res - = aarch64_parse_cpu (str, res, isa_flags); + = aarch64_parse_cpu (str, res, isa_flags, &invalid_extension); if (parse_res == AARCH64_PARSE_OK) return true; @@ -11111,7 +11136,10 @@ aarch64_validate_mcpu (const char *str, const struct processor **res, aarch64_print_hint_for_core (str); break; case AARCH64_PARSE_INVALID_FEATURE: - error ("invalid feature modifier in %<-mcpu=%s%>", str); + error ("invalid feature modifier %qs in %<-mcpu=%s%>", + invalid_extension, str); + aarch64_print_hint_for_extensions (invalid_extension); + free (invalid_extension); break; default: gcc_unreachable (); @@ -11129,8 +11157,9 @@ static bool aarch64_validate_march (const char *str, const struct processor **res, unsigned long *isa_flags) { + char *invalid_extension; enum aarch64_parse_opt_result parse_res - = aarch64_parse_arch (str, res, isa_flags); + = aarch64_parse_arch (str, res, isa_flags, &invalid_extension); if (parse_res == AARCH64_PARSE_OK) return true; @@ -11145,7 +11174,10 @@ aarch64_validate_march (const char *str, const struct processor **res, aarch64_print_hint_for_arch (str); break; case AARCH64_PARSE_INVALID_FEATURE: - error ("invalid feature modifier in %<-march=%s%>", str); + error ("invalid feature modifier %qs in %<-march=%s%>", + invalid_extension, str); + aarch64_print_hint_for_extensions (invalid_extension); + free (invalid_extension); break; default: gcc_unreachable (); @@ -11545,8 +11577,9 @@ static bool aarch64_handle_attr_arch (const char *str) { const struct processor *tmp_arch = NULL; + char *invalid_extension; enum aarch64_parse_opt_result parse_res - = aarch64_parse_arch (str, &tmp_arch, &aarch64_isa_flags); + = aarch64_parse_arch (str, &tmp_arch, &aarch64_isa_flags, &invalid_extension); if (parse_res == AARCH64_PARSE_OK) { @@ -11566,7 +11599,10 @@ aarch64_handle_attr_arch (const char *str) aarch64_print_hint_for_arch (str); break; case AARCH64_PARSE_INVALID_FEATURE: - error ("invalid value (\"%s\") in % pragma or attribute", str); + error ("invalid feature modifier %s of value (\"%s\") in " + "% pragma or attribute", invalid_extension, str); + aarch64_print_hint_for_extensions (invalid_extension); + free (invalid_extension); break; default: gcc_unreachable (); @@ -11581,8 +11617,9 @@ static bool aarch64_handle_attr_cpu (const char *str) { const struct processor *tmp_cpu = NULL; + char *invalid_extension; enum aarch64_parse_opt_result parse_res - = aarch64_parse_cpu (str, &tmp_cpu, &aarch64_isa_flags); + = aarch64_parse_cpu (str, &tmp_cpu, &aarch64_isa_flags, &invalid_extension); if (parse_res == AARCH64_PARSE_OK) { @@ -11605,7 +11642,10 @@ aarch64_handle_attr_cpu (const char *str) aarch64_print_hint_for_core (str); break; case AARCH64_PARSE_INVALID_FEATURE: - error ("invalid value (\"%s\") in % pragma or attribute", str); + error ("invalid feature modifier %s of value (\"%s\") in " + "% pragma or attribute", invalid_extension, str); + aarch64_print_hint_for_extensions (invalid_extension); + free (invalid_extension); break; default: gcc_unreachable (); @@ -11663,7 +11703,8 @@ aarch64_handle_attr_isa_flags (char *str) str += 8; } - parse_res = aarch64_parse_extension (str, &isa_flags); + char *invalid_extension; + parse_res = aarch64_parse_extension (str, &isa_flags, &invalid_extension); if (parse_res == AARCH64_PARSE_OK) { @@ -11678,7 +11719,9 @@ aarch64_handle_attr_isa_flags (char *str) break; case AARCH64_PARSE_INVALID_FEATURE: - error ("invalid value (\"%s\") in % pragma or attribute", str); + error ("invalid feature modified %s of value (\"%s\") in " + "% pragma or attribute", invalid_extension, str); + free (invalid_extension); break; default: diff --git a/gcc/testsuite/gcc.target/aarch64/spellcheck_7.c b/gcc/testsuite/gcc.target/aarch64/spellcheck_7.c new file mode 100644 index 00000000000..1d31950cb61 --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/spellcheck_7.c @@ -0,0 +1,12 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-march=*" } { "" } } */ +/* { dg-skip-if "" { *-*-* } { "-mcpu=*" } { "" } } */ +/* { dg-options "-march=armv8-a+typo" } */ + +void +foo () +{ +} + +/* { dg-error "invalid feature modifier .typo. in .-march=armv8-a\\+typo." "" { target *-*-* } 0 } */ +/* { dg-message "valid arguments are: \[^\n\r]*;'?" "" { target *-*-* } 0 } */ diff --git a/gcc/testsuite/gcc.target/aarch64/spellcheck_8.c b/gcc/testsuite/gcc.target/aarch64/spellcheck_8.c new file mode 100644 index 00000000000..1b8c5ebfeb1 --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/spellcheck_8.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-march=*" } { "" } } */ +/* { dg-skip-if "" { *-*-* } { "-mcpu=*" } { "" } } */ +/* { dg-options "-march=armv8-a+cripto" } */ + +void +foo () +{ +} + +/* { dg-error "invalid feature modifier .cripto. in .-march=armv8-a\\+cripto." "" { target *-*-* } 0 } */ +/* { dg-message "valid arguments are: \[^\n\r]*; did you mean .crypto.?" "" { target *-*-* } 0 } */ + diff --git a/gcc/testsuite/gcc.target/aarch64/spellcheck_9.c b/gcc/testsuite/gcc.target/aarch64/spellcheck_9.c new file mode 100644 index 00000000000..ad5b82589c1 --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/spellcheck_9.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-march=*" } { "" } } */ +/* { dg-skip-if "" { *-*-* } { "-mcpu=*" } { "" } } */ +/* { dg-options "-mcpu=thunderx+cripto" } */ + +void +foo () +{ +} + +/* { dg-error "invalid feature modifier .cripto. in .-mcpu=thunderx\\+cripto." "" { target *-*-* } 0 } */ +/* { dg-message "valid arguments are: \[^\n\r]*; did you mean .crypto.?" "" { target *-*-* } 0 } */ + -- 2.19.0 --------------3292220C9863C2B03A090946--