⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 x87denormalsquasher.h

📁 这是整套横扫千军3D版游戏的源码
💻 H
📖 第 1 页 / 共 2 页
字号:
/*
    streflop: STandalone REproducible FLOating-Point
    Nicolas Brodu, 2006
    Code released according to the GNU Lesser General Public License

    Heavily relies on GNU Libm, itself depending on netlib fplibm, GNU MP, and IBM MP lib.
    Uses SoftFloat too.

    Please read the history and copyright information in the documentation provided with the source code
*/

#ifndef X87DenormalSquasher_H
#define X87DenormalSquasher_H

/// This file should be included from within a streflop namespace

template<typename ValueType> inline void X87DenormalSquashFunction(ValueType& value) {
    struct X {};
    X Unknown_numeric_type;
    // unknown types do not compile
    value = Unknown_numeric_type;
}

// Use cmov instruction to avoid branching?
// Pro: branching may be costly, though the branching predictor may compensate when there are few denormals
// Con: cmov forces an unconditional writeback to the mem just after read, which may be worse than the branch

template<> inline void X87DenormalSquashFunction<float>(float& value) {
    if ((reinterpret_cast<int*>(&value)[0] & 0x7F800000) == 0) value = 0.0f;
}

template<> inline void X87DenormalSquashFunction<double>(double& value) {
    if ((reinterpret_cast<int*>(&value)[1] & 0x7FF00000) == 0) value = 0.0;
}

template<> inline void X87DenormalSquashFunction<long double>(long double& value) {
    if ((reinterpret_cast<short*>(&value)[4] & 0x7FFF) == 0) value = 0.0L;
}

/// Wrapper class for the denormal squashing of X87
/// The goal is to be able to use this file for normal arithmetic operations
/// as if this was a native float or double, thanks to C++ operator overloading.
/// In particular, the GNU libm may be compiled this way, though no effort was made
/// to optimize out the denormal parts (and squashing denormals is non-IEEE compliant anyway)

template<typename ValueType> struct X87DenormalSquasher {

// Define value
    ValueType value;

    /// Uninitialized object
    inline X87DenormalSquasher() {}

    /// Copy and conversion from other precisions
    inline X87DenormalSquasher(const X87DenormalSquasher<float>& f) : value(f.value) {X87DenormalSquashFunction<ValueType>(value);}
    inline X87DenormalSquasher(const X87DenormalSquasher<double>& f) : value(f.value) {X87DenormalSquashFunction<ValueType>(value);}
    inline X87DenormalSquasher(const X87DenormalSquasher<long double>& f) : value(f.value) {X87DenormalSquashFunction<ValueType>(value);}
    inline X87DenormalSquasher& operator=(const X87DenormalSquasher<float>& f) {value = f.value; X87DenormalSquashFunction<ValueType>(value); return *this;} // self-ref OK
    inline X87DenormalSquasher& operator=(const X87DenormalSquasher<double>& f) {value = f.value; X87DenormalSquashFunction<ValueType>(value); return *this;} // self-ref OK
    inline X87DenormalSquasher& operator=(const X87DenormalSquasher<long double>& f) {value = f.value; X87DenormalSquashFunction<ValueType>(value); return *this;} // self-ref OK

    /// Destructor
    inline ~X87DenormalSquasher() {}

    /// Now the real fun, arithmetic operator overloading
    inline X87DenormalSquasher& operator+=(const X87DenormalSquasher& f) {value += f.value; X87DenormalSquashFunction<ValueType>(value); return *this;}
    inline X87DenormalSquasher& operator-=(const X87DenormalSquasher& f) {value -= f.value; X87DenormalSquashFunction<ValueType>(value); return *this;}
    inline X87DenormalSquasher& operator*=(const X87DenormalSquasher& f) {value *= f.value; X87DenormalSquashFunction<ValueType>(value); return *this;}
    inline X87DenormalSquasher& operator/=(const X87DenormalSquasher& f) {value /= f.value; X87DenormalSquashFunction<ValueType>(value); return *this;}
    inline bool operator==(const X87DenormalSquasher& f) const {return value == f.value;}
    inline bool operator!=(const X87DenormalSquasher& f) const {return value != f.value;}
    inline bool operator<(const X87DenormalSquasher& f) const {return value < f.value;}
    inline bool operator<=(const X87DenormalSquasher& f) const {return value <= f.value;}
    inline bool operator>(const X87DenormalSquasher& f) const {return value > f.value;}
    inline bool operator>=(const X87DenormalSquasher& f) const {return value >= f.value;}

#define STREFLOP_X87DENORMAL_NATIVE_FLOAT_OPS(native_type) \
    inline X87DenormalSquasher(const native_type f) {value = f; X87DenormalSquashFunction<ValueType>(value);} \
    inline X87DenormalSquasher& operator=(const native_type f) {value = f; X87DenormalSquashFunction<ValueType>(value); return *this;} \
    inline operator native_type() const {return static_cast<native_type>(value);} \
    inline X87DenormalSquasher& operator+=(const native_type f) {return operator+=(X87DenormalSquasher(f));} \
    inline X87DenormalSquasher& operator-=(const native_type f) {return operator-=(X87DenormalSquasher(f));} \
    inline X87DenormalSquasher& operator*=(const native_type f) {return operator*=(X87DenormalSquasher(f));} \
    inline X87DenormalSquasher& operator/=(const native_type f) {return operator/=(X87DenormalSquasher(f));} \
    inline bool operator==(const native_type f) const {return operator==(X87DenormalSquasher(f));} \
    inline bool operator!=(const native_type f) const {return operator!=(X87DenormalSquasher(f));} \
    inline bool operator<(const native_type f) const {return operator<(X87DenormalSquasher(f));} \
    inline bool operator<=(const native_type f) const {return operator<=(X87DenormalSquasher(f));} \
    inline bool operator>(const native_type f) const {return operator>(X87DenormalSquasher(f));} \
    inline bool operator>=(const native_type f) const {return operator>=(X87DenormalSquasher(f));}

#define STREFLOP_X87DENORMAL_NATIVE_INT_OPS(native_type) \
    inline X87DenormalSquasher(const native_type x) {value = x;} \
    inline X87DenormalSquasher& operator=(const native_type x) {value = x; return *this;} \
    inline operator native_type() const {return static_cast<native_type>(value);} \
    inline X87DenormalSquasher& operator+=(const native_type f) {value += f; X87DenormalSquashFunction<ValueType>(value); return *this;} \
    inline X87DenormalSquasher& operator-=(const native_type f) {value -= f; X87DenormalSquashFunction<ValueType>(value); return *this;} \
    inline X87DenormalSquasher& operator*=(const native_type f) {value *= f; X87DenormalSquashFunction<ValueType>(value); return *this;} \
    inline X87DenormalSquasher& operator/=(const native_type f) {value /= f; X87DenormalSquashFunction<ValueType>(value); return *this;} \

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -