From patchwork Tue Oct 3 09:09:31 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kito Cheng X-Patchwork-Id: 1842531 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.a=rsa-sha256 header.s=google header.b=VrekizF4; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=2620:52:3:1:0:246e:9693:128c; helo=server2.sourceware.org; envelope-from=gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [IPv6:2620:52:3:1:0:246e:9693:128c]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4S0BqL4XXBz20Zh for ; Tue, 3 Oct 2023 20:10:06 +1100 (AEDT) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id AA1E83858024 for ; Tue, 3 Oct 2023 09:10:03 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-pf1-x42c.google.com (mail-pf1-x42c.google.com [IPv6:2607:f8b0:4864:20::42c]) by sourceware.org (Postfix) with ESMTPS id 151723858C62 for ; Tue, 3 Oct 2023 09:09:48 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 151723858C62 Authentication-Results: sourceware.org; dmarc=pass (p=reject dis=none) header.from=sifive.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=sifive.com Received: by mail-pf1-x42c.google.com with SMTP id d2e1a72fcca58-690d2441b95so485554b3a.1 for ; Tue, 03 Oct 2023 02:09:48 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; t=1696324186; x=1696928986; darn=gcc.gnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=P0Qp0af6j9vFw5Zn3/gNAXxjZ78E1Nu27Im6R6yil3g=; b=VrekizF4aBaiRxvPXAcScxsdjAveEHzDZFKns4u0y7zFV7Sx1GXEZUcfB+F02kdLF5 qJfpS/8IHqL/2q39TocHOp4hg1/7kwsTiQ8mSsgnppp4W3bgao1KODPD7OVHcQMEU8KT tK4sdpP6wAscFGkWFGm5awNtnNi/MaQdJ2NWlDX74rU4rIm3m9weHoVnfo1/Ux3vMYXM ZvSwuQ8Y9IbDf5LEUTNjtFuidXXRZ/bTLWqtXVUDbRChmAm1B3X3zNRh7vhNXcetOp6n 6JynWcR9HGlrV5cslNkJyeIhS8tZ2dK5+HxeZXn9p2XFVLj0EgFXH4YRzlL2h3mwaKKF MaPw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1696324186; x=1696928986; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=P0Qp0af6j9vFw5Zn3/gNAXxjZ78E1Nu27Im6R6yil3g=; b=t+1zFktFWDbNQhdGeNPUhaaLhLPTb7MV+nPAIoV3p8ypffUDvQNGkoyb5OaIbogC+f Khy8JFKvCNBlrtfx4VBgYOMBOqXT6b9cTCVus9nAXhjdb4KBvF1iwbf3f79NteIEEd28 LAAFT1WD3aDCLdEBgQ8wjWYMI8pZwpcakvdvyQTYWDwm7FWLIeJBSQeY4j40VRmF4/O8 Cb2wD8XuW22Nb1zZC7m70hGKFWLxTSMyCb3uO1opBoxGUq4+ytYaOXMQ0V8uFL5bckpg K5faOJPNTXh7iSVFBVFty0vjd95FYBhtm/Zo26vqcYFaWTU9q7SsRQjufl+PossvtyQB JH1w== X-Gm-Message-State: AOJu0YxuM/mYntqcvb4vTQTIihrGq7hKQYwnbHGJ1OFf2TvGh5omf3EW Q4vZYpk3/1cpvbsZlYbKw3NbXqDoV4/+F3THPy2DvuCY1Bz48ORz4B0EiwYTF0HqDY5Z1qGBkq6 Dc1trmxmvF62/4J4jQv9/meAH1TVQ0vJZCTuK6/7jKlVlsOH7wWKxV+Np+O7vLCSUA04Kpf3YcG Qb90I= X-Google-Smtp-Source: AGHT+IFuCncQCRHjP0mUl9BYhcjzVBpuMQv5IZxtXECloW5kINHvSL9ga6g0IDCblM01Y4FWklaHAQ== X-Received: by 2002:a05:6a00:8ca:b0:691:27b:15b4 with SMTP id s10-20020a056a0008ca00b00691027b15b4mr3891652pfu.5.1696324186419; Tue, 03 Oct 2023 02:09:46 -0700 (PDT) Received: from SiX1E.internal.sifive.com (59-124-168-89.hinet-ip.hinet.net. [59.124.168.89]) by smtp.gmail.com with ESMTPSA id fn25-20020a056a002fd900b00692b6fe1c7asm892679pfb.179.2023.10.03.02.09.44 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 03 Oct 2023 02:09:46 -0700 (PDT) From: Kito Cheng To: gcc-patches@gcc.gnu.org, kito.cheng@gmail.com, palmer@dabbelt.com, jeffreyalaw@gmail.com, rdapp@ventanamicro.com, juzhe.zhong@rivai.ai Cc: Kito Cheng Subject: [PATCH v1 1/4] options: Define TARGET__P and TARGET__OPTS_P macro for Mask and InverseMask Date: Tue, 3 Oct 2023 17:09:31 +0800 Message-Id: <20231003090934.12182-2-kito.cheng@sifive.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20231003090934.12182-1-kito.cheng@sifive.com> References: <20231003090934.12182-1-kito.cheng@sifive.com> MIME-Version: 1.0 X-Spam-Status: No, score=-12.7 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org We TARGET__P marcro to test a Mask and InverseMask with user specified target_variable, however we may want to test with specific gcc_options variable rather than target_variable. Like RISC-V has defined lots of Mask with TargetVariable, which is not easy to use, because that means we need to known which Mask are associate with which TargetVariable, so take a gcc_options variable is a better interface for such use case. gcc/ChangeLog: * doc/options.texi (Mask): Document TARGET__P and TARGET__OPTS_P. (InverseMask): Ditto. * opth-gen.awk (Mask): Generate TARGET__P and TARGET__OPTS_P macro. (InverseMask): Ditto. --- gcc/doc/options.texi | 23 ++++++++++++++++------- gcc/opth-gen.awk | 13 ++++++++++++- 2 files changed, 28 insertions(+), 8 deletions(-) diff --git a/gcc/doc/options.texi b/gcc/doc/options.texi index 1f7c15b8eb4..715f0a1479c 100644 --- a/gcc/doc/options.texi +++ b/gcc/doc/options.texi @@ -404,18 +404,27 @@ You may also specify @code{Var} to select a variable other than The options-processing script will automatically allocate a unique bit for the option. If the option is attached to @samp{target_flags} or @code{Var} which is defined by @code{TargetVariable}, the script will set the macro -@code{MASK_@var{name}} to the appropriate bitmask. It will also declare a -@code{TARGET_@var{name}} macro that has the value 1 when the option is active -and 0 otherwise. If you use @code{Var} to attach the option to a different variable -which is not defined by @code{TargetVariable}, the bitmask macro with be -called @code{OPTION_MASK_@var{name}}. +@code{MASK_@var{name}} to the appropriate bitmask. It will also declare a +@code{TARGET_@var{name}}, @code{TARGET_@var{name}_P} and +@code{TARGET_@var{name}_OPTS_P}: @code{TARGET_@var{name}} macros that has the +value 1 when the option is active and 0 otherwise, @code{TARGET_@var{name}_P} is +similar to @code{TARGET_@var{name}} but take an argument as @samp{target_flags} +or @code{TargetVariable}, and @code{TARGET_@var{name}_OPTS_P} also similar to +@code{TARGET_@var{name}} but take an argument as @code{gcc_options}. +If you use @code{Var} to attach the option to a different variable which is not +defined by @code{TargetVariable}, the bitmask macro with be called +@code{OPTION_MASK_@var{name}}. @item InverseMask(@var{othername}) @itemx InverseMask(@var{othername}, @var{thisname}) The option is the inverse of another option that has the @code{Mask(@var{othername})} property. If @var{thisname} is given, -the options-processing script will declare a @code{TARGET_@var{thisname}} -macro that is 1 when the option is active and 0 otherwise. +the options-processing script will declare @code{TARGET_@var{thisname}}, +@code{TARGET_@var{name}_P} and @code{TARGET_@var{name}_OPTS_P} macros: +@code{TARGET_@var{thisname}} is 1 when the option is active and 0 otherwise, +@code{TARGET_@var{name}_P} is similar to @code{TARGET_@var{name}} but take an +argument as @samp{target_flags}, and and @code{TARGET_@var{name}_OPTS_P} also +similar to @code{TARGET_@var{name}} but take an argument as @code{gcc_options}. @item Enum(@var{name}) The option's argument is a string from the set of strings associated diff --git a/gcc/opth-gen.awk b/gcc/opth-gen.awk index 70ca3d37719..4d498abd130 100644 --- a/gcc/opth-gen.awk +++ b/gcc/opth-gen.awk @@ -439,6 +439,10 @@ for (i = 0; i < n_target_vars; i++) { print "#define TARGET_" other_masks[i][j] \ " ((" target_vars[i] " & MASK_" other_masks[i][j] ") != 0)" + print "#define TARGET_" other_masks[i][j] "_P(" target_vars[i] ")" \ + " (((" target_vars[i] ") & MASK_" other_masks[i][j] ") != 0)" + print "#define TARGET_" other_masks[i][j] "_OPTS_P(opts)" \ + " (((opts->x_" target_vars[i] ") & MASK_" other_masks[i][j] ") != 0)" } } print "" @@ -469,15 +473,22 @@ for (i = 0; i < n_opts; i++) { " ((" vname " & " mask original_name ") != 0)" print "#define TARGET_" name "_P(" vname ")" \ " (((" vname ") & " mask original_name ") != 0)" + print "#define TARGET_" name "_OPTS_P(opts)" \ + " (((opts->x_" vname ") & " mask original_name ") != 0)" print "#define TARGET_EXPLICIT_" name "_P(opts)" \ " ((opts->x_" vname "_explicit & " mask original_name ") != 0)" print "#define SET_TARGET_" name "(opts) opts->x_" vname " |= " mask original_name } } for (i = 0; i < n_extra_masks; i++) { - if (extra_mask_macros[extra_masks[i]] == 0) + if (extra_mask_macros[extra_masks[i]] == 0) { print "#define TARGET_" extra_masks[i] \ " ((target_flags & MASK_" extra_masks[i] ") != 0)" + print "#define TARGET_" extra_masks[i] "_P(target_flags)" \ + " (((target_flags) & " extra_masks[i] ") != 0)" + print "#define TARGET_" extra_masks[i] "_OPTS_P(opts)" \ + " (((opts->x_target_flags) & MASK_" extra_masks[i] ") != 0)" + } } print "" From patchwork Tue Oct 3 09:09:32 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kito Cheng X-Patchwork-Id: 1842532 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.a=rsa-sha256 header.s=google header.b=W8EIat88; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=8.43.85.97; helo=server2.sourceware.org; envelope-from=gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [8.43.85.97]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4S0Bqc1vXwz1yqM for ; Tue, 3 Oct 2023 20:10:20 +1100 (AEDT) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 94FFD385CC9D for ; Tue, 3 Oct 2023 09:10:17 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-pg1-x536.google.com (mail-pg1-x536.google.com [IPv6:2607:f8b0:4864:20::536]) by sourceware.org (Postfix) with ESMTPS id 9F2A7385773F for ; Tue, 3 Oct 2023 09:09:57 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 9F2A7385773F Authentication-Results: sourceware.org; dmarc=pass (p=reject dis=none) header.from=sifive.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=sifive.com Received: by mail-pg1-x536.google.com with SMTP id 41be03b00d2f7-5789de5c677so381493a12.3 for ; Tue, 03 Oct 2023 02:09:57 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; t=1696324196; x=1696928996; darn=gcc.gnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=wxysxx2GBA50yynLtfCfLdDKwttbhjmxWwbFiJsL2mw=; b=W8EIat88M14KP5mTlLkzYBtc3yqQHMdpjCKJpSSV48EvTumL+hSNESLMStdec7QMcu 1jahDIGn6EMcHVppMvsudzwCcas2Q6HFjuKU1SxOCx/Tdasx0eUbrkCEB8MSGMj8mJuR czw947+jk/JZDjfoi8iK66E8VZE8nruu4X1ckX9qxt2AbJNZIyU9/KD6TuDD9nQcy3sA bkFa0xHlEB0Th4WJ9iBvLCwrFTpObcdttPSOGLWk41qZzY0eVRXsjRF5NB0A99mZs3o/ n28r5wZEXmW5XA+GcKXoivUs5Xbt4U+ihFiXPD/c5lpTDDm3ScFInuHNDli2mwzAb13a 9eZA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1696324196; x=1696928996; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=wxysxx2GBA50yynLtfCfLdDKwttbhjmxWwbFiJsL2mw=; b=afWqoplsEL/utYocNN1GlO+GmGiwTOqhOeZbLs8ISdBMs2kBAld03nC1ehD3WlRrQU J/b9VefyZBGqs/9FMqTtdY7vDuUHz94Qs7aGlFQsQV4F3eLkxqbHgb6h0thHikgWUipG /9/gYD0vhADKdbYx2ppNcU8r2tXsI7AVClN4154pvRWqnIukMxG//BgKE0eBfFdTV6Zh WYDryP7pOwZp9rbaMrozLZHZhzA5tDfXgSYSApnciorqavrwP68e3ZydN3kDUJ1lqaLq hnYcghV7hs0TppvE8wfh5DaVMDVkH4fRo9UrhgLdo/gktDHssSov826DwhOmv63gxOxi fiqg== X-Gm-Message-State: AOJu0Yw12VrRvwSldnFWcn/pInwgolpBBhZw/1npIOOk9CFg2iWooTKT qzVQh8uHv+TTDNhKD/C5Y8akAvzhJ3VytlTft5S931F9XzygtTiegwsHChYbh9Eph02vTVy7GWv vKVkk4rBODpiVH1JWViEAJq8RDJ4lTrEDzF9Rogd2nhn7qMARXaqUP1v9Tile50hlvcYCMnSoeT Se3Mc= X-Google-Smtp-Source: AGHT+IHzoo4SnwJN5zaqLqMUAKM/zSuMYX6o9/Sooa4fIuMLtqx/VvyWj7lCHtSS0o8kh7ZHBaXINw== X-Received: by 2002:a05:6a20:8e2a:b0:14c:d0c0:dd27 with SMTP id y42-20020a056a208e2a00b0014cd0c0dd27mr13023829pzj.44.1696324195712; Tue, 03 Oct 2023 02:09:55 -0700 (PDT) Received: from SiX1E.internal.sifive.com (59-124-168-89.hinet-ip.hinet.net. [59.124.168.89]) by smtp.gmail.com with ESMTPSA id fn25-20020a056a002fd900b00692b6fe1c7asm892679pfb.179.2023.10.03.02.09.53 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 03 Oct 2023 02:09:55 -0700 (PDT) From: Kito Cheng To: gcc-patches@gcc.gnu.org, kito.cheng@gmail.com, palmer@dabbelt.com, jeffreyalaw@gmail.com, rdapp@ventanamicro.com, juzhe.zhong@rivai.ai Cc: Kito Cheng Subject: [PATCH v1 2/4] RISC-V: Refactor riscv_option_override and riscv_convert_vector_bits. [NFC] Date: Tue, 3 Oct 2023 17:09:32 +0800 Message-Id: <20231003090934.12182-3-kito.cheng@sifive.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20231003090934.12182-1-kito.cheng@sifive.com> References: <20231003090934.12182-1-kito.cheng@sifive.com> MIME-Version: 1.0 X-Spam-Status: No, score=-12.0 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP, URIBL_BLACK autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org Allow those funciton apply from a local gcc_options rather than the global options. Preparatory for target attribute, sperate this change for eaiser reivew since it's a NFC. gcc/ChangeLog: * config/riscv/riscv.cc (riscv_convert_vector_bits): Get setting from argument rather than get setting from global setting. (riscv_override_options_internal): New, splited from riscv_override_options, also take a gcc_options argument. (riscv_option_override): Splited most part to riscv_override_options_internal. --- gcc/config/riscv/riscv.cc | 93 ++++++++++++++++++++++----------------- 1 file changed, 52 insertions(+), 41 deletions(-) diff --git a/gcc/config/riscv/riscv.cc b/gcc/config/riscv/riscv.cc index d5446b63dbf..d089ec1b241 100644 --- a/gcc/config/riscv/riscv.cc +++ b/gcc/config/riscv/riscv.cc @@ -7982,10 +7982,11 @@ riscv_init_machine_status (void) /* Return the VLEN value associated with -march. TODO: So far we only support length-agnostic value. */ static poly_uint16 -riscv_convert_vector_bits (void) +riscv_convert_vector_bits (struct gcc_options *opts) { int chunk_num; - if (TARGET_MIN_VLEN > 32) + int min_vlen = TARGET_MIN_VLEN_OPTS (opts); + if (min_vlen > 32) { /* When targetting minimum VLEN > 32, we should use 64-bit chunk size. Otherwise we can not include SEW = 64bits. @@ -8003,7 +8004,7 @@ riscv_convert_vector_bits (void) - TARGET_MIN_VLEN = 2048bit: [256,256] - TARGET_MIN_VLEN = 4096bit: [512,512] FIXME: We currently DON'T support TARGET_MIN_VLEN > 4096bit. */ - chunk_num = TARGET_MIN_VLEN / 64; + chunk_num = min_vlen / 64; } else { @@ -8022,10 +8023,10 @@ riscv_convert_vector_bits (void) to set RVV mode size. The RVV machine modes size are run-time constant if TARGET_VECTOR is enabled. The RVV machine modes size remains default compile-time constant if TARGET_VECTOR is disabled. */ - if (TARGET_VECTOR) + if (TARGET_VECTOR_OPTS_P (opts)) { - if (riscv_autovec_preference == RVV_FIXED_VLMAX) - return (int) TARGET_MIN_VLEN / (riscv_bytes_per_vector_chunk * 8); + if (opts->x_riscv_autovec_preference == RVV_FIXED_VLMAX) + return (int) min_vlen / (riscv_bytes_per_vector_chunk * 8); else return poly_uint16 (chunk_num, chunk_num); } @@ -8033,40 +8034,33 @@ riscv_convert_vector_bits (void) return 1; } -/* Implement TARGET_OPTION_OVERRIDE. */ - -static void -riscv_option_override (void) +/* 'Unpack' up the internal tuning structs and update the options + in OPTS. The caller must have set up selected_tune and selected_arch + as all the other target-specific codegen decisions are + derived from them. */ +void +riscv_override_options_internal (struct gcc_options *opts) { const struct riscv_tune_info *cpu; -#ifdef SUBTARGET_OVERRIDE_OPTIONS - SUBTARGET_OVERRIDE_OPTIONS; -#endif - - flag_pcc_struct_return = 0; - - if (flag_pic) - g_switch_value = 0; - /* The presence of the M extension implies that division instructions are present, so include them unless explicitly disabled. */ - if (TARGET_MUL && (target_flags_explicit & MASK_DIV) == 0) - target_flags |= MASK_DIV; - else if (!TARGET_MUL && TARGET_DIV) + if (TARGET_MUL_OPTS_P (opts) && (target_flags_explicit & MASK_DIV) == 0) + opts->x_target_flags |= MASK_DIV; + else if (!TARGET_MUL_OPTS_P (opts) && TARGET_DIV_OPTS_P (opts)) error ("%<-mdiv%> requires %<-march%> to subsume the % extension"); /* Likewise floating-point division and square root. */ if ((TARGET_HARD_FLOAT || TARGET_ZFINX) && (target_flags_explicit & MASK_FDIV) == 0) - target_flags |= MASK_FDIV; + opts->x_target_flags |= MASK_FDIV; /* Handle -mtune, use -mcpu if -mtune is not given, and use default -mtune if both -mtune and -mcpu are not given. */ - cpu = riscv_parse_tune (riscv_tune_string ? riscv_tune_string : - (riscv_cpu_string ? riscv_cpu_string : + cpu = riscv_parse_tune (opts->x_riscv_tune_string ? opts->x_riscv_tune_string : + (opts->x_riscv_cpu_string ? opts->x_riscv_cpu_string : RISCV_TUNE_STRING_DEFAULT)); riscv_microarchitecture = cpu->microarchitecture; - tune_param = optimize_size ? &optimize_size_tune_info : cpu->tune_param; + tune_param = opts->x_optimize_size ? &optimize_size_tune_info : cpu->tune_param; /* Use -mtune's setting for slow_unaligned_access, even when optimizing for size. For architectures that trap and emulate unaligned accesses, @@ -8082,15 +8076,38 @@ riscv_option_override (void) if ((target_flags_explicit & MASK_STRICT_ALIGN) == 0 && cpu->tune_param->slow_unaligned_access) - target_flags |= MASK_STRICT_ALIGN; + opts->x_target_flags |= MASK_STRICT_ALIGN; /* If the user hasn't specified a branch cost, use the processor's default. */ - if (riscv_branch_cost == 0) - riscv_branch_cost = tune_param->branch_cost; + if (opts->x_riscv_branch_cost == 0) + opts->x_riscv_branch_cost = tune_param->branch_cost; - /* Function to allocate machine-dependent function status. */ - init_machine_status = &riscv_init_machine_status; + /* FIXME: We don't allow TARGET_MIN_VLEN > 4096 since the datatypes of + both GET_MODE_SIZE and GET_MODE_BITSIZE are poly_uint16. + + We can only allow TARGET_MIN_VLEN * 8 (LMUL) < 65535. */ + if (TARGET_MIN_VLEN_OPTS (opts) > 4096) + sorry ("Current RISC-V GCC cannot support VLEN greater than 4096bit for " + "'V' Extension"); + + /* Convert -march to a chunks count. */ + riscv_vector_chunks = riscv_convert_vector_bits (opts); +} + +/* Implement TARGET_OPTION_OVERRIDE. */ + +static void +riscv_option_override (void) +{ +#ifdef SUBTARGET_OVERRIDE_OPTIONS + SUBTARGET_OVERRIDE_OPTIONS; +#endif + + flag_pcc_struct_return = 0; + + if (flag_pic) + g_switch_value = 0; if (flag_pic) riscv_cmodel = CM_PIC; @@ -8205,20 +8222,14 @@ riscv_option_override (void) riscv_stack_protector_guard_offset = offs; } - /* FIXME: We don't allow TARGET_MIN_VLEN > 4096 since the datatypes of - both GET_MODE_SIZE and GET_MODE_BITSIZE are poly_uint16. - - We can only allow TARGET_MIN_VLEN * 8 (LMUL) < 65535. */ - if (TARGET_MIN_VLEN > 4096) - sorry ( - "Current RISC-V GCC cannot support VLEN greater than 4096bit for 'V' Extension"); - SET_OPTION_IF_UNSET (&global_options, &global_options_set, param_sched_pressure_algorithm, SCHED_PRESSURE_MODEL); - /* Convert -march to a chunks count. */ - riscv_vector_chunks = riscv_convert_vector_bits (); + /* Function to allocate machine-dependent function status. */ + init_machine_status = &riscv_init_machine_status; + + riscv_override_options_internal (&global_options); } /* Implement TARGET_CONDITIONAL_REGISTER_USAGE. */ From patchwork Tue Oct 3 09:09:33 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kito Cheng X-Patchwork-Id: 1842534 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.a=rsa-sha256 header.s=google header.b=K3HQ5EFZ; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=2620:52:3:1:0:246e:9693:128c; helo=server2.sourceware.org; envelope-from=gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [IPv6:2620:52:3:1:0:246e:9693:128c]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4S0BrC1lfCz1yqM for ; Tue, 3 Oct 2023 20:10:51 +1100 (AEDT) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 4CE8B38323C0 for ; Tue, 3 Oct 2023 09:10:49 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-pf1-x42e.google.com (mail-pf1-x42e.google.com [IPv6:2607:f8b0:4864:20::42e]) by sourceware.org (Postfix) with ESMTPS id 6270E385773C for ; Tue, 3 Oct 2023 09:10:00 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 6270E385773C Authentication-Results: sourceware.org; dmarc=pass (p=reject dis=none) header.from=sifive.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=sifive.com Received: by mail-pf1-x42e.google.com with SMTP id d2e1a72fcca58-69101d33315so530665b3a.3 for ; Tue, 03 Oct 2023 02:10:00 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; t=1696324199; x=1696928999; darn=gcc.gnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=+T1icYvXQHbPamZTcSJMOKQnH8OXHtdIyG8HmaJi7ds=; b=K3HQ5EFZfVRqWlXP5wwDIz3MLqfeb3pFTyd/tSF0l7ocFWjWYdsrJquOUF6XvBc5hf g2tYGeoyhPeplH24mOgdD38Mvs5/p3Qu59ZIyYkVknzQ3NvSbAqB7J1IojRQA978qOxg AxtQoifSsGtmy0ZMyCE56rgFZs1zZxw+w3jfTzR9U71E9Lidw/0tnE+GeeOJB0ug8DRg 0k8oSuN55wBJldLkpVdQB88LVXQNDtKYnf3EWeOZghJE8auvxcFe0mkE0UouWgvlisP4 0taB3tADQYGVJIjDpleX+R9mZpfQLTU5brCaIWkemDQIqVFKoGhXPClAX5qrn6UAJb6G vIZQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1696324199; x=1696928999; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=+T1icYvXQHbPamZTcSJMOKQnH8OXHtdIyG8HmaJi7ds=; b=dd/+ozfr1OtpCwGMR6QnZIzTGEB8J3VJj0QLr5ir7xeSiFUdZOLGXyxNxlLnCIPO+W fNN/y8RpNCEECOC1oqiHrLYfI27w+tyHKYMRLqAgeTttnOlg6kPGQxH1FrzI/HldSVR/ PKHsWYNzNBqLcz4GBX9Z/UVAywwTRySU0EO3oy+sBHapX8tIqlgNuHMHiRcaOvGL1wfy 6rKLsVQ7p58UbYFtzuSkyMyKMv6e65BUGr22MD2IxUZ3Zgd/SQ/uHVrk6ifJHglSHqHa PicFCQ65IWH0z5wnXSat2sRDSgHKa9tPWlJ5WLOHMH+ZP09s3KdF7OU0DbQkoN6k8I8y TYPg== X-Gm-Message-State: AOJu0Yzrv8rC+DHXjivLgFM/ruCxsdLoEdiD3ya8GPWU5WiKLnizl+h8 DtCyWyQI0IOT/61dUTnGdX+nJuaJY3PTDpyH9wpb4dMIj+5L7jAFWsrwOEzbGv4BtvpIekdhNRH xHC2kMPYjGUWICBptdttptan1/qd1hMmBc2Drvu4y+prOjfg1X4w8oKxOXcThyw4O/5E5/u/Ijf dvkJQ= X-Google-Smtp-Source: AGHT+IH/q71aEdz5Gj2G8WBpX9Jd8M8fJJGsOTf6i18ojA3u1bfcRt3ZoqyzhgUT9Qh79waPT5lClw== X-Received: by 2002:a05:6a00:2d0e:b0:692:780a:de90 with SMTP id fa14-20020a056a002d0e00b00692780ade90mr12996530pfb.30.1696324198816; Tue, 03 Oct 2023 02:09:58 -0700 (PDT) Received: from SiX1E.internal.sifive.com (59-124-168-89.hinet-ip.hinet.net. [59.124.168.89]) by smtp.gmail.com with ESMTPSA id fn25-20020a056a002fd900b00692b6fe1c7asm892679pfb.179.2023.10.03.02.09.56 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 03 Oct 2023 02:09:58 -0700 (PDT) From: Kito Cheng To: gcc-patches@gcc.gnu.org, kito.cheng@gmail.com, palmer@dabbelt.com, jeffreyalaw@gmail.com, rdapp@ventanamicro.com, juzhe.zhong@rivai.ai Cc: Kito Cheng Subject: [PATCH v1 3/4] RISC-V: Extend riscv_subset_list, preparatory for target attribute support Date: Tue, 3 Oct 2023 17:09:33 +0800 Message-Id: <20231003090934.12182-4-kito.cheng@sifive.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20231003090934.12182-1-kito.cheng@sifive.com> References: <20231003090934.12182-1-kito.cheng@sifive.com> MIME-Version: 1.0 X-Spam-Status: No, score=-12.8 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org riscv_subset_list only accept a full arch string before, but we need to parse single extension when supporting target attribute, also we may set a riscv_subset_list directly rather than re-parsing the ISA string again. gcc/ChangeLog: * config/riscv/riscv-subset.h (riscv_subset_list::parse_single_std_ext): New. (riscv_subset_list::parse_single_multiletter_ext): Ditto. (riscv_subset_list::clone): Ditto. (riscv_subset_list::parse_single_ext): Ditto. (riscv_subset_list::set_loc): Ditto. (riscv_set_arch_by_subset_list): Ditto. * common/config/riscv/riscv-common.cc (riscv_subset_list::parse_single_std_ext): New. (riscv_subset_list::parse_single_multiletter_ext): Ditto. (riscv_subset_list::clone): Ditto. (riscv_subset_list::parse_single_ext): Ditto. (riscv_subset_list::set_loc): Ditto. (riscv_set_arch_by_subset_list): Ditto. --- gcc/common/config/riscv/riscv-common.cc | 210 ++++++++++++++++++++++++ gcc/config/riscv/riscv-subset.h | 11 ++ 2 files changed, 221 insertions(+) diff --git a/gcc/common/config/riscv/riscv-common.cc b/gcc/common/config/riscv/riscv-common.cc index 9a0a68fe5db..76a1378874d 100644 --- a/gcc/common/config/riscv/riscv-common.cc +++ b/gcc/common/config/riscv/riscv-common.cc @@ -1036,6 +1036,41 @@ riscv_subset_list::parse_std_ext (const char *p) return p; } +/* Parsing function for one standard extensions. + + Return Value: + Points to the end of extensions. + + Arguments: + `p`: Current parsing position. */ + +const char * +riscv_subset_list::parse_single_std_ext (const char *p) +{ + if (*p == 'x' || *p == 's' || *p == 'z') + { + error_at (m_loc, + "%<-march=%s%>: Not single-letter extension. " + "%<%c%>", + m_arch, *p); + return nullptr; + } + + unsigned major_version = 0; + unsigned minor_version = 0; + bool explicit_version_p = false; + char subset[2] = {0, 0}; + + subset[0] = *p; + + p++; + + p = parsing_subset_version (subset, p, &major_version, &minor_version, + /* std_ext_p= */ true, &explicit_version_p); + + add (subset, major_version, minor_version, explicit_version_p, false); + return p; +} /* Check any implied extensions for EXT. */ void @@ -1138,6 +1173,109 @@ riscv_subset_list::handle_combine_ext () } } +/* Parsing function for multi-letter extensions. + + Return Value: + Points to the end of extensions. + + Arguments: + `p`: Current parsing position. + `ext_type`: What kind of extensions, 's', 'z' or 'x'. + `ext_type_str`: Full name for kind of extension. */ + + +const char * +riscv_subset_list::parse_single_multiletter_ext (const char *p, + const char *ext_type, + const char *ext_type_str) +{ + unsigned major_version = 0; + unsigned minor_version = 0; + size_t ext_type_len = strlen (ext_type); + + { + if (strncmp (p, ext_type, ext_type_len) != 0) + return NULL; + + char *subset = xstrdup (p); + char *q = subset; + const char *end_of_version; + bool explicit_version_p = false; + char *ext; + char backup; + size_t len; + size_t end_of_version_pos, i; + bool found_any_number = false; + bool found_minor_version = false; + + backup = *q; + *q = '\0'; + len = q - subset; + *q = backup; + + end_of_version_pos = len; + /* Find the begin of version string. */ + for (i = len -1; i > 0; --i) + { + if (ISDIGIT (subset[i])) + { + found_any_number = true; + continue; + } + /* Might be version seperator, but need to check one more char, + we only allow p, so we could stop parsing if found + any more `p`. */ + if (subset[i] == 'p' && + !found_minor_version && + found_any_number && ISDIGIT (subset[i-1])) + { + found_minor_version = true; + continue; + } + + end_of_version_pos = i + 1; + break; + } + + backup = subset[end_of_version_pos]; + subset[end_of_version_pos] = '\0'; + ext = xstrdup (subset); + subset[end_of_version_pos] = backup; + + end_of_version + = parsing_subset_version (ext, subset + end_of_version_pos, &major_version, &minor_version, + /* std_ext_p= */ false, &explicit_version_p); + free (ext); + + if (end_of_version == NULL) + return NULL; + + subset[end_of_version_pos] = '\0'; + + if (strlen (subset) == 1) + { + error_at (m_loc, "%<-march=%s%>: name of %s must be more than 1 letter", + m_arch, ext_type_str); + free (subset); + return NULL; + } + + add (subset, major_version, minor_version, explicit_version_p, false); + p += end_of_version - subset; + free (subset); + + if (*p != '\0' && *p != '_') + { + error_at (m_loc, "%<-march=%s%>: %s must separate with %<_%>", + m_arch, ext_type_str); + return NULL; + } + } + + return p; + +} + /* Parsing function for multi-letter extensions. Return Value: @@ -1250,6 +1388,30 @@ riscv_subset_list::parse_multiletter_ext (const char *p, return p; } +/* Parsing function for a single-letter or multi-letter extensions. + + Return Value: + Points to the end of extensions. + + Arguments: + `p`: Current parsing position. */ + +const char * +riscv_subset_list::parse_single_ext (const char *p) +{ + switch (p[0]) + { + case 'x': + return parse_single_multiletter_ext (p, "x", "non-standard extension"); + case 'z': + return parse_single_multiletter_ext (p, "z", "sub-extension"); + case 's': + return parse_single_multiletter_ext (p, "s", "supervisor extension"); + default: + return parse_single_std_ext (p); + } +} + /* Parsing arch string to subset list, return NULL if parsing failed. */ riscv_subset_list * @@ -1342,6 +1504,26 @@ fail: return NULL; } +/* Clone whole subset list. */ + +riscv_subset_list * +riscv_subset_list::clone () const +{ + riscv_subset_list *new_list = new riscv_subset_list (m_arch, m_loc); + for (riscv_subset_t *itr = m_head; itr != NULL; itr = itr->next) + new_list->add (itr->name.c_str (), itr->major_version, itr->minor_version, + itr->explicit_version_p, true); + + new_list->m_xlen = m_xlen; + return new_list; +} + +void +riscv_subset_list::set_loc (location_t loc) +{ + m_loc = loc; +} + /* Return the current arch string. */ std::string @@ -1498,6 +1680,34 @@ static const riscv_ext_flag_table_t riscv_ext_flag_table[] = {NULL, NULL, 0} }; +void +riscv_set_arch_by_subset_list (riscv_subset_list *subset_list, + struct gcc_options *opts) +{ + if (opts) + { + const riscv_ext_flag_table_t *arch_ext_flag_tab; + /* Clean up target flags before we set. */ + for (arch_ext_flag_tab = &riscv_ext_flag_table[0]; arch_ext_flag_tab->ext; + ++arch_ext_flag_tab) + opts->*arch_ext_flag_tab->var_ref &= ~arch_ext_flag_tab->mask; + + if (subset_list->xlen () == 32) + opts->x_target_flags &= ~MASK_64BIT; + else if (subset_list->xlen () == 64) + opts->x_target_flags |= MASK_64BIT; + + for (arch_ext_flag_tab = &riscv_ext_flag_table[0]; arch_ext_flag_tab->ext; + ++arch_ext_flag_tab) + { + if (subset_list->lookup (arch_ext_flag_tab->ext)) + opts->*arch_ext_flag_tab->var_ref |= arch_ext_flag_tab->mask; + } + } + + current_subset_list = subset_list; +} + /* Parse a RISC-V ISA string into an option mask. Must clear or set all arch dependent mask bits, in case more than one -march string is passed. */ diff --git a/gcc/config/riscv/riscv-subset.h b/gcc/config/riscv/riscv-subset.h index dca07284efa..d2a4bd20530 100644 --- a/gcc/config/riscv/riscv-subset.h +++ b/gcc/config/riscv/riscv-subset.h @@ -69,8 +69,12 @@ private: const char *parse_std_ext (const char *); + const char *parse_single_std_ext (const char *); + const char *parse_multiletter_ext (const char *, const char *, const char *); + const char *parse_single_multiletter_ext (const char *, const char *, + const char *); void handle_implied_ext (const char *); bool check_implied_ext (); @@ -91,14 +95,21 @@ public: unsigned xlen () const {return m_xlen;}; + riscv_subset_list *clone () const; + static riscv_subset_list *parse (const char *, location_t); + const char *parse_single_ext (const char *); const riscv_subset_t *begin () const {return m_head;}; const riscv_subset_t *end () const {return NULL;}; int match_score (riscv_subset_list *) const; + + void set_loc (location_t); }; extern const riscv_subset_list *riscv_current_subset_list (void); +extern void +riscv_set_arch_by_subset_list (riscv_subset_list *, struct gcc_options *); #endif /* ! GCC_RISCV_SUBSET_H */ From patchwork Tue Oct 3 09:09:34 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kito Cheng X-Patchwork-Id: 1842533 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=sifive.com header.i=@sifive.com header.a=rsa-sha256 header.s=google header.b=L/rUCevZ; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=2620:52:3:1:0:246e:9693:128c; helo=server2.sourceware.org; envelope-from=gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [IPv6:2620:52:3:1:0:246e:9693:128c]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4S0Bqq6Fbxz1yqM for ; Tue, 3 Oct 2023 20:10:31 +1100 (AEDT) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 2B6E13875423 for ; Tue, 3 Oct 2023 09:10:27 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-pf1-x433.google.com (mail-pf1-x433.google.com [IPv6:2607:f8b0:4864:20::433]) by sourceware.org (Postfix) with ESMTPS id 2EEC5385842E for ; Tue, 3 Oct 2023 09:10:04 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 2EEC5385842E Authentication-Results: sourceware.org; dmarc=pass (p=reject dis=none) header.from=sifive.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=sifive.com Received: by mail-pf1-x433.google.com with SMTP id d2e1a72fcca58-690d8c05784so487979b3a.2 for ; Tue, 03 Oct 2023 02:10:04 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sifive.com; s=google; t=1696324203; x=1696929003; darn=gcc.gnu.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=C5z9cWGDF6uQ5xAdkow9CBGiXpRjPIp8Ve1dwG1lPxc=; b=L/rUCevZ1dt9igUJR1KJMz02iuWgV2ElUOkGCVt5/NHoEjiNLujpdncgxgW1DKSFp3 KuDVmJyK+0IKLqg9otsCQf0gv7JbnAitSgx8SwI16iWf3Jq/P9x3kLZZzOUZ6qdUxTX0 iaZNJtizp+bYobyyYaH0T/4P0lJeSkO9Z482uSuprILIw9+S8zAa1wQhXTup/gry7SND 0W98gl6Cbq6qoEMByWe9RkY9ru8u9aX+UaohC8mBDcXCQ2dtN5e7I9Qye64mV2RQ71SB UL6uM1GvLShEhQW/uQZMHJlGGZ3Nu2DzWWs7e0sR+y2PxxEe2ZqV/etHuBhqI5W9a+RZ JRLw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1696324203; x=1696929003; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=C5z9cWGDF6uQ5xAdkow9CBGiXpRjPIp8Ve1dwG1lPxc=; b=E7ZZouTBf+jw0onM88GWfoC/zD0+d3FsIx1oSHzEP8NY1vZQ8frz6ohUOnU3HfJN0e IrnsVz6Hqyyc9r0P8nkI9rEoBRDuiep0sJ+j6B4UM11EMJhxJR1l3MlN0WR050OediB3 z/GFvIuCeyFLn4yWBcCvu3xAslQEMeoJvtFOJEnU/rZwdVgSiMqZCCXR6dIg4sFv0CFJ 9J2WN8ZBp4fl7gbPhTVicFO2xJcKQ6ftE/hrWl6Cz8c5B2BwQGiOmop+i5noVn3+PD9x pQehfeXlBcu6EL0EvrbTnym2q9fCYnH1qiY6XgZY+gECMOmP9JjOQ6IlDHOD6A3zkSIm INHw== X-Gm-Message-State: AOJu0YxlVGQe99RMsAGeeKeinroyybKXhepNWt8ESIKzXClDA7gbr2MP s2+sR0FsPgRJrnRxKNphaKkv+pgWSNdqF+j4Y1bOcwQ6vwQUSQ4ZfSVQVFBAmG9L/d9USwVw66C mE+nuUnG4rfl+RG5hm9oKnbsSqLx7Iu3TSPU9JM6fXM8C4TRQyXhk3OBJRTu2CUsYtrXIgUqIez /rGSY= X-Google-Smtp-Source: AGHT+IG2Bp5CCYlDRLfPenaWIKeXklwlT+Qbb8EkTStiH91CsSPgnRcCctUPWMPr+4miF8Yu75YUDA== X-Received: by 2002:a05:6a20:3d02:b0:15d:7e2a:cc77 with SMTP id y2-20020a056a203d0200b0015d7e2acc77mr15530129pzi.48.1696324201804; Tue, 03 Oct 2023 02:10:01 -0700 (PDT) Received: from SiX1E.internal.sifive.com (59-124-168-89.hinet-ip.hinet.net. [59.124.168.89]) by smtp.gmail.com with ESMTPSA id fn25-20020a056a002fd900b00692b6fe1c7asm892679pfb.179.2023.10.03.02.10.00 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 03 Oct 2023 02:10:01 -0700 (PDT) From: Kito Cheng To: gcc-patches@gcc.gnu.org, kito.cheng@gmail.com, palmer@dabbelt.com, jeffreyalaw@gmail.com, rdapp@ventanamicro.com, juzhe.zhong@rivai.ai Cc: Kito Cheng Subject: [PATCH v1 4/4] RISC-V: Implement target attribute Date: Tue, 3 Oct 2023 17:09:34 +0800 Message-Id: <20231003090934.12182-5-kito.cheng@sifive.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20231003090934.12182-1-kito.cheng@sifive.com> References: <20231003090934.12182-1-kito.cheng@sifive.com> MIME-Version: 1.0 X-Spam-Status: No, score=-12.0 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, KAM_SHORT, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP, URIBL_BLACK autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org The target attribute which proposed in [1], target attribute allow user to specify a local setting per-function basis. The syntax of target attribute is `__attribute__((target("")))`. and the syntax of `` describes below: ``` ATTR-STRING := ATTR-STRING ';' ATTR | ATTR ATTR := ARCH-ATTR | CPU-ATTR | TUNE-ATTR ARCH-ATTR := 'arch=' EXTENSIONS-OR-FULLARCH EXTENSIONS-OR-FULLARCH := | EXTENSIONS := ',' | FULLARCHSTR := EXTENSION := OP := '+' VERSION := [0-9]+ 'p' [0-9]+ | [1-9][0-9]* | EXTENSION-NAME := Naming rule is defined in RISC-V ISA manual CPU-ATTR := 'cpu=' TUNE-ATTR := 'tune=' ``` [1] https://github.com/riscv-non-isa/riscv-c-api-doc/pull/35 gcc/ChangeLog: * config.gcc (riscv): Add riscv-target-attr.o. * config/riscv/riscv-opts.h (TARGET_MIN_VLEN_OPTS): New. * config/riscv/riscv-protos.h (riscv_declare_function_size) New. (riscv_option_valid_attribute_p): New. (riscv_override_options_internal): New. (struct riscv_tune_info): New. (riscv_parse_tune): New. * config/riscv/riscv-target-attr.cc (class riscv_target_attr_parser): New. (struct riscv_attribute_info): New. (riscv_attributes): New. (riscv_target_attr_parser::parse_arch): (riscv_target_attr_parser::handle_arch): (riscv_target_attr_parser::handle_cpu): (riscv_target_attr_parser::handle_tune): (riscv_target_attr_parser::update_settings): (riscv_process_one_target_attr): (num_occurences_in_str): (riscv_process_target_attr): (riscv_option_valid_attribute_p): * config/riscv/riscv.cc: Include target-globals.h and riscv-subset.h. (struct riscv_tune_info): Move to riscv-protos.h. (get_tune_str): (riscv_parse_tune): (riscv_declare_function_size): (riscv_option_override): Build target_option_default_node and target_option_current_node. (riscv_save_restore_target_globals): (riscv_option_restore): (riscv_previous_fndecl): (riscv_set_current_function): Apply the target attribute. (TARGET_OPTION_RESTORE): Define. (TARGET_OPTION_VALID_ATTRIBUTE_P): Ditto. * config/riscv/riscv.h (SWITCHABLE_TARGET): Define to 1. (ASM_DECLARE_FUNCTION_SIZE) Define. * config/riscv/riscv.opt (mtune=): Add Save attribute. (mcpu=): Ditto. (mcmodel=): Ditto. * config/riscv/t-riscv: Add build rule for riscv-target-attr.o * doc/extend.texi: Add doc for target attribute. gcc/testsuite/ChangeLog: * gcc.target/riscv/target-attr-01.c: New. * gcc.target/riscv/target-attr-02.c: Ditto. * gcc.target/riscv/target-attr-03.c: Ditto. * gcc.target/riscv/target-attr-04.c: Ditto. * gcc.target/riscv/target-attr-05.c: Ditto. * gcc.target/riscv/target-attr-06.c: Ditto. * gcc.target/riscv/target-attr-07.c: Ditto. * gcc.target/riscv/target-attr-bad-01.c: Ditto. * gcc.target/riscv/target-attr-bad-02.c: Ditto. * gcc.target/riscv/target-attr-bad-03.c: Ditto. * gcc.target/riscv/target-attr-bad-04.c: Ditto. * gcc.target/riscv/target-attr-bad-05.c: Ditto. * gcc.target/riscv/target-attr-bad-06.c: Ditto. * gcc.target/riscv/target-attr-bad-07.c: Ditto. * gcc.target/riscv/target-attr-warning-01.c: Ditto. * gcc.target/riscv/target-attr-warning-02.c: Ditto. * gcc.target/riscv/target-attr-warning-03.c: Ditto. --- gcc/config.gcc | 2 +- gcc/config/riscv/riscv-opts.h | 6 + gcc/config/riscv/riscv-protos.h | 21 + gcc/config/riscv/riscv-target-attr.cc | 396 ++++++++++++++++++ gcc/config/riscv/riscv.cc | 192 +++++++-- gcc/config/riscv/riscv.h | 6 + gcc/config/riscv/riscv.opt | 6 +- gcc/config/riscv/t-riscv | 5 + gcc/doc/extend.texi | 58 +++ .../gcc.target/riscv/target-attr-01.c | 31 ++ .../gcc.target/riscv/target-attr-02.c | 31 ++ .../gcc.target/riscv/target-attr-03.c | 26 ++ .../gcc.target/riscv/target-attr-04.c | 28 ++ .../gcc.target/riscv/target-attr-05.c | 27 ++ .../gcc.target/riscv/target-attr-06.c | 27 ++ .../gcc.target/riscv/target-attr-07.c | 25 ++ .../gcc.target/riscv/target-attr-bad-01.c | 13 + .../gcc.target/riscv/target-attr-bad-02.c | 13 + .../gcc.target/riscv/target-attr-bad-03.c | 13 + .../gcc.target/riscv/target-attr-bad-04.c | 13 + .../gcc.target/riscv/target-attr-bad-05.c | 13 + .../gcc.target/riscv/target-attr-bad-06.c | 13 + .../gcc.target/riscv/target-attr-bad-07.c | 13 + .../gcc.target/riscv/target-attr-warning-01.c | 8 + .../gcc.target/riscv/target-attr-warning-02.c | 8 + .../gcc.target/riscv/target-attr-warning-03.c | 8 + 26 files changed, 957 insertions(+), 45 deletions(-) create mode 100644 gcc/config/riscv/riscv-target-attr.cc create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-01.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-02.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-03.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-04.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-05.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-06.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-07.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-01.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-02.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-03.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-04.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-05.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-06.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-bad-07.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-warning-01.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-warning-02.c create mode 100644 gcc/testsuite/gcc.target/riscv/target-attr-warning-03.c diff --git a/gcc/config.gcc b/gcc/config.gcc index ee46d96bf62..b62fb096b59 100644 --- a/gcc/config.gcc +++ b/gcc/config.gcc @@ -544,7 +544,7 @@ riscv*) extra_objs="riscv-builtins.o riscv-c.o riscv-sr.o riscv-shorten-memrefs.o riscv-selftests.o riscv-string.o" extra_objs="${extra_objs} riscv-v.o riscv-vsetvl.o riscv-vector-costs.o" extra_objs="${extra_objs} riscv-vector-builtins.o riscv-vector-builtins-shapes.o riscv-vector-builtins-bases.o" - extra_objs="${extra_objs} thead.o" + extra_objs="${extra_objs} thead.o riscv-target-attr.o" d_target_objs="riscv-d.o" extra_headers="riscv_vector.h" target_gtfiles="$target_gtfiles \$(srcdir)/config/riscv/riscv-vector-builtins.cc" diff --git a/gcc/config/riscv/riscv-opts.h b/gcc/config/riscv/riscv-opts.h index 7e4b0cc6fe1..8d0ae3237c3 100644 --- a/gcc/config/riscv/riscv-opts.h +++ b/gcc/config/riscv/riscv-opts.h @@ -111,6 +111,12 @@ enum riscv_entity ? 0 \ : 32 << (__builtin_popcount (riscv_zvl_flags) - 1)) +/* Same as TARGET_MIN_VLEN, but take an OPTS as gcc_options. */ +#define TARGET_MIN_VLEN_OPTS(opts) \ + ((opts->x_riscv_zvl_flags == 0) \ + ? 0 \ + : 32 << (__builtin_popcount (opts->x_riscv_zvl_flags) - 1)) + /* We only enable VLS modes for VLA vectorization since fixed length VLMAX mode is the highest priority choice and should not conflict with VLS modes. */ #define TARGET_VECTOR_VLS \ diff --git a/gcc/config/riscv/riscv-protos.h b/gcc/config/riscv/riscv-protos.h index af5baf37e6a..c3107be1391 100644 --- a/gcc/config/riscv/riscv-protos.h +++ b/gcc/config/riscv/riscv-protos.h @@ -103,6 +103,7 @@ extern void riscv_split_doubleword_move (rtx, rtx); extern const char *riscv_output_move (rtx, rtx); extern const char *riscv_output_return (); extern void riscv_declare_function_name (FILE *, const char *, tree); +extern void riscv_declare_function_size (FILE *, const char *, tree); extern void riscv_asm_output_alias (FILE *, const tree, const tree); extern void riscv_asm_output_external (FILE *, const tree, const char *); extern bool @@ -578,5 +579,25 @@ th_mempair_output_move (rtx[4], bool, machine_mode, RTX_CODE); extern bool riscv_use_divmod_expander (void); void riscv_init_cumulative_args (CUMULATIVE_ARGS *, tree, rtx, tree, int); +extern bool +riscv_option_valid_attribute_p (tree, tree, tree, int); +extern void +riscv_override_options_internal (struct gcc_options *); + +struct riscv_tune_param; +/* Information about one micro-arch we know about. */ +struct riscv_tune_info { + /* This micro-arch canonical name. */ + const char *name; + + /* Which automaton to use for tuning. */ + enum riscv_microarchitecture_type microarchitecture; + + /* Tuning parameters for this micro-arch. */ + const struct riscv_tune_param *tune_param; +}; + +const struct riscv_tune_info * +riscv_parse_tune (const char *, bool); #endif /* ! GCC_RISCV_PROTOS_H */ diff --git a/gcc/config/riscv/riscv-target-attr.cc b/gcc/config/riscv/riscv-target-attr.cc new file mode 100644 index 00000000000..9eec3b951c7 --- /dev/null +++ b/gcc/config/riscv/riscv-target-attr.cc @@ -0,0 +1,396 @@ +/* Subroutines used for parsing target attribute for RISC-V. + Copyright (C) 2023 Free Software Foundation, Inc. + +This file is part of GCC. + +GCC is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 3, or (at your option) +any later version. + +GCC is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with GCC; see the file COPYING3. If not see +. */ + +#define IN_TARGET_CODE 1 + +#define INCLUDE_STRING +#include "config.h" +#include "system.h" +#include "coretypes.h" +#include "target.h" +#include "tree.h" +#include "tm_p.h" +#include "diagnostic.h" +#include "opts.h" +#include "riscv-subset.h" + +namespace { +class riscv_target_attr_parser +{ +public: + riscv_target_attr_parser (location_t loc) + : m_found_arch_p (false) + , m_found_tune_p (false) + , m_found_cpu_p (false) + , m_subset_list (nullptr) + , m_loc (loc) + , m_cpu_info (nullptr) + , m_tune (nullptr) + { + } + + bool handle_arch (const char *); + bool handle_cpu (const char *); + bool handle_tune (const char *); + + void set_loc (location_t loc) { + m_loc = loc; + } + + void update_settings (struct gcc_options *opts) const; +private: + const char *m_raw_attr_str; + bool parse_arch (const char *); + + bool m_found_arch_p; + bool m_found_tune_p; + bool m_found_cpu_p; + riscv_subset_list *m_subset_list; + location_t m_loc; + const riscv_cpu_info *m_cpu_info; + const char *m_tune; +}; +} + +/* All the information needed to handle a target attribute. + NAME is the name of the attribute. + HANDLER is the function that takes the attribute string as an argument. */ + +struct riscv_attribute_info +{ + const char *name; + bool (riscv_target_attr_parser::*handler) (const char *); +}; + +/* The target attributes that we support. */ + +static const struct riscv_attribute_info riscv_attributes[] + = {{"arch", &riscv_target_attr_parser::handle_arch}, + {"cpu", &riscv_target_attr_parser::handle_cpu}, + {"tune", &riscv_target_attr_parser::handle_tune}}; + +bool +riscv_target_attr_parser::parse_arch (const char *str) +{ + if (m_subset_list) + delete m_subset_list; + /* Check if it's setting full arch string. */ + if (strncmp ("rv", str, strlen ("rv")) == 0) + { + m_subset_list = riscv_subset_list::parse (str, location_t ()); + + if (m_subset_list == nullptr) + goto fail; + + return true; + } + else + { + /* Parsing the extension list like "+[,+]*". */ + size_t len = strlen (str); + char *str_to_check = (char *) alloca (len + 1); + strcpy (str_to_check, str); + const char *token = strtok_r (str_to_check, ",", &str_to_check); + m_subset_list = riscv_current_subset_list ()->clone (); + m_subset_list->set_loc (m_loc); + while (token) + { + if (token[0] != '+') + { + error_at ( + m_loc, + "unexpected arch for % attribute: must start " + "with + or rv"); + goto fail; + } + else + { + const char *result = m_subset_list->parse_single_ext (token + 1); + /* Check parse_single_ext has consume all string. */ + if (*result != '\0') + { + error_at ( + m_loc, + "unexpected arch for % attribute: bad " + "string found %<%s%>", token); + goto fail; + } + } + token = strtok_r (NULL, ",", &str_to_check); + } + + return true; + } +fail: + if (m_subset_list != nullptr) + { + delete m_subset_list; + m_subset_list = nullptr; + } + return false; +} + +/* Handle the ARCH_STR argument to the arch= target attribute. */ + +bool +riscv_target_attr_parser::handle_arch (const char *str) +{ + if (m_found_arch_p) + warning_at (m_loc, 0, + "% attribute: arch appears more than once, the " + "settings of the last one will be used"); + m_found_arch_p = true; + return parse_arch (str); +} + +/* Handle the CPU_STR argument to the cpu= target attribute. */ + +bool +riscv_target_attr_parser::handle_cpu (const char *str) +{ + if (m_found_cpu_p) + warning_at (m_loc, 0, + "% attribute: cpu appears more than once, the " + "settings of the last one will be used"); + + m_found_cpu_p = true; + const riscv_cpu_info *cpu_info = riscv_find_cpu (str); + + if (!cpu_info) + { + error_at (m_loc, 0, "% attribute: unknown CPU %<%s%>", str); + return false; + } + + if (m_subset_list == nullptr) + { + const char *arch_str = cpu_info->arch; + m_subset_list = riscv_subset_list::parse (arch_str, m_loc); + gcc_assert (m_subset_list); + } + + m_cpu_info = cpu_info; + return true; +} + +/* Handle the TUNE_STR argument to the tune= target attribute. */ + +bool +riscv_target_attr_parser::handle_tune (const char *str) +{ + if (m_found_tune_p) + warning_at (m_loc, 0, + "% attribute: tune appears more than once, the " + "settings of the last one will be used"); + m_found_tune_p = true; + const struct riscv_tune_info *tune = riscv_parse_tune (str, true); + + if (tune == nullptr) + { + error_at (m_loc, 0, "% attribute: unknown TUNE %<%s%>", str); + return false; + } + + m_tune = tune->name; + + return true; +} + +void +riscv_target_attr_parser::update_settings (struct gcc_options *opts) const +{ + if (m_subset_list) + riscv_set_arch_by_subset_list (m_subset_list, opts); + + if (m_cpu_info) + opts->x_riscv_cpu_string = m_cpu_info->name; + + if (m_tune) + opts->x_riscv_tune_string = m_tune; + else + { + if (m_cpu_info) + opts->x_riscv_tune_string = m_cpu_info->tune; + } +} + +/* Parse ARG_STR which contains the definition of one target attribute. + Show appropriate errors if any or return true if the attribute is valid. */ + +static bool +riscv_process_one_target_attr (char *arg_str, + location_t loc, + riscv_target_attr_parser &attr_parser) +{ + size_t len = strlen (arg_str); + + if (len == 0) + { + error_at (loc, "malformed % attribute"); + return false; + } + + char *str_to_check = (char *) alloca (len + 1); + strcpy (str_to_check, arg_str); + + char *arg = strchr (str_to_check, '='); + + if (!arg) + { + error_at ( + loc, + "attribute % does not accept an argument", + str_to_check); + return false; + } + + arg[0] = '\0'; + ++arg; + for (const auto &attr : riscv_attributes) + { + /* If the names don't match up, or the user has given an argument + to an attribute that doesn't accept one, or didn't give an argument + to an attribute that expects one, fail to match. */ + if (strncmp (str_to_check, attr.name, strlen (attr.name)) != 0) + continue; + + return (&attr_parser->*attr.handler) (arg); + } + error_at (loc, "Got unknown attribute %", str_to_check); + + return false; +} + +/* Count how many times the character C appears in + NULL-terminated string STR. */ + +static unsigned int +num_occurences_in_str (char c, char *str) +{ + unsigned int res = 0; + while (*str != '\0') + { + if (*str == c) + res++; + + str++; + } + + return res; +} + +/* Parse the tree in ARGS that contains the target attribute information + and update the global target options space. */ + +static bool +riscv_process_target_attr (tree args, location_t loc, struct gcc_options *opts) +{ + if (TREE_CODE (args) == TREE_LIST) + { + do + { + tree head = TREE_VALUE (args); + if (head) + { + if (!riscv_process_target_attr (head, loc, opts)) + return false; + } + args = TREE_CHAIN (args); + } while (args); + + return true; + } + + if (TREE_CODE (args) != STRING_CST) + { + error_at (loc, "attribute % argument not a string"); + return false; + } + size_t len = strlen (TREE_STRING_POINTER (args)); + char *str_to_check = (char *) alloca (len + 1); + strcpy (str_to_check, TREE_STRING_POINTER (args)); + + if (len == 0) + { + error_at (loc, "malformed % attribute"); + return false; + } + + /* Used to catch empty spaces between commas i.e. + attribute ((target ("attr1;;attr2"))). */ + unsigned int num_commas = num_occurences_in_str (';', str_to_check); + + /* Handle multiple target attributes separated by ','. */ + char *token = strtok_r (str_to_check, ";", &str_to_check); + + riscv_target_attr_parser attr_parser (loc); + unsigned int num_attrs = 0; + while (token) + { + num_attrs++; + riscv_process_one_target_attr (token, loc, attr_parser); + token = strtok_r (NULL, ";", &str_to_check); + } + + if (num_attrs != num_commas + 1) + { + error_at (loc, "malformed % attribute", + TREE_STRING_POINTER (args)); + return false; + } + + /* Apply settings from target attribute. */ + attr_parser.update_settings (opts); + + return true; +} + +/* Implement TARGET_OPTION_VALID_ATTRIBUTE_P. This is used to + process attribute ((target ("..."))). */ + +bool +riscv_option_valid_attribute_p (tree fndecl, tree, tree args, int) +{ + struct cl_target_option cur_target; + bool ret; + tree new_target; + location_t loc = DECL_SOURCE_LOCATION (fndecl); + + /* Save the current target options to restore at the end. */ + cl_target_option_save (&cur_target, &global_options, &global_options_set); + + ret = riscv_process_target_attr (args, loc, &global_options); + + if (ret) + { + riscv_override_options_internal (&global_options); + new_target + = build_target_option_node (&global_options, &global_options_set); + } + else + new_target = NULL; + + if (fndecl && ret) + { + DECL_FUNCTION_SPECIFIC_TARGET (fndecl) = new_target; + } + + cl_target_option_restore (&global_options, &global_options_set, &cur_target); + return ret; +} diff --git a/gcc/config/riscv/riscv.cc b/gcc/config/riscv/riscv.cc index d089ec1b241..ace2903a13d 100644 --- a/gcc/config/riscv/riscv.cc +++ b/gcc/config/riscv/riscv.cc @@ -73,10 +73,12 @@ along with GCC; see the file COPYING3. If not see #include "tree-vectorizer.h" #include "gcse.h" #include "tree-dfa.h" +#include "target-globals.h" /* This file should be included last. */ #include "target-def.h" #include "riscv-vector-costs.h" +#include "riscv-subset.h" /* True if X is an UNSPEC wrapper around a SYMBOL_REF or LABEL_REF. */ #define UNSPEC_ADDRESS_P(X) \ @@ -261,17 +263,6 @@ struct riscv_tune_param bool use_divmod_expansion; }; -/* Information about one micro-arch we know about. */ -struct riscv_tune_info { - /* This micro-arch canonical name. */ - const char *name; - - /* Which automaton to use for tuning. */ - enum riscv_microarchitecture_type microarchitecture; - - /* Tuning parameters for this micro-arch. */ - const struct riscv_tune_param *tune_param; -}; /* Global variables for machine-dependent things. */ @@ -483,10 +474,23 @@ riscv_min_arithmetic_precision (void) return 32; } -/* Return the riscv_tune_info entry for the given name string. */ +template +static const char * +get_tune_str (const T *opts) +{ + const char *tune_string = RISCV_TUNE_STRING_DEFAULT; + if (opts->x_riscv_tune_string) + tune_string = opts->x_riscv_tune_string; + else if (opts->x_riscv_cpu_string) + tune_string = opts->x_riscv_cpu_string; + return tune_string; +} + +/* Return the riscv_tune_info entry for the given name string, return nullptr + if NULL_P is true, otherwise return an placeholder and report error. */ -static const struct riscv_tune_info * -riscv_parse_tune (const char *tune_string) +const struct riscv_tune_info * +riscv_parse_tune (const char *tune_string, bool null_p) { const riscv_cpu_info *cpu = riscv_find_cpu (tune_string); @@ -497,6 +501,9 @@ riscv_parse_tune (const char *tune_string) if (strcmp (riscv_tune_info_table[i].name, tune_string) == 0) return riscv_tune_info_table + i; + if (null_p) + return nullptr; + error ("unknown cpu %qs for %<-mtune%>", tune_string); return riscv_tune_info_table; } @@ -7845,6 +7852,33 @@ riscv_declare_function_name (FILE *stream, const char *name, tree fndecl) riscv_asm_output_variant_cc (stream, fndecl, name); ASM_OUTPUT_TYPE_DIRECTIVE (stream, name, "function"); ASM_OUTPUT_LABEL (stream, name); + if (DECL_FUNCTION_SPECIFIC_TARGET (fndecl)) + { + fprintf (stream, "\t.option push\n"); + std::string isa = riscv_current_subset_list ()->to_string (true); + fprintf (stream, "\t.option arch, %s\n", isa.c_str ()); + + struct cl_target_option *local_cl_target = + TREE_TARGET_OPTION (DECL_FUNCTION_SPECIFIC_TARGET (fndecl)); + struct cl_target_option *global_cl_target = + TREE_TARGET_OPTION (target_option_default_node); + const char *local_tune_str = get_tune_str (local_cl_target); + const char *global_tune_str = get_tune_str (global_cl_target); + if (strcmp (local_tune_str, global_tune_str) != 0) + fprintf (stream, "\t# tune = %s\n", local_tune_str); + } +} + +void +riscv_declare_function_size (FILE *stream, const char *name, tree fndecl) +{ + if (!flag_inhibit_size_directive) + ASM_OUTPUT_MEASURED_SIZE (stream, name); + + if (DECL_FUNCTION_SPECIFIC_TARGET (fndecl)) + { + fprintf (stream, "\t.option pop\n"); + } } /* Implement ASM_OUTPUT_DEF_FROM_DECLS. */ @@ -8051,16 +8085,18 @@ riscv_override_options_internal (struct gcc_options *opts) error ("%<-mdiv%> requires %<-march%> to subsume the % extension"); /* Likewise floating-point division and square root. */ - if ((TARGET_HARD_FLOAT || TARGET_ZFINX) && (target_flags_explicit & MASK_FDIV) == 0) + if ((TARGET_HARD_FLOAT_OPTS_P (opts) || TARGET_ZFINX_OPTS_P (opts)) + && ((target_flags_explicit & MASK_FDIV) == 0)) opts->x_target_flags |= MASK_FDIV; /* Handle -mtune, use -mcpu if -mtune is not given, and use default -mtune if both -mtune and -mcpu are not given. */ - cpu = riscv_parse_tune (opts->x_riscv_tune_string ? opts->x_riscv_tune_string : - (opts->x_riscv_cpu_string ? opts->x_riscv_cpu_string : - RISCV_TUNE_STRING_DEFAULT)); + const char *tune_string = get_tune_str (opts); + cpu = riscv_parse_tune (tune_string, false); riscv_microarchitecture = cpu->microarchitecture; - tune_param = opts->x_optimize_size ? &optimize_size_tune_info : cpu->tune_param; + tune_param = opts->x_optimize_size + ? &optimize_size_tune_info + : cpu->tune_param; /* Use -mtune's setting for slow_unaligned_access, even when optimizing for size. For architectures that trap and emulate unaligned accesses, @@ -8072,7 +8108,7 @@ riscv_override_options_internal (struct gcc_options *opts) /* Make a note if user explicity passed -mstrict-align for later builtin macro generation. Can't use target_flags_explicitly since it is set even for -mno-strict-align. */ - riscv_user_wants_strict_align = TARGET_STRICT_ALIGN; + riscv_user_wants_strict_align = TARGET_STRICT_ALIGN_OPTS_P (opts); if ((target_flags_explicit & MASK_STRICT_ALIGN) == 0 && cpu->tune_param->slow_unaligned_access) @@ -8230,8 +8266,41 @@ riscv_option_override (void) init_machine_status = &riscv_init_machine_status; riscv_override_options_internal (&global_options); + + /* Save these options as the default ones in case we push and pop them later + while processing functions with potential target attributes. */ + target_option_default_node = target_option_current_node + = build_target_option_node (&global_options, &global_options_set); +} + +/* Restore or save the TREE_TARGET_GLOBALS from or to NEW_TREE. + Used by riscv_set_current_function to + make sure optab availability predicates are recomputed when necessary. */ + +void +riscv_save_restore_target_globals (tree new_tree) +{ + if (TREE_TARGET_GLOBALS (new_tree)) + restore_target_globals (TREE_TARGET_GLOBALS (new_tree)); + else if (new_tree == target_option_default_node) + restore_target_globals (&default_target_globals); + else + TREE_TARGET_GLOBALS (new_tree) = save_target_globals_default_opts (); } +/* Implements TARGET_OPTION_RESTORE. Restore the backend codegen decisions + using the information saved in PTR. */ + +static void +riscv_option_restore (struct gcc_options *opts, + struct gcc_options * /* opts_set */, + struct cl_target_option * /* ptr */) +{ + riscv_override_options_internal (opts); +} + +static GTY (()) tree riscv_previous_fndecl; + /* Implement TARGET_CONDITIONAL_REGISTER_USAGE. */ static void @@ -8477,7 +8546,12 @@ riscv_get_interrupt_type (tree decl) return MACHINE_MODE; } -/* Implement `TARGET_SET_CURRENT_FUNCTION'. */ +/* Implement `TARGET_SET_CURRENT_FUNCTION'. Unpack the codegen decisions + like tuning and ISA features from the DECL_FUNCTION_SPECIFIC_TARGET + of the function, if such exists. This function may be called multiple + times on a single function so use aarch64_previous_fndecl to avoid + setting up identical state. */ + /* Sanity cheching for above function attributes. */ static void riscv_set_current_function (tree decl) @@ -8485,36 +8559,66 @@ riscv_set_current_function (tree decl) if (decl == NULL_TREE || current_function_decl == NULL_TREE || current_function_decl == error_mark_node - || ! cfun->machine - || cfun->machine->attributes_checked_p) + || ! cfun->machine) return; - cfun->machine->naked_p = riscv_naked_function_p (decl); - cfun->machine->interrupt_handler_p - = riscv_interrupt_type_p (TREE_TYPE (decl)); + if (!cfun->machine->attributes_checked_p) + { + cfun->machine->naked_p = riscv_naked_function_p (decl); + cfun->machine->interrupt_handler_p + = riscv_interrupt_type_p (TREE_TYPE (decl)); - if (cfun->machine->naked_p && cfun->machine->interrupt_handler_p) - error ("function attributes %qs and %qs are mutually exclusive", - "interrupt", "naked"); + if (cfun->machine->naked_p && cfun->machine->interrupt_handler_p) + error ("function attributes %qs and %qs are mutually exclusive", + "interrupt", "naked"); - if (cfun->machine->interrupt_handler_p) - { - tree ret = TREE_TYPE (TREE_TYPE (decl)); - tree args = TYPE_ARG_TYPES (TREE_TYPE (decl)); + if (cfun->machine->interrupt_handler_p) + { + tree ret = TREE_TYPE (TREE_TYPE (decl)); + tree args = TYPE_ARG_TYPES (TREE_TYPE (decl)); + + if (TREE_CODE (ret) != VOID_TYPE) + error ("%qs function cannot return a value", "interrupt"); - if (TREE_CODE (ret) != VOID_TYPE) - error ("%qs function cannot return a value", "interrupt"); + if (args && TREE_CODE (TREE_VALUE (args)) != VOID_TYPE) + error ("%qs function cannot have arguments", "interrupt"); - if (args && TREE_CODE (TREE_VALUE (args)) != VOID_TYPE) - error ("%qs function cannot have arguments", "interrupt"); + cfun->machine->interrupt_mode = riscv_get_interrupt_type (decl); - cfun->machine->interrupt_mode = riscv_get_interrupt_type (decl); + gcc_assert (cfun->machine->interrupt_mode != UNKNOWN_MODE); + } - gcc_assert (cfun->machine->interrupt_mode != UNKNOWN_MODE); + /* Don't print the above diagnostics more than once. */ + cfun->machine->attributes_checked_p = 1; } - /* Don't print the above diagnostics more than once. */ - cfun->machine->attributes_checked_p = 1; + if (!decl || decl == riscv_previous_fndecl) + return; + + tree old_tree = (riscv_previous_fndecl + ? DECL_FUNCTION_SPECIFIC_TARGET (riscv_previous_fndecl) + : NULL_TREE); + + tree new_tree = DECL_FUNCTION_SPECIFIC_TARGET (decl); + + /* If current function has no attributes but the previous one did, + use the default node. */ + if (!new_tree && old_tree) + new_tree = target_option_default_node; + + /* If nothing to do, return. #pragma GCC reset or #pragma GCC pop to + the default have been handled by aarch64_save_restore_target_globals from + aarch64_pragma_target_parse. */ + if (old_tree == new_tree) + return; + + riscv_previous_fndecl = decl; + + /* First set the target options. */ + cl_target_option_restore (&global_options, &global_options_set, + TREE_TARGET_OPTION (new_tree)); + + riscv_save_restore_target_globals (new_tree); } /* Implement TARGET_MERGE_DECL_ATTRIBUTES. */ @@ -9633,6 +9737,12 @@ riscv_preferred_else_value (unsigned ifn, tree vectype, unsigned int nops, #undef TARGET_OPTION_OVERRIDE #define TARGET_OPTION_OVERRIDE riscv_option_override +#undef TARGET_OPTION_RESTORE +#define TARGET_OPTION_RESTORE riscv_option_restore + +#undef TARGET_OPTION_VALID_ATTRIBUTE_P +#define TARGET_OPTION_VALID_ATTRIBUTE_P riscv_option_valid_attribute_p + #undef TARGET_LEGITIMIZE_ADDRESS #define TARGET_LEGITIMIZE_ADDRESS riscv_legitimize_address diff --git a/gcc/config/riscv/riscv.h b/gcc/config/riscv/riscv.h index 7ac78847b3a..a88c6f917a6 100644 --- a/gcc/config/riscv/riscv.h +++ b/gcc/config/riscv/riscv.h @@ -25,6 +25,8 @@ along with GCC; see the file COPYING3. If not see #include #include "config/riscv/riscv-opts.h" +#define SWITCHABLE_TARGET 1 + /* Target CPU builtins. */ #define TARGET_CPU_CPP_BUILTINS() riscv_cpu_cpp_builtins (pfile) @@ -1054,6 +1056,10 @@ while (0) #define ASM_DECLARE_FUNCTION_NAME(STR, NAME, DECL) \ riscv_declare_function_name (STR, NAME, DECL) +#undef ASM_DECLARE_FUNCTION_SIZE +#define ASM_DECLARE_FUNCTION_SIZE(FILE, FNAME, DECL) \ + riscv_declare_function_size (FILE, FNAME, DECL) + /* Add output .variant_cc directive for specific alias definition. */ #undef ASM_OUTPUT_DEF_FROM_DECLS #define ASM_OUTPUT_DEF_FROM_DECLS(STR, DECL, TARGET) \ diff --git a/gcc/config/riscv/riscv.opt b/gcc/config/riscv/riscv.opt index 9424b239058..17f3adcc622 100644 --- a/gcc/config/riscv/riscv.opt +++ b/gcc/config/riscv/riscv.opt @@ -84,11 +84,11 @@ Target RejectNegative Joined Negative(march=) lower-case. mtune= -Target RejectNegative Joined Var(riscv_tune_string) +Target RejectNegative Joined Var(riscv_tune_string) Save -mtune=PROCESSOR Optimize the output for PROCESSOR. mcpu= -Target RejectNegative Joined Var(riscv_cpu_string) +Target RejectNegative Joined Var(riscv_cpu_string) Save -mcpu=PROCESSOR Use architecture of and optimize the output for PROCESSOR. msmall-data-limit= @@ -106,7 +106,7 @@ memory accesses to be generated as compressed instructions. Currently targets 32-bit integer load/stores. mcmodel= -Target RejectNegative Joined Enum(code_model) Var(riscv_cmodel) Init(TARGET_DEFAULT_CMODEL) +Target RejectNegative Joined Enum(code_model) Var(riscv_cmodel) Init(TARGET_DEFAULT_CMODEL) Save Specify the code model. mstrict-align diff --git a/gcc/config/riscv/t-riscv b/gcc/config/riscv/t-riscv index f137e1f17ef..d46459ff462 100644 --- a/gcc/config/riscv/t-riscv +++ b/gcc/config/riscv/t-riscv @@ -108,6 +108,11 @@ riscv-v.o: $(srcdir)/config/riscv/riscv-v.cc \ $(COMPILE) $< $(POSTCOMPILE) +riscv-target-attr.o: $(srcdir)/config/riscv/riscv-target-attr.cc $(CONFIG_H) \ + $(SYSTEM_H) coretypes.h $(TM_H) $(TREE_H) $(DIAGNOSTIC_CORE_H) + $(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) \ + $(srcdir)/config/riscv/riscv-target-attr.cc + thead.o: $(srcdir)/config/riscv/thead.cc \ $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TARGET_H) backend.h $(RTL_H) \ memmodel.h $(EMIT_RTL_H) poly-int.h output.h diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi index b4770f1a149..e8b0a823b59 100644 --- a/gcc/doc/extend.texi +++ b/gcc/doc/extend.texi @@ -6224,8 +6224,66 @@ void f (void) __attribute__ ((interrupt ("user"))); Permissible values for this parameter are @code{user}, @code{supervisor}, and @code{machine}. If there is no parameter, then it defaults to @code{machine}. + +@end table + +The following target-specific function attributes are available for the +RISC-V target. For the most part, these options mirror the behavior of +similar command-line options (@pxref{RISC-V Options}), but on a +per-function basis. + +@table @code +@cindex @code{arch=} function attribute, RISC-V +@item arch= +Specifies the architecture version and architectural extensions to use +for this function. The behavior and permissible arguments are the same as +for the @option{-march=} command-line option, in addtion, it also support +extension enablement list, a list of extension name and prefixed with @code{+}, +like @code{arch=+zba} means enable @code{zba} extension. +Multiple extension can be enabled by separating them with a comma. For example: +@code{arch=+zba,+zbb}. + +@cindex @code{tune=} function attribute, RISC-V +@item tune= +Specifies the core for which to tune the performance of this function. +The behavior and permissible arguments are the same as for the @option{-mtune=} +command-line option. + +@cindex @code{cpu=} function attribute, RISC-V +@item cpu= +Specifies the core for which to tune the performance of this function and also +whose architectural features to use. The behavior and valid arguments are the +same as for the @option{-mcpu=} command-line option. + @end table +The above target attributes can be specified as follows: + +@smallexample +__attribute__((target("@var{attr-string}"))) +int +f (int a) +@{ + return a + 5; +@} +@end smallexample + +where @code{@var{attr-string}} is one of the attribute strings specified above. + +Multiple target function attributes can be specified by separating them with +a semicolon. For example: +@smallexample +__attribute__((target("arch=+zba,+zbb;tune=rocket"))) +int +foo (int a) +@{ + return a + 5; +@} +@end smallexample + +is valid and compiles function @code{foo} with @code{zba} +and @code{zbb} extensions and tunes it for @code{rocket}. + @node RL78 Function Attributes @subsection RL78 Function Attributes diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-01.c b/gcc/testsuite/gcc.target/riscv/target-attr-01.c new file mode 100644 index 00000000000..b3f3d65d543 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-01.c @@ -0,0 +1,31 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + + +/* +** foo: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ + + +long foo() __attribute__((target("arch=rv64gc_zba"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** slli\s*a1,a1,1 +** add\s*a0,a1,a0 +** ... +*/ + + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-02.c b/gcc/testsuite/gcc.target/riscv/target-attr-02.c new file mode 100644 index 00000000000..c010089a823 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-02.c @@ -0,0 +1,31 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + + +/* +** foo: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ + + +long foo() __attribute__((target("arch=+zba"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** slli\s*a1,a1,1 +** add\s*a0,a1,a0 +** ... +*/ + + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-03.c b/gcc/testsuite/gcc.target/riscv/target-attr-03.c new file mode 100644 index 00000000000..b4896cb2e27 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-03.c @@ -0,0 +1,26 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc_zba -O2 -mabi=lp64" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + +/* +** foo: +** ... +** slli\s*a1,a1,1 +** add\s*a0,a1,a0 +** ... +*/ +long foo() __attribute__((target("arch=rv64gc"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-04.c b/gcc/testsuite/gcc.target/riscv/target-attr-04.c new file mode 100644 index 00000000000..369d6514e5a --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-04.c @@ -0,0 +1,28 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc_zba -O2 -mabi=lp64 -mtune=rocket" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + +/* +** foo: +** ... +** # tune = sifive-7-series +** ... +** slli\s*a1,a1,1 +** add\s*a0,a1,a0 +** ... +*/ +long foo() __attribute__((target("cpu=sifive-u74"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-05.c b/gcc/testsuite/gcc.target/riscv/target-attr-05.c new file mode 100644 index 00000000000..c75368dcebf --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-05.c @@ -0,0 +1,27 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc_zba -O2 -mabi=lp64 -mtune=rocket" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + +/* +** foo: +** ... +** # tune = sifive-7-series +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long foo() __attribute__((target("cpu=sifive-u74;arch=rv64gc_zba"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-06.c b/gcc/testsuite/gcc.target/riscv/target-attr-06.c new file mode 100644 index 00000000000..369c95eeb54 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-06.c @@ -0,0 +1,27 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc_zba -O2 -mabi=lp64 -mtune=rocket" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + +/* +** foo: +** ... +** # tune = sifive-5-series +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long foo() __attribute__((target("cpu=sifive-u74;tune=sifive-5-series;arch=rv64gc_zba"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-07.c b/gcc/testsuite/gcc.target/riscv/target-attr-07.c new file mode 100644 index 00000000000..4ff81166a62 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-07.c @@ -0,0 +1,25 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc_zba -O2 -mabi=lp64 -mtune=rocket" } */ +/* { dg-final { check-function-bodies "**" "" } } */ + +/* +** foo: +** ... +** # tune = sifive-5-series +** ... +*/ +long foo() __attribute__((target("tune=sifive-5-series"))); +long foo(long a, long b){ + return a + (b * 2); +} + +/* +** bar: +** ... +** sh1add\s*a0,a1,a0 +** ... +*/ +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-01.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-01.c new file mode 100644 index 00000000000..91cbcaac21d --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-01.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target("arch=rv64gc_zba;;"))); /* { dg-error "malformed" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-02.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-02.c new file mode 100644 index 00000000000..0c838bb3ca7 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-02.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target("cpu=xyz-cpu"))); /* { dg-error "unknown CPU" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-03.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-03.c new file mode 100644 index 00000000000..09702d1690a --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-03.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target("tune=xyz-cpu"))); /* { dg-error "unknown TUNE" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-04.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-04.c new file mode 100644 index 00000000000..1d9a0ffdd88 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-04.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target(123))); /* { dg-error "argument not a string" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-05.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-05.c new file mode 100644 index 00000000000..599d0a73ac0 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-05.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target(""))); /* { dg-error "empty string in attribute" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-06.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-06.c new file mode 100644 index 00000000000..7bd7446e9eb --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-06.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target("arch=*x"))); /* { dg-error "must start with + or rv" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-bad-07.c b/gcc/testsuite/gcc.target/riscv/target-attr-bad-07.c new file mode 100644 index 00000000000..ca54baf6aad --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-bad-07.c @@ -0,0 +1,13 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + + +long foo() __attribute__((target("arch=+zbb_zba"))); /* { dg-error "must start with + or rv" } */ +long foo(long a, long b){ + return a + (b * 2); +} + +long bar(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-warning-01.c b/gcc/testsuite/gcc.target/riscv/target-attr-warning-01.c new file mode 100644 index 00000000000..d4b6e4e505a --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-warning-01.c @@ -0,0 +1,8 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + +long foo() __attribute__((target("arch=rv64gc_zba;arch=rv64gc_zba"))); /* { dg-warning "arch appears more than once" } */ +long foo(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-warning-02.c b/gcc/testsuite/gcc.target/riscv/target-attr-warning-02.c new file mode 100644 index 00000000000..b43b131c955 --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-warning-02.c @@ -0,0 +1,8 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + +long foo() __attribute__((target("cpu=sifive-u74;cpu=sifive-u74"))); /* { dg-warning "cpu appears more than once" } */ +long foo(long a, long b){ + return a + (b * 2); +} diff --git a/gcc/testsuite/gcc.target/riscv/target-attr-warning-03.c b/gcc/testsuite/gcc.target/riscv/target-attr-warning-03.c new file mode 100644 index 00000000000..551c56e37dc --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/target-attr-warning-03.c @@ -0,0 +1,8 @@ +/* { dg-do compile } */ +/* { dg-skip-if "" { *-*-* } { "-fno-fat-lto-objects" } } */ +/* { dg-options "-march=rv64gc -O2 -mabi=lp64" } */ + +long foo() __attribute__((target("tune=sifive-u74;tune=sifive-u74"))); /* { dg-warning "tune appears more than once" } */ +long foo(long a, long b){ + return a + (b * 2); +}