From 842d697e35d93038708605202acfef12b5ae03bc Mon Sep 17 00:00:00 2001
From: Rye Mutt <rye@alchemyviewer.org>
Date: Tue, 10 Mar 2020 18:22:16 -0400
Subject: [PATCH] Fix up SIMD wrappers to be trivial types with a standard
 layout

---
 indra/llmath/llmatrix3a.h       |  8 ++++++--
 indra/llmath/llmatrix4a.h       |  3 +++
 indra/llmath/llquaternion2.h    |  4 +++-
 indra/llmath/llsimdtypes.h      | 25 ++++++-------------------
 indra/llmath/llvector4a.h       | 11 ++++++++---
 indra/llmath/llvector4a.inl     |  6 ------
 indra/llmath/llvector4logical.h |  4 +++-
 7 files changed, 29 insertions(+), 32 deletions(-)

diff --git a/indra/llmath/llmatrix3a.h b/indra/llmath/llmatrix3a.h
index 9916cfd2dab..4c2fd711007 100644
--- a/indra/llmath/llmatrix3a.h
+++ b/indra/llmath/llmatrix3a.h
@@ -56,7 +56,7 @@ class LLMatrix3a
 	//////////////////////////
 	
 	// Ctor
-	LLMatrix3a() {}
+	LLMatrix3a() = default;
 
 	// Ctor for setting by columns
 	inline LLMatrix3a( const LLVector4a& c0, const LLVector4a& c1, const LLVector4a& c2 );
@@ -114,15 +114,19 @@ class LLMatrix3a
 	LL_ALIGN_16(LLVector4a mColumns[3]);
 
 };
+static_assert(std::is_trivial<LLMatrix3a>::value, "LLMatrix3a must be a trivial type");
+static_assert(std::is_standard_layout<LLMatrix3a>::value, "LLMatrix3a must be a standard layout type");
 
 class LLRotation : public LLMatrix3a
 {
 public:
 	
-	LLRotation() {}
+	LLRotation() = default;
 	
 	// Returns true if this rotation is orthonormal with det ~= 1
 	inline bool isOkRotation() const;		
 };
+static_assert(std::is_trivial<LLRotation>::value, "LLRotation must be a trivial type");
+static_assert(std::is_standard_layout<LLRotation>::value, "LLRotation must be a standard layout type");
 
 #endif
diff --git a/indra/llmath/llmatrix4a.h b/indra/llmath/llmatrix4a.h
index 7ba347062f7..ee3ce332e7d 100644
--- a/indra/llmath/llmatrix4a.h
+++ b/indra/llmath/llmatrix4a.h
@@ -153,6 +153,9 @@ class LLMatrix4a
     }
 };
 
+static_assert(std::is_trivial<LLMatrix4a>::value, "LLMatrix4a must be a trivial type");
+static_assert(std::is_standard_layout<LLMatrix4a>::value, "LLMatrix4a must be a standard layout type");
+
 inline LLVector4a rowMul(const LLVector4a &row, const LLMatrix4a &mat)
 {
     LLVector4a result;
diff --git a/indra/llmath/llquaternion2.h b/indra/llmath/llquaternion2.h
index fd9c0cf3aba..6ced9f59614 100644
--- a/indra/llmath/llquaternion2.h
+++ b/indra/llmath/llquaternion2.h
@@ -49,7 +49,7 @@ class LLQuaternion2
 	//////////////////////////
 	
 	// Ctor
-	LLQuaternion2() {}
+	LLQuaternion2() = default;
 
 	// Ctor from LLQuaternion
 	explicit LLQuaternion2( const class LLQuaternion& quat );
@@ -101,5 +101,7 @@ class LLQuaternion2
 	LLVector4a mQ;
 
 };
+static_assert(std::is_trivial<LLQuaternion2>::value, "LLQuaternion2 must be a trivial type");
+static_assert(std::is_standard_layout<LLQuaternion2>::value, "LLQuaternion2 must be a standard layout type");
 
 #endif
diff --git a/indra/llmath/llsimdtypes.h b/indra/llmath/llsimdtypes.h
index bd991d0e71d..5290630ce58 100644
--- a/indra/llmath/llsimdtypes.h
+++ b/indra/llmath/llsimdtypes.h
@@ -34,23 +34,10 @@
 typedef __m128	LLQuad;
 
 
-#if LL_WINDOWS
-#pragma warning(push)
-#pragma warning( disable : 4800 3 ) // Disable warning about casting int to bool for this class.
-#if defined(_MSC_VER) && (_MSC_VER < 1500)
-// VC++ 2005 is missing these intrinsics
-// __forceinline is MSVC specific and attempts to override compiler inlining judgment. This is so
-// even in debug builds this call is a NOP.
-__forceinline const __m128 _mm_castsi128_ps( const __m128i a ) { return reinterpret_cast<const __m128&>(a); }
-__forceinline const __m128i _mm_castps_si128( const __m128 a ) { return reinterpret_cast<const __m128i&>(a); }
-#endif // _MSC_VER
-
-#endif // LL_WINDOWS
-
 class LLBool32
 {
 public:
-	inline LLBool32() {}
+	inline LLBool32() = default;
 	inline LLBool32(int rhs) : m_bool(rhs) {}
 	inline LLBool32(unsigned int rhs) : m_bool(rhs) {}
 	inline LLBool32(bool rhs) { m_bool = static_cast<const int>(rhs); }
@@ -63,14 +50,10 @@ class LLBool32
 	int m_bool;
 };
 
