diff --git a/glm/common.hpp b/glm/common.hpp index 89722845..f8c21e87 100644 --- a/glm/common.hpp +++ b/glm/common.hpp @@ -30,7 +30,7 @@ namespace glm /// @see GLSL 4.20.8 specification, section 8.3 Common Functions /// @see qualifier template - GLM_FUNC_DECL genType abs(genType x); + GLM_FUNC_DECL GLM_CONSTEXPR_CXX11 genType abs(genType x); /// Returns x if x >= 0; otherwise, it returns -x. /// @@ -41,7 +41,7 @@ namespace glm /// @see GLSL abs man page /// @see GLSL 4.20.8 specification, section 8.3 Common Functions template - GLM_FUNC_DECL vec abs(vec const& x); + GLM_FUNC_DECL GLM_CONSTEXPR_CXX11 vec abs(vec const& x); /// Returns 1.0 if x > 0, 0.0 if x == 0, or -1.0 if x < 0. /// diff --git a/glm/detail/_vectorize.hpp b/glm/detail/_vectorize.hpp index 2e577a80..0165f574 100644 --- a/glm/detail/_vectorize.hpp +++ b/glm/detail/_vectorize.hpp @@ -17,7 +17,7 @@ namespace detail template struct functor1<1, R, T, Q> { - GLM_FUNC_QUALIFIER static vec<1, R, Q> call(R (*Func) (T x), vec<1, T, Q> const& v) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static vec<1, R, Q> call(R (*Func) (T x), vec<1, T, Q> const& v) { return vec<1, R, Q>(Func(v.x)); } @@ -26,7 +26,7 @@ namespace detail template struct functor1<2, R, T, Q> { - GLM_FUNC_QUALIFIER static vec<2, R, Q> call(R (*Func) (T x), vec<2, T, Q> const& v) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static vec<2, R, Q> call(R (*Func) (T x), vec<2, T, Q> const& v) { return vec<2, R, Q>(Func(v.x), Func(v.y)); } @@ -35,7 +35,7 @@ namespace detail template struct functor1<3, R, T, Q> { - GLM_FUNC_QUALIFIER static vec<3, R, Q> call(R (*Func) (T x), vec<3, T, Q> const& v) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static vec<3, R, Q> call(R (*Func) (T x), vec<3, T, Q> const& v) { return vec<3, R, Q>(Func(v.x), Func(v.y), Func(v.z)); } @@ -44,7 +44,7 @@ namespace detail template struct functor1<4, R, T, Q> { - GLM_FUNC_QUALIFIER static vec<4, R, Q> call(R (*Func) (T x), vec<4, T, Q> const& v) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static vec<4, R, Q> call(R (*Func) (T x), vec<4, T, Q> const& v) { return vec<4, R, Q>(Func(v.x), Func(v.y), Func(v.z), Func(v.w)); } diff --git a/glm/detail/compute_common.hpp b/glm/detail/compute_common.hpp new file mode 100644 index 00000000..4e3b3b81 --- /dev/null +++ b/glm/detail/compute_common.hpp @@ -0,0 +1,60 @@ +#pragma once + +#include "setup.hpp" +#include +#include + +namespace glm{ +namespace detail +{ + template + struct compute_abs + {}; + + template + struct compute_abs + { + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static genFIType call(genFIType x) + { + GLM_STATIC_ASSERT( + std::numeric_limits::is_iec559 || std::numeric_limits::is_signed || GLM_UNRESTRICTED_GENTYPE, + "'abs' only accept floating-point and integer scalar or vector inputs"); + + return x >= genFIType(0) ? x : -x; + // TODO, perf comp with: *(((int *) &x) + 1) &= 0x7fffffff; + } + }; + +#if GLM_COMPILER & GLM_COMPILER_CUDA + template<> + struct compute_abs + { + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static float call(float x) + { + return fabsf(x); + } + }; +#endif + + template + struct compute_abs + { + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static genFIType call(genFIType x) + { + GLM_STATIC_ASSERT( + (!std::numeric_limits::is_signed && std::numeric_limits::is_integer) || GLM_UNRESTRICTED_GENTYPE, + "'abs' only accept floating-point and integer scalar or vector inputs"); + return x; + } + }; + + template + struct compute_abs_vector + { + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static vec call(vec const& x) + { + return detail::functor1::call(abs, x); + } + }; +}//namespace detail +}//namespace glm diff --git a/glm/detail/compute_vector_relational.hpp b/glm/detail/compute_vector_relational.hpp index e5610ef1..4c0e21df 100644 --- a/glm/detail/compute_vector_relational.hpp +++ b/glm/detail/compute_vector_relational.hpp @@ -1,5 +1,6 @@ #pragma once +#include "compute_common.hpp" #include "setup.hpp" #include #include @@ -10,7 +11,7 @@ namespace detail template ::is_iec559> struct compute_equal { - GLM_FUNC_QUALIFIER static bool call(T a, T b) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static bool call(T a, T b) { return a == b; } @@ -19,9 +20,10 @@ namespace detail template struct compute_equal { - GLM_FUNC_QUALIFIER static bool call(T a, T b) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 static bool call(T a, T b) { - return std::memcmp(&a, &b, sizeof(T)) == 0; + return detail::compute_abs::is_signed>::call(b - a) <= static_cast(0); + //return std::memcmp(&a, &b, sizeof(T)) == 0; } }; }//namespace detail diff --git a/glm/detail/func_common.inl b/glm/detail/func_common.inl index 8b2d0b02..1c10069e 100644 --- a/glm/detail/func_common.inl +++ b/glm/detail/func_common.inl @@ -2,6 +2,7 @@ /// @file glm/detail/func_common.inl #include "../vector_relational.hpp" +#include "compute_common.hpp" #include "type_vec2.hpp" #include "type_vec3.hpp" #include "type_vec4.hpp" @@ -66,56 +67,6 @@ namespace glm namespace glm{ namespace detail { - template - struct compute_abs - {}; - - template - struct compute_abs - { - GLM_FUNC_QUALIFIER static genFIType call(genFIType x) - { - GLM_STATIC_ASSERT( - std::numeric_limits::is_iec559 || std::numeric_limits::is_signed || GLM_UNRESTRICTED_GENTYPE, - "'abs' only accept floating-point and integer scalar or vector inputs"); - - return x >= genFIType(0) ? x : -x; - // TODO, perf comp with: *(((int *) &x) + 1) &= 0x7fffffff; - } - }; - - #if GLM_COMPILER & GLM_COMPILER_CUDA - template<> - struct compute_abs - { - GLM_FUNC_QUALIFIER static float call(float x) - { - return fabsf(x); - } - }; - #endif - - template - struct compute_abs - { - GLM_FUNC_QUALIFIER static genFIType call(genFIType x) - { - GLM_STATIC_ASSERT( - (!std::numeric_limits::is_signed && std::numeric_limits::is_integer) || GLM_UNRESTRICTED_GENTYPE, - "'abs' only accept floating-point and integer scalar or vector inputs"); - return x; - } - }; - - template - struct compute_abs_vector - { - GLM_FUNC_QUALIFIER static vec call(vec const& x) - { - return detail::functor1::call(abs, x); - } - }; - template struct compute_mix_vector { @@ -306,13 +257,13 @@ namespace detail }//namespace detail template - GLM_FUNC_QUALIFIER genFIType abs(genFIType x) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 genFIType abs(genFIType x) { return detail::compute_abs::is_signed>::call(x); } template - GLM_FUNC_QUALIFIER vec abs(vec const& x) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 vec abs(vec const& x) { return detail::compute_abs_vector::value>::call(x); } diff --git a/glm/detail/type_vec3.hpp b/glm/detail/type_vec3.hpp index 60a59f28..40ce6507 100644 --- a/glm/detail/type_vec3.hpp +++ b/glm/detail/type_vec3.hpp @@ -409,7 +409,7 @@ namespace glm GLM_FUNC_DECL GLM_CONSTEXPR_CXX11 bool operator==(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2); template - GLM_FUNC_DECL bool operator!=(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2); + GLM_FUNC_DECL GLM_CONSTEXPR_CXX11 bool operator!=(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2); template GLM_FUNC_DECL vec<3, bool, Q> operator&&(vec<3, bool, Q> const& v1, vec<3, bool, Q> const& v2); diff --git a/glm/detail/type_vec3.inl b/glm/detail/type_vec3.inl index 3a06eca0..9db8302f 100644 --- a/glm/detail/type_vec3.inl +++ b/glm/detail/type_vec3.inl @@ -1023,17 +1023,14 @@ namespace glm template GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 bool operator==(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2) { - return v1.x == v2.x && v1.y == v2.y && v1.z == v2.z; -/* return detail::compute_equal::call(v1.x, v2.x) && detail::compute_equal::call(v1.y, v2.y) && detail::compute_equal::call(v1.z, v2.z); -*/ } template - GLM_FUNC_QUALIFIER bool operator!=(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2) + GLM_FUNC_QUALIFIER GLM_CONSTEXPR_CXX11 bool operator!=(vec<3, T, Q> const& v1, vec<3, T, Q> const& v2) { return !(v1 == v2); } diff --git a/glm/detail/type_vec4.hpp b/glm/detail/type_vec4.hpp index 4b73d565..bf244f8d 100644 --- a/glm/detail/type_vec4.hpp +++ b/glm/detail/type_vec4.hpp @@ -42,7 +42,7 @@ namespace glm union { - struct { T x, y, z, w;}; + struct { T x, y, z, w; }; struct { T r, g, b, a; }; struct { T s, t, p, q; }; diff --git a/test/core/core_func_common.cpp b/test/core/core_func_common.cpp index df8e7ed4..1822bae2 100644 --- a/test/core/core_func_common.cpp +++ b/test/core/core_func_common.cpp @@ -1289,10 +1289,19 @@ namespace ldexp_ } }//namespace ldexp_ +static int test_constexpr() +{ + static_assert(glm::abs(1.0f) > 0.0f, "GLM: Failed constexpr"); + static_assert(glm::abs(glm::vec3(1.0f)) != glm::vec3(0.0f), "GLM: Failed constexpr"); + + return 0; +} + int main() { int Error = 0; + Error += test_constexpr(); Error += sign::test(); Error += floor_::test(); Error += mod_::test();