[gcc r16-5666] libstdc++: Fix exposure of TU-local lambda in __detail::__func_handle_t.

Tomasz Kaminski tkaminsk@gcc.gnu.org
Thu Nov 27 14:02:36 GMT 2025


https://gcc.gnu.org/g:2c1e896ac970654a092e565f82ba12241c8286df

commit r16-5666-g2c1e896ac970654a092e565f82ba12241c8286df
Author: Tomasz Kamiński <tkaminsk@redhat.com>
Date:   Thu Nov 27 14:31:51 2025 +0100

    libstdc++: Fix exposure of TU-local lambda in __detail::__func_handle_t.
    
    The lambda is considered to be TU-local entity, use a named function
    instead.
    
    As drive-by, a functor stored inside __func_handle::_Inplace is renamed
    to _M_fn, as we no longer limit the functor type to function pointers.
    
    libstdc++-v3/ChangeLog:
    
            * include/std/ranges (__func_handle::__select): Named function
            extracted from local lambda.
            (__detail::__func_handle_t): Define using __func_handle::__select.
            (__func_handle::_Inplace): Raname _M_ptr to _M_fn.
    
    Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
    Signed-off-by: Tomasz Kamiński <tkaminsk@redhat.com>

Diff:
---
 libstdc++-v3/include/std/ranges | 45 +++++++++++++++++++++++------------------
 1 file changed, 25 insertions(+), 20 deletions(-)

diff --git a/libstdc++-v3/include/std/ranges b/libstdc++-v3/include/std/ranges
index 7c5ac931e313..b3105c553839 100644
--- a/libstdc++-v3/include/std/ranges
+++ b/libstdc++-v3/include/std/ranges
@@ -346,23 +346,23 @@ namespace ranges
 
 	    constexpr explicit
 	    _Inplace(_Fn __func) noexcept
-	    : _M_ptr(__func)
+	    : _M_fn(__func)
 	    { }
 
 	    template<typename... _Iters>
 	      constexpr decltype(auto)
 	      _M_call_deref(const _Iters&... __iters) const
-	      noexcept(noexcept(_M_ptr(*__iters...)))
-	      { return _M_ptr(*__iters...); }
+	      noexcept(noexcept(_M_fn(*__iters...)))
+	      { return _M_fn(*__iters...); }
 
 	    template<typename _DistType, typename... _Iters>
 	      constexpr decltype(auto)
 	      _M_call_subscript(const _DistType __n, const _Iters&... __iters) const
-	      noexcept(noexcept(_M_ptr(__iters[iter_difference_t<_Iters>(__n)]...)))
-	      { return _M_ptr(__iters[iter_difference_t<_Iters>(__n)]...); }
+	      noexcept(noexcept(_M_fn(__iters[iter_difference_t<_Iters>(__n)]...)))
+	      { return _M_fn(__iters[iter_difference_t<_Iters>(__n)]...); }
 
 	  private:
-	    [[no_unique_address]] _Fn _M_ptr = _Fn();
+	    [[no_unique_address]] _Fn _M_fn = _Fn();
 	  };
 
 	template<typename _Fn>
@@ -448,23 +448,28 @@ namespace ranges
 	      noexcept(noexcept(_Fn::operator()(__iters[iter_difference_t<_Iters>(__n)]...)))
 	      { return _Fn::operator()(__iters[iter_difference_t<_Iters>(__n)]...); }
 	  };
+
+	  template<typename _Fn, typename... _Iters>
+	    consteval auto
+	    __select()
+	    {
+	      using _Fd = remove_cv_t<_Fn>;
+	      if constexpr (is_member_pointer_v<_Fd>)
+		return __func_handle::_InplaceMemPtr<_Fd>();
+	      else if constexpr (is_function_v<remove_pointer_t<_Fd>>)
+		return __func_handle::_Inplace<_Fd>();
+	      else if constexpr (__is_std_op_wrapper<_Fd>)
+	       return __func_handle::_Inplace<_Fd>();
+	     else if constexpr (requires (const _Iters&... __iters)
+				{ _Fd::operator()(*__iters...); })
+	       return __func_handle::_StaticCall<_Fd>();
+	     else
+	       return __func_handle::_ViaPointer<_Fn>();
+	   };
       } // __func_handle
 
       template<typename _Fn, typename... _Iters>
-	using __func_handle_t = decltype([] {
-	  using _Fd = remove_cv_t<_Fn>;
-	  if constexpr (is_member_pointer_v<_Fd>)
-	    return __func_handle::_InplaceMemPtr<_Fd>();
-	  else if constexpr (is_function_v<remove_pointer_t<_Fd>>)
-	    return __func_handle::_Inplace<_Fd>();
-	  else if constexpr (__is_std_op_wrapper<_Fd>)
-	    return __func_handle::_Inplace<_Fd>();
-	  else if constexpr (requires (const _Iters&... __iters)
-			       { _Fd::operator()(*__iters...); })
-	    return __func_handle::_StaticCall<_Fd>();
-	  else
-	    return __func_handle::_ViaPointer<_Fn>();
-	}());
+	using __func_handle_t = decltype(__func_handle::__select<_Fn, _Iters...>());
   } // namespace __detail
 
   /// A view that contains exactly one element.


More information about the Libstdc++-cvs mailing list