diff mbox

Define 3-argument overloads of std::hypot for C++17 (P0030R1)

Message ID 20160929105807.GJ29482@redhat.com
State New
Headers show

Commit Message

Jonathan Wakely Sept. 29, 2016, 10:58 a.m. UTC
On 29/09/16 11:47 +0100, Jonathan Wakely wrote:
>On 29/09/16 12:39 +0200, Rainer Orth wrote:
>>Hi Jonathan,
>>
>>>>That would suggest Solaris uses include/c_std/cmath (where I forgot to
>>>>add the new overloads) rather than include/c_global/cmath ... is that
>>>>right?
>>>
>>>Alternatively it's using c_global/cmath but _GLIBCXX_USE_C99_MATH_TR1
>>>is not defined, as the new overloads are inside that block. I thought
>>>that was defined for Solaris though, which is why we have the
>>>__CORRECT_ISO_CPP11_MATH_H_PROTO there in that file.
>>
>>it is indeed, at least initially.  What I see in preprocessed input is
>>this:
>>
>>ro@galeras 208 > grep _GLIBCXX_USE_C99_MATH testsuite/normal4/hypot.ii
>>#define _GLIBCXX_USE_C99_MATH _GLIBCXX11_USE_C99_MATH
>>#define _GLIBCXX_USE_C99_MATH_TR1 1
>>#undef _GLIBCXX_USE_C99_MATH
>>#undef _GLIBCXX_USE_C99_MATH_TR1
>>
>>It turns out the #undef's are from <math.h>:
>>
>>#if __cplusplus >= 201103L
>>#undef  _GLIBCXX_USE_C99_MATH
>>#undef  _GLIBCXX_USE_C99_MATH_TR1
>>#endif
>>
>>No idea what this nonsense is trying to accomplish!  It's already in
>>Solaris 11.3, however.
>
>Wow.
>
>If only there was some way the Solaris team could contact us so we
>could coordinate and stop adding more and more hacks to mess with each
>others headers. But I assume they don't have access to the www or
>email, because the only other explanation is too rude to say on a
>public list.

Presumably they now provide all the declarations for C++11, so we
don't need to declare them. Moving the new hypot overload outside the
_GLIBCXX_USE_C99_MATH_TR1 block should mean it's declared. That will
break when Solaris adds C++17 support, so we'd better add some macro
to guard the new hypot overloads, so they can be disabled again. Let's
call it __CORRECT_ISO_CPP17_MATH_H_PROTO (and maybe add a coment like
"Dear Solaris team, ...").

Does this work?

Comments

Rainer Orth Sept. 29, 2016, 12:02 p.m. UTC | #1
Hi Jonathan,

>>If only there was some way the Solaris team could contact us so we
>>could coordinate and stop adding more and more hacks to mess with each
>>others headers. But I assume they don't have access to the www or
>>email, because the only other explanation is too rude to say on a
>>public list.
>
> Presumably they now provide all the declarations for C++11, so we
> don't need to declare them. Moving the new hypot overload outside the

still this doesn't need into <math.h>, but into libstdc++ configury
IMNSHO.

> _GLIBCXX_USE_C99_MATH_TR1 block should mean it's declared. That will
> break when Solaris adds C++17 support, so we'd better add some macro
> to guard the new hypot overloads, so they can be disabled again. Let's
> call it __CORRECT_ISO_CPP17_MATH_H_PROTO (and maybe add a coment like
> "Dear Solaris team, ...").

... which assumes they do read this ;-)

> Does this work?

It does indeed, at least running the single testcase with runtest now
passes.

Thanks.
        Rainer
Jonathan Wakely Sept. 29, 2016, 12:12 p.m. UTC | #2
On 29/09/16 14:02 +0200, Rainer Orth wrote:
>Hi Jonathan,
>
>>>If only there was some way the Solaris team could contact us so we
>>>could coordinate and stop adding more and more hacks to mess with each
>>>others headers. But I assume they don't have access to the www or
>>>email, because the only other explanation is too rude to say on a
>>>public list.
>>
>> Presumably they now provide all the declarations for C++11, so we
>> don't need to declare them. Moving the new hypot overload outside the
>
>still this doesn't need into <math.h>, but into libstdc++ configury
>IMNSHO.

I agree. Presumably they wanted their updated headers to work with
existing GCC releases, and not have to wait until we modified our
configury to cooperate with their changes.

But if they simply communicated with us we could plan for that kind of
thing in advance, and ensure we don't keep trying to fix each others
headers from a distance.

>> _GLIBCXX_USE_C99_MATH_TR1 block should mean it's declared. That will
>> break when Solaris adds C++17 support, so we'd better add some macro
>> to guard the new hypot overloads, so they can be disabled again. Let's
>> call it __CORRECT_ISO_CPP17_MATH_H_PROTO (and maybe add a coment like
>> "Dear Solaris team, ...").
>
>... which assumes they do read this ;-)

Indeed.

Since they seem to be adding declarations to <math.h> and only in the
global namespace, and the 3-argument form doesn't exist in the global
namespace, maybe we can assume they aren't going to add it to
<math.h>.


>> Does this work?
>
>It does indeed, at least running the single testcase with runtest now
>passes.

Thanks, I'll commit that soon.
diff mbox

Patch

diff --git a/libstdc++-v3/include/c_global/cmath b/libstdc++-v3/include/c_global/cmath
index fffa0e7..86ffd34 100644
--- a/libstdc++-v3/include/c_global/cmath
+++ b/libstdc++-v3/include/c_global/cmath
@@ -1455,46 +1455,6 @@  _GLIBCXX_BEGIN_NAMESPACE_VERSION
       return hypot(__type(__x), __type(__y));
     }
 
-#if __cplusplus > 201402L
-#define __cpp_lib_hypot 201603
-  // [c.math.hypot3], three-dimensional hypotenuse
-
-  template<typename _Tp>
-    inline _Tp
-    __hypot3(_Tp __x, _Tp __y, _Tp __z)
-    {
-      __x = std::abs(__x);
-      __y = std::abs(__y);
-      __z = std::abs(__z);
-      if (_Tp __a = __x < __y ? __y < __z ? __z : __y : __x < __z ? __z : __x)
-	return __a * std::sqrt((__x / __a) * (__x / __a)
-			       + (__y / __a) * (__y / __a)
-			       + (__z / __a) * (__z / __a));
-      else
-	return {};
-    }
-
-  inline float
-  hypot(float __x, float __y, float __z)
-  { return std::__hypot3<float>(__x, __y, __z); }
-
-  inline double
-  hypot(double __x, double __y, double __z)
-  { return std::__hypot3<double>(__x, __y, __z); }
-
-  inline long double
-  hypot(long double __x, long double __y, long double __z)
-  { return std::__hypot3<long double>(__x, __y, __z); }
-
-  template<typename _Tp, typename _Up, typename _Vp>
-    typename __gnu_cxx::__promote_3<_Tp, _Up, _Vp>::__type
-    hypot(_Tp __x, _Up __y, _Vp __z)
-    {
-      using __type = typename __gnu_cxx::__promote_3<_Tp, _Up, _Vp>::__type;
-      return std::__hypot3<__type>(__x, __y, __z);
-    }
-#endif // C++17
-
 #ifndef __CORRECT_ISO_CPP11_MATH_H_PROTO
   constexpr int
   ilogb(float __x)
@@ -1830,6 +1790,55 @@  _GLIBCXX_END_NAMESPACE_VERSION
 
 #endif // C++11
 
+#if __cplusplus > 201402L
+namespace std _GLIBCXX_VISIBILITY(default)
+{
+_GLIBCXX_BEGIN_NAMESPACE_VERSION
+
+#ifndef __CORRECT_ISO_CPP17_MATH_H_PROTO
+  // [c.math.hypot3], three-dimensional hypotenuse
+#define __cpp_lib_hypot 201603
+
+  template<typename _Tp>
+    inline _Tp
+    __hypot3(_Tp __x, _Tp __y, _Tp __z)
+    {
+      __x = std::abs(__x);
+      __y = std::abs(__y);
+      __z = std::abs(__z);
+      if (_Tp __a = __x < __y ? __y < __z ? __z : __y : __x < __z ? __z : __x)
+	return __a * std::sqrt((__x / __a) * (__x / __a)
+			       + (__y / __a) * (__y / __a)
+			       + (__z / __a) * (__z / __a));
+      else
+	return {};
+    }
+
+  inline float
+  hypot(float __x, float __y, float __z)
+  { return std::__hypot3<float>(__x, __y, __z); }
+
+  inline double
+  hypot(double __x, double __y, double __z)
+  { return std::__hypot3<double>(__x, __y, __z); }
+
+  inline long double
+  hypot(long double __x, long double __y, long double __z)
+  { return std::__hypot3<long double>(__x, __y, __z); }
+
+  template<typename _Tp, typename _Up, typename _Vp>
+    typename __gnu_cxx::__promote_3<_Tp, _Up, _Vp>::__type
+    hypot(_Tp __x, _Up __y, _Vp __z)
+    {
+      using __type = typename __gnu_cxx::__promote_3<_Tp, _Up, _Vp>::__type;
+      return std::__hypot3<__type>(__x, __y, __z);
+#endif
+    }
+_GLIBCXX_END_NAMESPACE_VERSION
+} // namespace
+#endif // C++17
+
+
 #if _GLIBCXX_USE_STD_SPEC_FUNCS
 #  include <bits/specfun.h>
 #endif