Implement Concatenate() and Insert() for Int2.

Change-Id: I2f5bbf0cab904a9500a6219bd6a218cb877611fa
Reviewed-on: https://swiftshader-review.googlesource.com/3142
Reviewed-by: Alexis Hétu <sugoi@google.com>
Reviewed-by: Nicolas Capens <capn@google.com>
Tested-by: Nicolas Capens <capn@google.com>
diff --git a/src/Reactor/Nucleus.cpp b/src/Reactor/Nucleus.cpp
index 49ec859..ee082e6 100644
--- a/src/Reactor/Nucleus.cpp
+++ b/src/Reactor/Nucleus.cpp
@@ -4824,6 +4824,17 @@
 		}
 	}
 
+	RValue<Int2> Concatenate(RValue<Int> lo, RValue<Int> hi)
+	{
+		Constant *shuffle[2];
+		shuffle[0] = Nucleus::createConstantInt(0);
+		shuffle[1] = Nucleus::createConstantInt(1);
+
+		Value *packed = Nucleus::createShuffleVector(Nucleus::createBitCast(lo.value, VectorType::get(Int::getType(), 1)), Nucleus::createBitCast(hi.value, VectorType::get(Int::getType(), 1)), Nucleus::createConstantVector(shuffle, 2));
+
+		return RValue<Int2>(Nucleus::createBitCast(packed, Int2::getType()));
+	}
+
 	RValue<Int> Extract(RValue<Int2> val, int i)
 	{
 		if(false)   // FIXME: LLVM does not generate optimal code
@@ -4845,11 +4856,10 @@
 		}
 	}
 
-	// FIXME: Crashes LLVM
-//	RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i)
-//	{
-//		return RValue<Int2>(Nucleus::createInsertElement(val.value, element.value, Nucleus::createConstantInt(i)));
-//	}
+	RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i)
+	{
+		return RValue<Int2>(Nucleus::createBitCast(Nucleus::createInsertElement(Nucleus::createBitCast(val.value, VectorType::get(Int::getType(), 2)), element.value, i), Int2::getType()));
+	}
 
 	Type *Int2::getType()
 	{
diff --git a/src/Reactor/Nucleus.hpp b/src/Reactor/Nucleus.hpp
index 59d43e0..6f39e68 100644
--- a/src/Reactor/Nucleus.hpp
+++ b/src/Reactor/Nucleus.hpp
@@ -1555,8 +1555,9 @@
 //	RValue<Int2> RoundInt(RValue<Float4> cast);

 	RValue<Long1> UnpackLow(RValue<Int2> x, RValue<Int2> y);

 	RValue<Long1> UnpackHigh(RValue<Int2> x, RValue<Int2> y);

+	RValue<Int2> Concatenate(RValue<Int> lo, RValue<Int> hi);

 	RValue<Int> Extract(RValue<Int2> val, int i);

-//	RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i);

+	RValue<Int2> Insert(RValue<Int2> val, RValue<Int> element, int i);

 

 	class UInt2 : public Variable<UInt2>

 	{