1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2025-01-31 12:41:49 +01:00

[ExecutionEngine] Add UnaryOperator visitor to the interpreter

This is to support the unary FNeg instruction.

Differential Revision: https://reviews.llvm.org/D62881

llvm-svn: 362941
This commit is contained in:
Cameron McInally 2019-06-10 14:38:48 +00:00
parent f21eb09da7
commit e5821b0815
3 changed files with 55 additions and 0 deletions

View File

@ -42,6 +42,58 @@ static void SetValue(Value *V, GenericValue Val, ExecutionContext &SF) {
SF.Values[V] = Val;
}
//===----------------------------------------------------------------------===//
// Unary Instruction Implementations
//===----------------------------------------------------------------------===//
static void executeFNegInst(GenericValue &Dest, GenericValue Src, Type *Ty) {
switch (Ty->getTypeID()) {
case Type::FloatTyID:
Dest.FloatVal = -Src.FloatVal;
case Type::DoubleTyID:
Dest.DoubleVal = -Src.DoubleVal;
default:
llvm_unreachable("Unhandled type for FNeg instruction");
}
}
void Interpreter::visitUnaryOperator(UnaryOperator &I) {
ExecutionContext &SF = ECStack.back();
Type *Ty = I.getOperand(0)->getType();
GenericValue Src = getOperandValue(I.getOperand(0), SF);
GenericValue R; // Result
// First process vector operation
if (Ty->isVectorTy()) {
R.AggregateVal.resize(Src.AggregateVal.size());
switch(I.getOpcode()) {
default:
llvm_unreachable("Don't know how to handle this unary operator");
break;
case Instruction::FNeg:
if (cast<VectorType>(Ty)->getElementType()->isFloatTy()) {
for (unsigned i = 0; i < R.AggregateVal.size(); ++i)
R.AggregateVal[i].FloatVal = -Src.AggregateVal[i].FloatVal;
} else if (cast<VectorType>(Ty)->getElementType()->isDoubleTy()) {
for (unsigned i = 0; i < R.AggregateVal.size(); ++i)
R.AggregateVal[i].DoubleVal = -Src.AggregateVal[i].DoubleVal;
} else {
llvm_unreachable("Unhandled type for FNeg instruction");
}
break;
}
} else {
switch (I.getOpcode()) {
default:
llvm_unreachable("Don't know how to handle this unary operator");
break;
case Instruction::FNeg: executeFNegInst(R, Src, Ty); break;
}
}
SetValue(&I, R, SF);
}
//===----------------------------------------------------------------------===//
// Binary Instruction Implementations
//===----------------------------------------------------------------------===//

View File

@ -124,6 +124,7 @@ public:
void visitSwitchInst(SwitchInst &I);
void visitIndirectBrInst(IndirectBrInst &I);
void visitUnaryOperator(UnaryOperator &I);
void visitBinaryOperator(BinaryOperator &I);
void visitICmpInst(ICmpInst &I);
void visitFCmpInst(FCmpInst &I);

View File

@ -8,6 +8,7 @@ define i32 @main() {
%C_float = fmul <4 x float> %B_float, %B_float
%D_float = fdiv <4 x float> %C_float, %B_float
%E_float = frem <4 x float> %D_float, %A_float
%F_float = fneg <4 x float> %E_float
%A_double = fadd <3 x double> <double 0.0, double 111.0, double 222.0>, <double 444.0, double 555.0, double 665.0>
@ -15,6 +16,7 @@ define i32 @main() {
%C_double = fmul <3 x double> %B_double, %B_double
%D_double = fdiv <3 x double> %C_double, %B_double
%E_double = frem <3 x double> %D_double, %A_double
%F_double = fneg <3 x double> %E_double
ret i32 0
}