diff --git a/src/common/QskAspect.h b/src/common/QskAspect.h index 87164eee..94b45452 100644 --- a/src/common/QskAspect.h +++ b/src/common/QskAspect.h @@ -179,19 +179,26 @@ namespace QskAspect constexpr Aspect( uint subControl, uint type, bool isAnimator, uint primitive, uint placement, uint states ); - uint m_subControl : 12; + union + { + struct + { + uint m_subControl : 12; - uint m_type : 3; - bool m_isAnimator : 1; + uint m_type : 3; + bool m_isAnimator : 1; - uint m_primitive : 7; - uint m_placement : 1; - uint m_reserved1 : 8; + uint m_primitive : 7; + uint m_placement : 1; + uint m_reserved1 : 8; - uint m_states : 16; - uint m_reserved2 : 16; + uint m_states : 16; + uint m_reserved2 : 16; + }; - } Q_PACKED; + quint64 m_value; + }; + }; inline constexpr Aspect::Aspect(): Aspect( Control, Flag, Preserved ) @@ -233,17 +240,17 @@ namespace QskAspect inline bool Aspect::operator==( const Aspect& other ) const { - return value() == other.value(); + return m_value == other.m_value; } inline bool Aspect::operator!=( const Aspect& other ) const { - return value() != other.value(); + return m_value != other.m_value; } inline bool Aspect::operator<( const Aspect& other ) const { - return value() < other.value(); + return m_value < other.m_value; } inline constexpr Aspect Aspect::operator|( Subcontrol subControl ) const @@ -288,7 +295,7 @@ namespace QskAspect inline constexpr quint64 Aspect::value() const { - return *( const quint64* ) this; + return m_value; } inline bool Aspect::isAnimator() const @@ -426,7 +433,7 @@ namespace QskAspect return Aspect( subControl ) | state; } - inline constexpr Aspect operator|( Type type, Placement placement ) + inline constexpr Aspect operator|( Type type, Placement placement ) { return Aspect( type ) | placement; } diff --git a/src/controls/QskControl.cpp b/src/controls/QskControl.cpp index d5e7ca5a..ce106c95 100644 --- a/src/controls/QskControl.cpp +++ b/src/controls/QskControl.cpp @@ -561,9 +561,12 @@ void QskControl::updateControlFlags( Flags flags ) if ( oldFlags != newFlags ) { - for ( uint i = 0; i <= LastFlag; ++i ) + const auto numBits = qCountTrailingZeroBits( + static_cast< quint32 >( LastFlag ) ); + + for ( quint32 i = 0; i <= numBits; ++i ) { - const uint flag = ( 1 << i ); + const quint32 flag = ( 1 << i ); updateControlFlag( flag, flags & flag ); } diff --git a/src/controls/QskVariantAnimator.cpp b/src/controls/QskVariantAnimator.cpp index 3edfd680..934fd3ec 100644 --- a/src/controls/QskVariantAnimator.cpp +++ b/src/controls/QskVariantAnimator.cpp @@ -33,9 +33,22 @@ static void qskRegisterInterpolator() Q_CONSTRUCTOR_FUNCTION( qskRegisterInterpolator ) #endif -static inline QVariant qskInterpolate( void( *interpolator )(), - const QVariant& from, const QVariant& to, qreal progress ) +#if defined(Q_CC_CLANG) +#if __has_feature(address_sanitizer) +#define QSK_DECL_INSANE __attribute__ ( ( no_sanitize ("undefined") ) ) +#endif +#endif + +QSK_DECL_INSANE static inline QVariant qskInterpolate ( + void( *interpolator )(), const QVariant& from, const QVariant& to, qreal progress ) { +#if 1 + /* + how to get rid of the reported runtime error from the clang sanitizer, + when calling F( const T&, ... ) as G( const void* ... ); TODO ... + */ +#endif + auto f = reinterpret_cast< QVariantAnimation::Interpolator >( interpolator ); return f( from.constData(), to.constData(), progress ); }