1 /** @addtogroup constants
2  *  @{
3  */
4 /*
5   Copyright (C) 2016 D Levin (https://www.kfrlib.com)
6   This file is part of KFR
7 
8   KFR is free software: you can redistribute it and/or modify
9   it under the terms of the GNU General Public License as published by
10   the Free Software Foundation, either version 2 of the License, or
11   (at your option) any later version.
12 
13   KFR is distributed in the hope that it will be useful,
14   but WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16   GNU General Public License for more details.
17 
18   You should have received a copy of the GNU General Public License
19   along with KFR.
20 
21   If GPL is not suitable for your project, you must purchase a commercial license to use KFR.
22   Buying a commercial license is mandatory as soon as you develop commercial activities without
23   disclosing the source code of your own applications.
24   See https://www.kfrlib.com for details.
25  */
26 #pragma once
27 
28 #include "types.hpp"
29 #include <limits>
30 
31 CMT_PRAGMA_MSVC(warning(push))
32 CMT_PRAGMA_MSVC(warning(disable : 4309))
33 CMT_PRAGMA_MSVC(warning(disable : 4146))
34 
35 namespace kfr
36 {
37 
38 #if CMT_COMPILER_GNU
39 constexpr double infinity = __builtin_inf();
40 constexpr double qnan     = __builtin_nan("");
41 #else
42 constexpr double infinity = HUGE_VAL;
43 constexpr double qnan     = NAN;
44 #endif
45 CMT_PRAGMA_GNU(GCC diagnostic push)
46 CMT_PRAGMA_GNU(GCC diagnostic ignored "-Woverflow")
47 
48 template <typename T>
49 struct scalar_constants
50 {
pi_skfr::scalar_constants51     constexpr static T pi_s(int m, int d = 1) { return pi * m / d; }
recip_pi_skfr::scalar_constants52     constexpr static T recip_pi_s(int m, int d = 1) { return recip_pi * m / d; }
53 
54     constexpr static T pi           = static_cast<T>(3.1415926535897932384626433832795);
55     constexpr static T sqr_pi       = static_cast<T>(9.8696044010893586188344909998762);
56     constexpr static T recip_pi     = static_cast<T>(0.31830988618379067153776752674503);
57     constexpr static T degtorad     = static_cast<T>(pi / 180);
58     constexpr static T radtodeg     = static_cast<T>(pi * 180);
59     constexpr static T e            = static_cast<T>(2.718281828459045235360287471352662);
60     constexpr static T recip_log_2  = static_cast<T>(1.442695040888963407359924681001892137426645954);
61     constexpr static T recip_log_10 = static_cast<T>(0.43429448190325182765112891891661);
62     constexpr static T log_2        = static_cast<T>(0.69314718055994530941723212145818);
63     constexpr static T log_10       = static_cast<T>(2.3025850929940456840179914546844);
64     constexpr static T sqrt_2       = static_cast<T>(1.4142135623730950488016887242097);
65 
66     constexpr static T fold_constant_div = choose_const<T>(
67         CMT_FP(0x1.921fb6p-1f, 7.8539818525e-01f), CMT_FP(0x1.921fb54442d18p-1, 7.853981633974482790e-01));
68 
69     constexpr static T fold_constant_hi = choose_const<T>(
70         CMT_FP(0x1.922000p-1f, 7.8540039062e-01f), CMT_FP(0x1.921fb40000000p-1, 7.853981256484985352e-01));
71     constexpr static T fold_constant_rem1 =
72         choose_const<T>(CMT_FP(-0x1.2ae000p-19f, -2.2267922759e-06f),
73                         CMT_FP(0x1.4442d00000000p-25, 3.774894707930798177e-08));
74     constexpr static T fold_constant_rem2 =
75         choose_const<T>(CMT_FP(-0x1.de973ep-32f, -4.3527578764e-10f),
76                         CMT_FP(0x1.8469898cc5170p-49, 2.695151429079059484e-15));
77 
78     constexpr static T epsilon     = std::numeric_limits<T>::epsilon();
79     constexpr static T infinity    = std::numeric_limits<T>::infinity();
80     constexpr static T neginfinity = -std::numeric_limits<T>::infinity();
81     constexpr static T qnan        = std::numeric_limits<T>::quiet_NaN();
82 };
83 
84 template <typename T>
85 struct constants : public scalar_constants<subtype<T>>
86 {
87 public:
88     using Tsub = subtype<T>;
89 };
90 
91 template <size_t Value>
92 constexpr inline size_t force_compiletime_size_t = Value;
93 
94 CMT_PRAGMA_GNU(GCC diagnostic pop)
95 
96 /// π (pi)
97 /// c_pi<f64, 4>      = 4pi
98 /// c_pi<f64, 3, 4>   = 3/4pi
99 template <typename T, int m = 1, int d = 1>
100 constexpr inline subtype<T> c_pi = subtype<T>(3.1415926535897932384626433832795 * m / d);
101 
102 /// π² (pi²)
103 /// c_sqr_pi<f64, 4>      = 4pi²
104 /// c_sqr_pi<f64, 3, 4>   = 3/4pi²
105 template <typename T, int m = 1, int d = 1>
106 constexpr inline subtype<T> c_sqr_pi = subtype<T>(9.8696044010893586188344909998762 * m / d);
107 
108 /// 1/π (1/pi)
109 /// c_recip_pi<f64>       1/pi
110 /// c_recip_pi<f64, 4>    4/pi
111 template <typename T, int m = 1, int d = 1>
112 constexpr inline subtype<T> c_recip_pi = subtype<T>(0.31830988618379067153776752674503 * m / d);
113 
114 /// degree to radian conversion factor
115 template <typename T>
116 constexpr inline subtype<T> c_degtorad = c_pi<T, 1, 180>;
117 
118 /// radian to degree conversion factor
119 template <typename T>
120 constexpr inline subtype<T> c_radtodeg = c_recip_pi<T, 180>;
121 
122 /// e, Euler's number
123 template <typename T, int m = 1, int d = 1>
124 constexpr inline subtype<T> c_e = subtype<T>(2.718281828459045235360287471352662 * m / d);
125 
126 template <typename T>
127 constexpr inline unsigned c_mantissa_bits = sizeof(subtype<T>) == 32 ? 23 : 52;
128 
129 template <typename T>
130 constexpr inline subtype<T> c_mantissa_mask = (subtype<T>(1) << c_mantissa_bits<T>)-1;
131 
132 template <typename T>
133 constexpr inline subtype<T> c_epsilon = (std::numeric_limits<subtype<T>>::epsilon());
134 
135 /// infinity
136 template <typename T>
137 constexpr inline subtype<T> c_infinity = std::numeric_limits<subtype<T>>::infinity();
138 
139 /// -infinity
140 template <typename T>
141 constexpr inline subtype<T> c_neginfinity = -std::numeric_limits<subtype<T>>::infinity();
142 
143 /// Quiet NaN
144 template <typename T>
145 constexpr inline subtype<T> c_qnan = std::numeric_limits<subtype<T>>::quiet_NaN();
146 
147 template <typename T>
148 constexpr inline subtype<T> c_recip_log_2 = subtype<T>(1.442695040888963407359924681001892137426645954);
149 
150 template <typename T>
151 constexpr inline subtype<T> c_recip_log_10 = subtype<T>(0.43429448190325182765112891891661);
152 
153 template <typename T>
154 constexpr inline subtype<T> c_log_2 = subtype<T>(0.69314718055994530941723212145818);
155 
156 template <typename T>
157 constexpr inline subtype<T> c_log_10 = subtype<T>(2.3025850929940456840179914546844);
158 
159 template <typename T, int m = 1, int d = 1>
160 constexpr inline subtype<T> c_sqrt_2 = subtype<T>(1.4142135623730950488016887242097 * m / d);
161 } // namespace kfr
162 
163 CMT_PRAGMA_MSVC(warning(pop))
164