Skip to content
33 changes: 1 addition & 32 deletions stl/inc/cmath
Original file line number Diff line number Diff line change
Expand Up @@ -19,14 +19,6 @@ _STL_DISABLE_CLANG_WARNINGS
#pragma push_macro("new")
#undef new

_NODISCARD _Check_return_ inline double pow(_In_ double _Xx, _In_ int _Yx) noexcept /* strengthened */ {
if (_Yx == 2) {
return _Xx * _Xx;
}

return _CSTD pow(_Xx, static_cast<double>(_Yx));
}

_NODISCARD _Check_return_ inline float acos(_In_ float _Xx) noexcept /* strengthened */ {
return _CSTD acosf(_Xx);
}
Expand Down Expand Up @@ -199,14 +191,6 @@ _NODISCARD _Check_return_ inline float pow(_In_ float _Xx, _In_ float _Yx) noexc
return _CSTD powf(_Xx, _Yx);
}

_NODISCARD _Check_return_ inline float pow(_In_ float _Xx, _In_ int _Yx) noexcept /* strengthened */ {
if (_Yx == 2) {
return _Xx * _Xx;
}

return _CSTD powf(_Xx, static_cast<float>(_Yx));
}

_NODISCARD _Check_return_ inline float remainder(_In_ float _Xx, _In_ float _Yx) noexcept /* strengthened */ {
return _CSTD remainderf(_Xx, _Yx);
}
Expand Down Expand Up @@ -442,14 +426,6 @@ _NODISCARD _Check_return_ inline long double pow(_In_ long double _Xx, _In_ long
return _CSTD powl(_Xx, _Yx);
}

_NODISCARD _Check_return_ inline long double pow(_In_ long double _Xx, _In_ int _Yx) noexcept /* strengthened */ {
if (_Yx == 2) {
return _Xx * _Xx;
}

return _CSTD powl(_Xx, static_cast<long double>(_Yx));
}

_NODISCARD _Check_return_ inline long double remainder(_In_ long double _Xx, _In_ long double _Yx) noexcept
/* strengthened */ {
return _CSTD remainderl(_Xx, _Yx);
Expand Down Expand Up @@ -517,13 +493,6 @@ double frexp(_Ty _Value, _Out_ int* const _Exp) noexcept /* strengthened */ {
return _CSTD frexp(static_cast<double>(_Value), _Exp);
}

// FUNCTION TEMPLATE pow
template <class _Ty1, class _Ty2, _STD enable_if_t<_STD is_arithmetic_v<_Ty1> && _STD is_arithmetic_v<_Ty2>, int> = 0>
_NODISCARD _STD _Common_float_type_t<_Ty1, _Ty2> pow(const _Ty1 _Left, const _Ty2 _Right) noexcept /* strengthened */ {
using _Common = _STD _Common_float_type_t<_Ty1, _Ty2>;
return _CSTD pow(static_cast<_Common>(_Left), static_cast<_Common>(_Right));
}

// FUNCTION TEMPLATE fma
#if !_HAS_IF_CONSTEXPR
inline float _Fma(float _Left, float _Middle, float _Right) noexcept {
Expand Down Expand Up @@ -643,7 +612,7 @@ _GENERIC_MATH1(cbrt)
_GENERIC_MATH1(fabs)
_GENERIC_MATH2(hypot)
// 3-arg hypot() is hand-crafted
// pow() is hand-crafted
_GENERIC_MATH2(pow)
_GENERIC_MATH1(sqrt)
_GENERIC_MATH1(erf)
_GENERIC_MATH1(erfc)
Expand Down
1 change: 1 addition & 0 deletions tests/std/test.lst
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@ tests\GH_000457_system_error_message
tests\GH_000545_include_compare
tests\GH_000685_condition_variable_any
tests\GH_000690_overaligned_function
tests\GH_000890_pow_template
tests\LWG3018_shared_ptr_function
tests\P0024R2_parallel_algorithms_adjacent_difference
tests\P0024R2_parallel_algorithms_adjacent_find
Expand Down
4 changes: 4 additions & 0 deletions tests/std/tests/GH_000890_pow_template/env.lst
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
# Copyright (c) Microsoft Corporation.
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception

RUNALL_INCLUDE ..\usual_matrix.lst
58 changes: 58 additions & 0 deletions tests/std/tests/GH_000890_pow_template/test.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
// Copyright (c) Microsoft Corporation.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception

#include <cmath>
#include <type_traits>

#define STATIC_ASSERT(...) static_assert(__VA_ARGS__, #__VA_ARGS__)

int main() {} // COMPILE-ONLY

constexpr long double ld = 10.0l;
constexpr double d = 10.0;
constexpr float f = 10.0f;
constexpr long long ll = 2;
constexpr int i = 2;
constexpr short s = 2;

STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, d)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, f)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, ll)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, i)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ld, s)), long double>);

STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, d)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, f)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, ll)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, i)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(d, s)), double>);

STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, d)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, f)), float>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, ll)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, i)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(f, s)), double>);

STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, d)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, f)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, ll)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, i)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(ll, s)), double>);

STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, d)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, f)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, ll)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, i)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(i, s)), double>);

STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, ld)), long double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, d)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, f)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, ll)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, i)), double>);
STATIC_ASSERT(std::is_same_v<decltype(std::pow(s, s)), double>);
2 changes: 1 addition & 1 deletion tests/std/tests/VSO_0099869_pow_float_overflow/test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ class test_std_pow_against_crt {

void single(uint32_t baseCandidate) {
float input = reinterpret_as<float>(baseCandidate);
float powOut = std::pow(input, 2);
float powOut = static_cast<float>(pow(input, 2));
float powfOut = powf(input, 2.0f);
int powClass = fpclassify(powOut);
int powfClass = fpclassify(powfOut);
Expand Down