Emulate sub-vector load/store intrinsics.
Bug b/37496321
Change-Id: I173b458a0d1d477ad75deaa33508ae1766c182c0
Reviewed-on: https://swiftshader-review.googlesource.com/9491
Tested-by: Nicolas Capens <nicolascapens@google.com>
Reviewed-by: Alexis Hétu <sugoi@google.com>
Reviewed-by: Nicolas Capens <nicolascapens@google.com>
diff --git a/src/Reactor/SubzeroReactor.cpp b/src/Reactor/SubzeroReactor.cpp
index 6fbd7a5..1a0ac08 100644
--- a/src/Reactor/SubzeroReactor.cpp
+++ b/src/Reactor/SubzeroReactor.cpp
@@ -849,12 +849,43 @@
if(valueType & EmulatedBits)
{
- const Ice::Intrinsics::IntrinsicInfo intrinsic = {Ice::Intrinsics::LoadSubVector, Ice::Intrinsics::SideEffects_F, Ice::Intrinsics::ReturnsTwice_F, Ice::Intrinsics::MemoryWrite_F};
- auto target = ::context->getConstantUndef(Ice::IceType_i32);
- auto load = Ice::InstIntrinsicCall::create(::function, 2, result, target, intrinsic);
- load->addArg(ptr);
- load->addArg(::context->getConstantInt32(typeSize(type)));
- ::basicBlock->appendInst(load);
+ if(emulateIntrinsics)
+ {
+ if(typeSize(type) == 4)
+ {
+ auto pointer = RValue<Pointer<Byte>>(ptr);
+ Int x = *Pointer<Int>(pointer +1-1);
+
+ Int4 vector;
+ vector = Insert(vector, x, 0);
+
+ auto bitcast = Ice::InstCast::create(::function, Ice::InstCast::Bitcast, result, vector.loadValue());
+ ::basicBlock->appendInst(bitcast);
+ }
+ else if(typeSize(type) == 8)
+ {
+ auto pointer = RValue<Pointer<Byte>>(ptr);
+ Int x = *Pointer<Int>(pointer +1-1);
+ Int y = *Pointer<Int>(pointer + 4);
+
+ Int4 vector;
+ vector = Insert(vector, x, 0);
+ vector = Insert(vector, y, 1);
+
+ auto bitcast = Ice::InstCast::create(::function, Ice::InstCast::Bitcast, result, vector.loadValue());
+ ::basicBlock->appendInst(bitcast);
+ }
+ else assert(false);
+ }
+ else
+ {
+ const Ice::Intrinsics::IntrinsicInfo intrinsic = {Ice::Intrinsics::LoadSubVector, Ice::Intrinsics::SideEffects_F, Ice::Intrinsics::ReturnsTwice_F, Ice::Intrinsics::MemoryWrite_F};
+ auto target = ::context->getConstantUndef(Ice::IceType_i32);
+ auto load = Ice::InstIntrinsicCall::create(::function, 2, result, target, intrinsic);
+ load->addArg(ptr);
+ load->addArg(::context->getConstantInt32(typeSize(type)));
+ ::basicBlock->appendInst(load);
+ }
}
else
{
@@ -871,13 +902,46 @@
if(valueType & EmulatedBits)
{
- const Ice::Intrinsics::IntrinsicInfo intrinsic = {Ice::Intrinsics::StoreSubVector, Ice::Intrinsics::SideEffects_T, Ice::Intrinsics::ReturnsTwice_F, Ice::Intrinsics::MemoryWrite_T};
- auto target = ::context->getConstantUndef(Ice::IceType_i32);
- auto store = Ice::InstIntrinsicCall::create(::function, 3, nullptr, target, intrinsic);
- store->addArg(value);
- store->addArg(ptr);
- store->addArg(::context->getConstantInt32(typeSize(type)));
- ::basicBlock->appendInst(store);
+ if(emulateIntrinsics)
+ {
+ if(typeSize(type) == 4)
+ {
+ Ice::Variable *vector = ::function->makeVariable(Ice::IceType_v4i32);
+ auto bitcast = Ice::InstCast::create(::function, Ice::InstCast::Bitcast, vector, value);
+ ::basicBlock->appendInst(bitcast);
+
+ RValue<Int4> v(V(vector));
+
+ auto pointer = RValue<Pointer<Byte>>(ptr);
+ Int x = Extract(v, 0);
+ *Pointer<Int>(pointer) = x;
+ }
+ else if(typeSize(type) == 8)
+ {
+ Ice::Variable *vector = ::function->makeVariable(Ice::IceType_v4i32);
+ auto bitcast = Ice::InstCast::create(::function, Ice::InstCast::Bitcast, vector, value);
+ ::basicBlock->appendInst(bitcast);
+
+ RValue<Int4> v(V(vector));
+
+ auto pointer = RValue<Pointer<Byte>>(ptr);
+ Int x = Extract(v, 0);
+ *Pointer<Int>(pointer) = x;
+ Int y = Extract(v, 1);
+ *Pointer<Int>(pointer + 4) = y;
+ }
+ else assert(false);
+ }
+ else
+ {
+ const Ice::Intrinsics::IntrinsicInfo intrinsic = {Ice::Intrinsics::StoreSubVector, Ice::Intrinsics::SideEffects_T, Ice::Intrinsics::ReturnsTwice_F, Ice::Intrinsics::MemoryWrite_T};
+ auto target = ::context->getConstantUndef(Ice::IceType_i32);
+ auto store = Ice::InstIntrinsicCall::create(::function, 3, nullptr, target, intrinsic);
+ store->addArg(value);
+ store->addArg(ptr);
+ store->addArg(::context->getConstantInt32(typeSize(type)));
+ ::basicBlock->appendInst(store);
+ }
}
else
{