From eae442ce66199d923642237b9106ce678103c42f Mon Sep 17 00:00:00 2001 From: "HuYingzhuo(hugo/hyzboy)" Date: Thu, 9 Feb 2023 14:27:53 +0800 Subject: [PATCH] added SplitFloat32/64, Float32toFloat16, MergeFloat32,MergeFloat64 --- inc/hgl/color/ColorFormat.h | 37 ++++------ inc/hgl/math/HalfFloat.h | 93 +++++++++++++++++++++++- inc/hgl/platform/compiler/DataTypeGNU.h | 3 +- inc/hgl/platform/compiler/DataTypeTiny.h | 1 + inc/hgl/platform/compiler/DataTypeWin.h | 4 +- 5 files changed, 112 insertions(+), 26 deletions(-) diff --git a/inc/hgl/color/ColorFormat.h b/inc/hgl/color/ColorFormat.h index 3e72f7d..18051d5 100644 --- a/inc/hgl/color/ColorFormat.h +++ b/inc/hgl/color/ColorFormat.h @@ -25,33 +25,26 @@ namespace hgl } } - constexpr uint16 RGBA8toA1RGB5(const uint8 r,const uint8 g,const uint8 b,const uint8 a) - { - return ((a>>7)<<15) - |((r<<7)&0x7C00) - |((g<<2)&0x3E0) - | (b>>3); - } - - inline void RGBA8toA1RGB5(uint16 *target,uint8 *src,uint size) - { - for(uint i=0;i>7)<<15) - |((src[0]<<7)&0x7C00) - |((src[1]<<2)&0x3E0) - | (src[2]>>3); - - ++target; - src+=4; - } - } - // Bit depth Sign bit present Exponent bits Mantissa bits // 32 Yes 8 23 // 16 Yes 5 10 // 11 No 5 6 // 10 No 5 5 + + inline void RGB32FtoB10GR11UF(uint32 *target,const float *source,uint size) + { + const uint32 *src=(uint32 *)source; + + for(uint i=0;i>4; + + ++target; + source+=3; + } + } constexpr uint32 RGB16FtoB10GR11UF(const half_float r, const half_float g, const half_float b) { diff --git a/inc/hgl/math/HalfFloat.h b/inc/hgl/math/HalfFloat.h index cd54fdb..50bd898 100644 --- a/inc/hgl/math/HalfFloat.h +++ b/inc/hgl/math/HalfFloat.h @@ -1,12 +1,101 @@ -#ifndef HGL_HALF_FLOAT_INCLUDE +#ifndef HGL_HALF_FLOAT_INCLUDE #define HGL_HALF_FLOAT_INCLUDE #include namespace hgl { - using half_float=uint16; + // Bit depth Sign bit present Exponent bits Mantissa bits + // 32 Yes 8 23 + // 16 Yes 5 10 + // 11 No 5 6 + // 10 No 5 5 + inline void SplitFloat32(bool &sign_bit,uint &exponent,uint &mantissa,const float value) + { + uint32 *p=(uint32 *)&value; + + sign_bit=(*p&0x80000000)!=0; + exponent=(*p&0x7F800000)>>23; + mantissa=(*p&0x007FFFFF); + } + + inline void SplitFloat64(bool &sign_bit,uint &exponent,uint64 &mantissa,const double value) + { + uint64 *p=(uint64 *)&value; + + sign_bit=(*p&0x8000000000000000)!=0; + exponent=(*p&0x7FF0000000000000)>>52; + mantissa=(*p&0x000FFFFFFFFFFFFF); + } + + constexpr float MergeFloat(const bool sign_bit,const uint exponent,const uint mantissa) + { + return float((sign_bit?0x80000000:0)|(exponent<<23)|mantissa); + } + + constexpr double MergeFloat64(const bool sign_bit,const uint exponent,const uint64 mantissa) + { + return double((sign_bit?0x8000000000000000:0)|(uint64(exponent)<<52)|mantissa); + } + + /** + * 标准版float32转float16处理 + */ + void Float32toFloat16(half_float *output,const float *input,const uint count) + { + const uint32 *src=(const uint32 *)input; + uint16 *dst=output; + + for(uint i=0;i>23; + uint32 mantissa=value&0x007FFFFF; + + if(exponent==0xFF) + { + if(mantissa==0) + dst[i]=sign_bit>>16; + else + dst[i]=0x7FFF; + } + else + { + if(exponent==0) + { + if(mantissa==0) + dst[i]=sign_bit>>16; + else + { + uint32 mantissa_bit=0x00800000; + + while((mantissa&mantissa_bit)==0) + { + mantissa_bit>>=1; + --exponent; + } + + exponent+=1; + mantissa&=~mantissa_bit; + } + } + else + { + exponent+=15-127; + mantissa>>=13; + } + + dst[i]=sign_bit>>16|exponent<<10|mantissa; + } + } + } + + /** + * 快速版float32转float16处理 + */ inline const half_float float2half(const float &f) { const uint32 x = *((uint32 *)&f); diff --git a/inc/hgl/platform/compiler/DataTypeGNU.h b/inc/hgl/platform/compiler/DataTypeGNU.h index 7d590bd..794c257 100644 --- a/inc/hgl/platform/compiler/DataTypeGNU.h +++ b/inc/hgl/platform/compiler/DataTypeGNU.h @@ -14,7 +14,8 @@ namespace hgl using int64 = signed long long; ///<有符号64位整型 using uint64 =unsigned long long; ///<无符号64位整型 - + + using half_float=uint16; using float32 =float; using float64 =double; diff --git a/inc/hgl/platform/compiler/DataTypeTiny.h b/inc/hgl/platform/compiler/DataTypeTiny.h index 2af4d18..8fe889e 100644 --- a/inc/hgl/platform/compiler/DataTypeTiny.h +++ b/inc/hgl/platform/compiler/DataTypeTiny.h @@ -13,6 +13,7 @@ namespace hgl using u32=uint32; using u64=uint64; + using f16=half_float; using f32=float; using f64=double; diff --git a/inc/hgl/platform/compiler/DataTypeWin.h b/inc/hgl/platform/compiler/DataTypeWin.h index 260cc84..a2d0455 100644 --- a/inc/hgl/platform/compiler/DataTypeWin.h +++ b/inc/hgl/platform/compiler/DataTypeWin.h @@ -1,5 +1,6 @@ #ifndef HGL_DATATYPE_WINDOWS_INCLUDE #define HGL_DATATYPE_WINDOWS_INCLUDE + namespace hgl { using int8 = signed __int8 ; ///<有符号 8位整型 @@ -10,7 +11,8 @@ namespace hgl using uint32 =unsigned __int32; ///<无符号32位整型 using int64 = signed __int64; ///<有符号64位整型 using uint64 =unsigned __int64; ///<无符号64位整型 - + + using half_float=uint16; using float32 =float; using float64 =double;