| Message ID | 20260506124515.400295-1-tkaminsk@redhat.com |
|---|---|
| State | New |
| Headers |
Return-Path: <gcc-patches-bounces~patchwork=sourceware.org@gcc.gnu.org> X-Original-To: patchwork@sourceware.org Delivered-To: patchwork@sourceware.org Received: from vm01.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id CAA954BA23E6 for <patchwork@sourceware.org>; Wed, 6 May 2026 12:46:13 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org CAA954BA23E6 Authentication-Results: sourceware.org; dkim=pass (1024-bit key, unprotected) header.d=redhat.com header.i=@redhat.com header.a=rsa-sha256 header.s=mimecast20190719 header.b=eSGCL/SS 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.133.124]) by sourceware.org (Postfix) with ESMTP id CC4234BA23D8 for <gcc-patches@gcc.gnu.org>; Wed, 6 May 2026 12:45:21 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org CC4234BA23D8 Authentication-Results: sourceware.org; dmarc=pass (p=quarantine dis=none) header.from=redhat.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=redhat.com ARC-Filter: OpenARC Filter v1.0.0 sourceware.org CC4234BA23D8 Authentication-Results: sourceware.org; arc=none smtp.remote-ip=170.10.133.124 ARC-Seal: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1778071521; cv=none; b=onTktq5kYIYLE1h/Cj1cY5+F2Aw2xkcxKNuEBEy4NTkIu60ONHigOr148oR2trAFka7kvA+k+FiPSlytrZyNBkVzscfrQkt/JBsz3ePOar46w9C1jz0DWhuF0GQnW+B3vp2obkd3khVytYpOtA1eUL/u+M7nE0PcFmYng33A4co= ARC-Message-Signature: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1778071521; c=relaxed/simple; bh=J8ReQ/OTOp11kf6Z4u5Erhw/iXdWhCSQ/OjWihWGkhs=; h=DKIM-Signature:From:To:Subject:Date:Message-ID:MIME-Version; b=gVfR1EUb4tLkOaIDxusBa/n2wuuB9Xh3AcLUf7BQwDIpwq5yo+z0mBWxpLFmUL6O377UmLDjeT5vU445kgFiqRbDvHUr8BzfDor7MqXmOM+UC25sU1i9qYbgQscVK/QXbuZiavTFtZB6sL+XxinfD0IvBgLp6EUECYpqI5dOrFo= ARC-Authentication-Results: i=1; sourceware.org; dkim=pass (1024-bit key, unprotected) header.d=redhat.com header.i=@redhat.com header.a=rsa-sha256 header.s=mimecast20190719 header.b=eSGCL/SS DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org CC4234BA23D8 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=redhat.com; s=mimecast20190719; t=1778071521; h=from:from:reply-to:subject:subject:date:date:message-id:message-id: to:to:cc:mime-version:mime-version:content-type:content-type: content-transfer-encoding:content-transfer-encoding; bh=cSZHi0ykwBmB/fTX864yqLOEG/x8ZT3RjLp2GZnv/Ug=; b=eSGCL/SSlARtIsW1i3xASOnTXc9QZkx5fqznqN6xpZxzR+mnRo6BCBpt8gsqdh+9Lr3ex7 V0muAKU4SjeMC4qS9ePlANtHQ4HxWlVEDJ74r0EW5huMXkT3mR/5/aR9kTyCq1GRNmVGta rjinZ0qa0//3GVtm5cfhfrPki1qZ/xg= Received: from mx-prod-mc-05.mail-002.prod.us-west-2.aws.redhat.com (ec2-54-186-198-63.us-west-2.compute.amazonaws.com [54.186.198.63]) by relay.mimecast.com with ESMTP with STARTTLS (version=TLSv1.3, cipher=TLS_AES_256_GCM_SHA384) id us-mta-250-PXl44SIvNO2xJXRsdHiiwQ-1; Wed, 06 May 2026 08:45:18 -0400 X-MC-Unique: PXl44SIvNO2xJXRsdHiiwQ-1 X-Mimecast-MFC-AGG-ID: PXl44SIvNO2xJXRsdHiiwQ_1778071517 Received: from mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com (mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com [10.30.177.4]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (No client certificate requested) by mx-prod-mc-05.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTPS id 5B6861956094; Wed, 6 May 2026 12:45:17 +0000 (UTC) Received: from localhost (unknown [10.44.34.53]) by mx-prod-int-01.mail-002.prod.us-west-2.aws.redhat.com (Postfix) with ESMTP id B83F03002D2D; Wed, 6 May 2026 12:45:16 +0000 (UTC) From: =?utf-8?q?Tomasz_Kami=C5=84ski?= <tkaminsk@redhat.com> To: libstdc++@gcc.gnu.org, gcc-patches@gcc.gnu.org Subject: [PATCH] libstdc++: Format all contiguous ranges usign spoan. Date: Wed, 6 May 2026 14:39:03 +0200 Message-ID: <20260506124515.400295-1-tkaminsk@redhat.com> MIME-Version: 1.0 X-Scanned-By: MIMEDefang 3.4.1 on 10.30.177.4 X-Mimecast-Spam-Score: 0 X-Mimecast-MFC-PROC-ID: DHr_nI2Z88H_1geP5KvoZa110hKvMg62x4VIE8qTd6M_1778071517 X-Mimecast-Originator: redhat.com Content-Transfer-Encoding: 8bit content-type: text/plain; charset="US-ASCII"; x-default=true X-Spam-Status: No, score=-10.8 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_BLOCKED, RCVD_IN_MSPIKE_H5, RCVD_IN_MSPIKE_WL, RCVD_IN_SBL_CSS, SPF_HELO_PASS, SPF_NONE, TXREP autolearn=unavailable autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list <gcc-patches.gcc.gnu.org> List-Unsubscribe: <https://gcc.gnu.org/mailman/options/gcc-patches>, <mailto:gcc-patches-request@gcc.gnu.org?subject=unsubscribe> List-Archive: <https://gcc.gnu.org/pipermail/gcc-patches/> List-Post: <mailto:gcc-patches@gcc.gnu.org> List-Help: <mailto:gcc-patches-request@gcc.gnu.org?subject=help> List-Subscribe: <https://gcc.gnu.org/mailman/listinfo/gcc-patches>, <mailto:gcc-patches-request@gcc.gnu.org?subject=subscribe> Errors-To: gcc-patches-bounces~patchwork=sourceware.org@gcc.gnu.org |
| Series |
libstdc++: Format all contiguous ranges usign spoan.
|
|
Commit Message
Tomasz Kaminski
May 6, 2026, 12:39 p.m. UTC
We convert all contiguous ranges into span of the possibly-const qualified _Tp (__format::__maybe_const<_Tp, _CharT>). The span object is const qualifed, to trigger _M_format<const span<T>> specialization, that is already used by formatter specialization for ranges. This conversion is applied regardless if range is sized, and ranges::distance to compute the size. Even for user-defined iterators, they will observe range being iterated only once. Finally, using raw pointers to iterate range during formatting guarantees, that no stdio lock will be taken. In consequence it would be now possible to enable_nonlocking_formatter_optimization for all contiguous ranges. libstdc++-v3/ChangeLog: * include/std/format (range_formatter::format): Format all contiguous ranges as span<__format::__maybe_const<_Tp, _CharT>>. --- For the file that formatted vector, array/span (of various sizes), and views adapated via them I have seen around 1s reduction. Less that I expected, but I think symbol reduction is valuable. And especially the fact that such approach could make vector use non-buffered print. I think we may want to change default enable_nonlocking_formatter_optimization to be true for contiguous ranges (we may need to check if there is no user-defined specialization formatter - check if one of our nested typedefs exits). I think that is technically non-coforming, but it is safe, and I doubt people will complain that print with vector is faster. Especially that for ranges we may need to allocate pretty large string. Testing on x86_64-linux. *format* test passed in all standard modes. OK for trunk when all test passes. libstdc++-v3/include/std/format | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
Comments
On Wed, 6 May 2026 at 13:45, Tomasz KamiĆski <tkaminsk@redhat.com> wrote: > > We convert all contiguous ranges into span of the possibly-const qualified > _Tp (__format::__maybe_const<_Tp, _CharT>). The span object is const qualifed, > to trigger _M_format<const span<T>> specialization, that is already used by > formatter specialization for ranges. > > This conversion is applied regardless if range is sized, and ranges::distance > to compute the size. Even for user-defined iterators, they will observe range > being iterated only once. > > Finally, using raw pointers to iterate range during formatting guarantees, > that no stdio lock will be taken. In consequence it would be now possible > to enable_nonlocking_formatter_optimization for all contiguous ranges. > > libstdc++-v3/ChangeLog: > > * include/std/format (range_formatter::format): Format all > contiguous ranges as span<__format::__maybe_const<_Tp, _CharT>>. > --- > For the file that formatted vector, array/span (of various sizes), and > views adapated via them I have seen around 1s reduction. Less that I > expected, but I think symbol reduction is valuable. And especially the > fact that such approach could make vector use non-buffered print. > > I think we may want to change default enable_nonlocking_formatter_optimization > to be true for contiguous ranges (we may need to check if there is no > user-defined specialization formatter - check if one of our nested > typedefs exits). > I think that is technically non-coforming, but it is safe, and I doubt > people will complain that print with vector is faster. Especially that > for ranges we may need to allocate pretty large string. > > Testing on x86_64-linux. *format* test passed in all standard modes. > OK for trunk when all test passes. Yes, this is nice. "usign spoan" -> "using span" in the first line of the commit log. OK for trunk with that change. > > libstdc++-v3/include/std/format | 8 +++++++- > 1 file changed, 7 insertions(+), 1 deletion(-) > > diff --git a/libstdc++-v3/include/std/format b/libstdc++-v3/include/std/format > index 4627381fa9e..60adca93b5d 100644 > --- a/libstdc++-v3/include/std/format > +++ b/libstdc++-v3/include/std/format > @@ -6175,7 +6175,13 @@ namespace __format > format(_Rg&& __rg, basic_format_context<_Out, _CharT>& __fc) const > { > using _Range = remove_reference_t<_Rg>; > - if constexpr (__format::__simply_formattable_range<_Range, _CharT>) > + if constexpr (ranges::contiguous_range<_Rg>) > + { > + const span<__format::__maybe_const<_Tp, _CharT>> > + __spn(ranges::data(__rg), size_t(ranges::distance(__rg))); > + return _M_format(__spn, __fc); > + } > + else if constexpr (__format::__simply_formattable_range<_Range, _CharT>) > return _M_format<const _Range>(__rg, __fc); > else > return _M_format(__rg, __fc); > -- > 2.54.0 >
diff --git a/libstdc++-v3/include/std/format b/libstdc++-v3/include/std/format index 4627381fa9e..60adca93b5d 100644 --- a/libstdc++-v3/include/std/format +++ b/libstdc++-v3/include/std/format @@ -6175,7 +6175,13 @@ namespace __format format(_Rg&& __rg, basic_format_context<_Out, _CharT>& __fc) const { using _Range = remove_reference_t<_Rg>; - if constexpr (__format::__simply_formattable_range<_Range, _CharT>) + if constexpr (ranges::contiguous_range<_Rg>) + { + const span<__format::__maybe_const<_Tp, _CharT>> + __spn(ranges::data(__rg), size_t(ranges::distance(__rg))); + return _M_format(__spn, __fc); + } + else if constexpr (__format::__simply_formattable_range<_Range, _CharT>) return _M_format<const _Range>(__rg, __fc); else return _M_format(__rg, __fc);