-#if LL_WINDOWS
-#pragma warning(pop)
-#endif
-
 class LLSimdScalar
 {
 public:
-	inline LLSimdScalar() {}
+	inline LLSimdScalar() = default;
 	inline LLSimdScalar(LLQuad q) 
 	{ 
 		mQ = q; 
@@ -120,5 +103,9 @@ class LLSimdScalar
 private:
 	LLQuad mQ;
 };
+static_assert(std::is_trivial<LLBool32>::value, "LLBool32 must be a trivial type");
+static_assert(std::is_standard_layout<LLBool32>::value, "LLBool32 must be a standard layout type");
+static_assert(std::is_trivial<LLSimdScalar>::value, "LLSimdScalar must be a trivial type");
+static_assert(std::is_standard_layout<LLSimdScalar>::value, "LLSimdScalar must be a standard layout type");
 
 #endif //LL_SIMD_TYPES_H
diff --git a/indra/llmath/llvector4a.h b/indra/llmath/llvector4a.h
index 222f3cf2351..57c415cbda5 100644
--- a/indra/llmath/llvector4a.h
+++ b/indra/llmath/llvector4a.h
@@ -92,10 +92,14 @@ class LLVector4a
 	// CONSTRUCTORS 
 	////////////////////////////////////
 	
+#if SHOW_ASSERT
 	LLVector4a()
 	{ //DO NOT INITIALIZE -- The overhead is completely unnecessary
 		ll_assert_aligned(this,16);
 	}
+#else
+	LLVector4a() = default;
+#endif
 	
 	LLVector4a(F32 x, F32 y, F32 z, F32 w = 0.f)
 	{
@@ -240,7 +244,7 @@ class LLVector4a
 	// Normalize this vector with respect to the x, y, and z components only. Accurate only to 10-12 bits of precision. W component is destroyed
 	// Same as above except substitutes default vector contents if the vector is non-finite or degenerate due to zero length.
 	//
-	inline void normalize3fast_checked(LLVector4a* d = 0);
+	inline void normalize3fast_checked(LLVector4a* d = nullptr);
 
 	// Return true if this vector is normalized with respect to x,y,z up to tolerance
 	inline LLBool32 isNormalized3( F32 tolerance = 1e-3 ) const;
@@ -315,8 +319,6 @@ class LLVector4a
 	////////////////////////////////////	
 	
 	// Do NOT add aditional operators without consulting someone with SSE experience
-	inline const LLVector4a& operator= ( const LLVector4a& rhs );
-	
 	inline const LLVector4a& operator= ( const LLQuad& rhs );
 
 	inline operator LLQuad() const;	
@@ -325,6 +327,9 @@ class LLVector4a
 	LLQuad mQ;
 } LL_ALIGN_POSTFIX(16);
 
+static_assert(std::is_trivial<LLVector4a>::value, "LLVector4a must be a trivial type");
+static_assert(std::is_standard_layout<LLVector4a>::value, "LLVector4a must be a standard layout type");
+
 inline void update_min_max(LLVector4a& min, LLVector4a& max, const LLVector4a& p)
 {
 	min.setMin(min, p);
diff --git a/indra/llmath/llvector4a.inl b/indra/llmath/llvector4a.inl
index 69d3d01efe4..fe416d97532 100644
--- a/indra/llmath/llvector4a.inl
+++ b/indra/llmath/llvector4a.inl
@@ -593,12 +593,6 @@ inline bool LLVector4a::equals3(const LLVector4a& rhs, F32 tolerance ) const
 ////////////////////////////////////	
 
 // Do NOT add aditional operators without consulting someone with SSE experience
-inline const LLVector4a& LLVector4a::operator= ( const LLVector4a& rhs )
-{
-	mQ = rhs.mQ;
-	return *this;
-}
-
 inline const LLVector4a& LLVector4a::operator= ( const LLQuad& rhs )
 {
 	mQ = rhs;
diff --git a/indra/llmath/llvector4logical.h b/indra/llmath/llvector4logical.h
index c5698f7cea6..d4214450c0e 100644
--- a/indra/llmath/llvector4logical.h
+++ b/indra/llmath/llvector4logical.h
@@ -61,7 +61,7 @@ class LLVector4Logical
 	};
 	
 	// Empty default ctor
-	LLVector4Logical() {}
+	LLVector4Logical() = default;
 	
 	LLVector4Logical( const LLQuad& quad )
 	{
@@ -122,5 +122,7 @@ class LLVector4Logical
 	
 	LLQuad mQ;
 };
+static_assert(std::is_trivial<LLVector4Logical>::value, "LLVector4Logical must be a trivial type");
+static_assert(std::is_standard_layout<LLVector4Logical>::value, "LLVector4Logical must be a standard layout type");
 
 #endif //LL_VECTOR4ALOGICAL_H
-- 
GitLab