From patchwork Thu Sep 1 09:29:32 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jonathan Wakely X-Patchwork-Id: 888 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:adf:ecc5:0:0:0:0:0 with SMTP id s5csp162776wro; Thu, 1 Sep 2022 02:31:16 -0700 (PDT) X-Google-Smtp-Source: AA6agR6Hcbk91gAOaNJzUfNdC9RaSBnd3EumpzHKH0IIHmbjNhipdzy8G7AJ1kcyw4DjUjiR9EkR X-Received: by 2002:a17:906:8c7:b0:730:c1a9:e187 with SMTP id o7-20020a17090608c700b00730c1a9e187mr23040937eje.55.1662024675890; Thu, 01 Sep 2022 02:31:15 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1662024675; cv=none; d=google.com; s=arc-20160816; b=rPs7cllTP5TaVyIHT3i5ZGpF27DeqHrEUzwVgHjmJKXayOQRh0wyyiaB3Yvu8cN/M4 hXdjoj4pjbWtPnECDGgOYylc++M3aVH7ZmWUP6EFpztj1uj6MJ6/TuHmwI18NLR2BAA2 PY1LG/Ua670pJXsh6eDYSwacTP27ERylCHY4XFKw8Kdg9mYoFki6dB4wlxGXuCzi43ZH viCjMIUTcu0h8WnOFh7MDc4tNq5ojgb3K8hgE71C65m6koRGWu9X7YB+pFeVAg+Gjcr/ nWzgp5IdAr1g3y1U/ro3fLGBvEKciVtsXA/wf+4st+foDkCAaChCLBh9UtHOTbgC4lhX kpAQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=sender:errors-to:reply-to:from:list-subscribe:list-help:list-post :list-archive:list-unsubscribe:list-id:precedence :content-transfer-encoding:mime-version:message-id:date:subject:to :dmarc-filter:delivered-to:dkim-signature:dkim-filter; bh=NZaqktcnA0plGWDRFyNnR1zpICkq3lQixYmgpBZXg38=; b=MCwIt9YnyA53prmuSbotzaHQo4eTbwDoRdbMFCvqhN1c4bE9l1+QTbjH0M0ee+1Ab3 6Pke3pPcDG3SxrS6P4L6mD9+L/LcGwF1TFqVqBZyFoz8VVsXQKmNX+FE3Dn95vR8Cahp pQCF90eIQOQAs6tnJh3oo16sGqUWb0EwoCxl8N3TwWv1S9cJOEwZ8ikIkMNG7NATSrSP /aVIBl8l3uJ8h4iia9twU/RHFCthOq878esr8FWs9vctWCOyDgMXCH2h1oFhqOyFrAfr QkKetJ9fD/HyBaYrS5PoG9SFU2Qh3hGMPvKLIg7OTXiik9FE6rsPMXhGQ6KisH7H8mmk hNpA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@gcc.gnu.org header.s=default header.b=cMesEdB4; spf=pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 2620:52:3:1:0:246e:9693:128c as permitted sender) smtp.mailfrom="gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=gnu.org Received: from sourceware.org (server2.sourceware.org. [2620:52:3:1:0:246e:9693:128c]) by mx.google.com with ESMTPS id e28-20020a50d4dc000000b00445e9f07800si1543654edj.501.2022.09.01.02.31.15 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 01 Sep 2022 02:31:15 -0700 (PDT) Received-SPF: pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 2620:52:3:1:0:246e:9693:128c as permitted sender) client-ip=2620:52:3:1:0:246e:9693:128c; Authentication-Results: mx.google.com; dkim=pass header.i=@gcc.gnu.org header.s=default header.b=cMesEdB4; spf=pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 2620:52:3:1:0:246e:9693:128c as permitted sender) smtp.mailfrom="gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org"; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=gnu.org Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 3FB1B3853558 for ; Thu, 1 Sep 2022 09:30:34 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 3FB1B3853558 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1662024634; bh=NZaqktcnA0plGWDRFyNnR1zpICkq3lQixYmgpBZXg38=; h=To:Subject:Date:List-Id:List-Unsubscribe:List-Archive:List-Post: List-Help:List-Subscribe:From:Reply-To:From; b=cMesEdB4k4aJGL/hpNhl/gksf9pDioiDJ2j/tGOkGbMjwtUa5BdadC/nV4zqQyyOT U87yUg/8KNRaIT5LtQd2vjm7d0aqpBP23JchDsfEof0WdIf8qrGhUGc4+erDML5iSm MoOkNY2/TzXTplbIRIxiNpGsgpGV30gv0ptWp124= X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from us-smtp-delivery-124.mimecast.com (us-smtp-delivery-124.mimecast.com [170.10.129.124]) by sourceware.org (Postfix) with ESMTPS id 000D63857012 for ; Thu, 1 Sep 2022 09:29:49 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org 000D63857012 Received: from mimecast-mx02.redhat.com (mimecast-mx02.redhat.com [66.187.233.88]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id us-mta-221-EfBpHGTOMDubULTD833P_w-1; Thu, 01 Sep 2022 05:29:40 -0400 X-MC-Unique: EfBpHGTOMDubULTD833P_w-1 Received: from smtp.corp.redhat.com (int-mx03.intmail.prod.int.rdu2.redhat.com [10.11.54.3]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mimecast-mx02.redhat.com (Postfix) with ESMTPS id 4B31590DE22; Thu, 1 Sep 2022 09:29:33 +0000 (UTC) Received: from localhost (unknown [10.33.36.187]) by smtp.corp.redhat.com (Postfix) with ESMTP id 14620112131E; Thu, 1 Sep 2022 09:29:32 +0000 (UTC) To: libstdc++@gcc.gnu.org, gcc-patches@gcc.gnu.org Subject: [committed] libstdc++: Optimize array traits Date: Thu, 1 Sep 2022 10:29:32 +0100 Message-Id: <20220901092932.193133-1-jwakely@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 2.78 on 10.11.54.3 X-Mimecast-Spam-Score: 0 X-Mimecast-Originator: redhat.com X-Spam-Status: No, score=-12.3 required=5.0 tests=BAYES_00, DKIMWL_WL_HIGH, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_LOW, SPF_HELO_NONE, SPF_NONE, TXREP, T_SCC_BODY_TEXT_LINE 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.29 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-Patchwork-Original-From: Jonathan Wakely via Gcc-patches From: Jonathan Wakely Reply-To: Jonathan Wakely Errors-To: gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org Sender: "Gcc-patches" X-getmail-retrieved-from-mailbox: =?utf-8?q?INBOX?= X-GMAIL-THRID: =?utf-8?q?1742759186672589890?= X-GMAIL-MSGID: =?utf-8?q?1742759186672589890?= Tested powerpc64le-linux, pushed to trunk. This is the first in a series of patches to optimize compile time for the contents of . -- >8 -- Improve compile times by avoiding unnecessary class template instantiations. __is_array_known_bounds and __is_array_unknown_bounds can be defined without instantiating extent, by providing partial specializations for the true cases. std::extent can avoid recursing down through a multidimensional array, so it stops after providing the result. Previously extent would instantiate extent and extent as well. std::is_array_v can use partial specializations to avoid instantiating std::is_array, and similarly for std::rank_v and std::extent_v. std::is_bounded_array_v and std::is_unbounded_array_v can also use partial specializations, and then the class templates can be defined in terms of the variable templates. This makes sense for these traits, because they are new in C++20 and so the variable templates are always available, which isn't true in general for C++11 and C++14 traits. libstdc++-v3/ChangeLog: * include/std/type_traits (__is_array_known_bounds): Add partial specialization instead of using std::extent. (__is_array_unknown_bounds): Likewise. (extent): Add partial specializations to stop recursion after the result is found. (is_array_v): Add partial specializations instead of instantiating the class template. (rank_v, extent_v): Likewise. (is_bounded_array_v, is_unbounded_array_v): Likewise. (is_bounded_array, is_unbounded_array): Define in terms of the variable templates. --- libstdc++-v3/include/std/type_traits | 102 ++++++++++++++++++--------- 1 file changed, 69 insertions(+), 33 deletions(-) diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits index c2f5cb9c806..5984442c0aa 100644 --- a/libstdc++-v3/include/std/type_traits +++ b/libstdc++-v3/include/std/type_traits @@ -867,21 +867,28 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION template auto declval() noexcept -> decltype(__declval<_Tp>(0)); - template - struct extent; - template struct remove_all_extents; /// @cond undocumented template struct __is_array_known_bounds - : public integral_constant::value > 0)> + : public false_type + { }; + + template + struct __is_array_known_bounds<_Tp[_Size]> + : public true_type { }; template struct __is_array_unknown_bounds - : public __and_, __not_>> + : public false_type + { }; + + template + struct __is_array_unknown_bounds<_Tp[]> + : public true_type { }; // Destructible and constructible type properties. @@ -1430,23 +1437,25 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION : public integral_constant::value> { }; /// extent - template + template struct extent - : public integral_constant { }; + : public integral_constant { }; - template + template + struct extent<_Tp[_Size], 0> + : public integral_constant { }; + + template struct extent<_Tp[_Size], _Uint> - : public integral_constant::value> - { }; + : public extent<_Tp, _Uint - 1>::type { }; + + template + struct extent<_Tp[], 0> + : public integral_constant { }; template struct extent<_Tp[], _Uint> - : public integral_constant::value> - { }; + : public extent<_Tp, _Uint - 1>::type { }; // Type relations. @@ -3133,8 +3142,14 @@ template inline constexpr bool is_integral_v = is_integral<_Tp>::value; template inline constexpr bool is_floating_point_v = is_floating_point<_Tp>::value; + template - inline constexpr bool is_array_v = is_array<_Tp>::value; + inline constexpr bool is_array_v = false; +template + inline constexpr bool is_array_v<_Tp[]> = true; +template + inline constexpr bool is_array_v<_Tp[_Num]> = true; + template inline constexpr bool is_pointer_v = is_pointer<_Tp>::value; template @@ -3276,10 +3291,25 @@ template has_virtual_destructor<_Tp>::value; template inline constexpr size_t alignment_of_v = alignment_of<_Tp>::value; + template - inline constexpr size_t rank_v = rank<_Tp>::value; + inline constexpr size_t rank_v = 0; +template + inline constexpr size_t rank_v<_Tp[_Size]> = 1 + rank_v<_Tp>; +template + inline constexpr size_t rank_v<_Tp[]> = 1 + rank_v<_Tp>; + template - inline constexpr size_t extent_v = extent<_Tp, _Idx>::value; + inline constexpr size_t extent_v = 0; +template + inline constexpr size_t extent_v<_Tp[_Size], 0> = _Size; +template + inline constexpr size_t extent_v<_Tp[_Size], _Idx> = extent_v<_Tp, _Idx - 1>; +template + inline constexpr size_t extent_v<_Tp[], 0> = 0; +template + inline constexpr size_t extent_v<_Tp[], _Idx> = extent_v<_Tp, _Idx - 1>; + #ifdef _GLIBCXX_HAVE_BUILTIN_IS_SAME template inline constexpr bool is_same_v = __is_same(_Tp, _Up); @@ -3407,32 +3437,38 @@ template #define __cpp_lib_bounded_array_traits 201902L + /// True for a type that is an array of known bound. + /// @ingroup variable_templates + /// @since C++20 + template + inline constexpr bool is_bounded_array_v = false; + + template + inline constexpr bool is_bounded_array_v<_Tp[_Size]> = true; + + /// True for a type that is an array of unknown bound. + /// @ingroup variable_templates + /// @since C++20 + template + inline constexpr bool is_unbounded_array_v = false; + + template + inline constexpr bool is_unbounded_array_v<_Tp[]> = true; + /// True for a type that is an array of known bound. /// @since C++20 template struct is_bounded_array - : public __is_array_known_bounds<_Tp> + : public bool_constant> { }; /// True for a type that is an array of unknown bound. /// @since C++20 template struct is_unbounded_array - : public __is_array_unknown_bounds<_Tp> + : public bool_constant> { }; - /// @ingroup variable_templates - /// @since C++20 - template - inline constexpr bool is_bounded_array_v - = is_bounded_array<_Tp>::value; - - /// @ingroup variable_templates - /// @since C++20 - template - inline constexpr bool is_unbounded_array_v - = is_unbounded_array<_Tp>::value; - #if __has_builtin(__is_layout_compatible) /// @since C++20