Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions llvm/include/llvm/CodeGen/GlobalISel/LegalizerHelper.h
Original file line number Diff line number Diff line change
Expand Up @@ -300,6 +300,10 @@ class LegalizerHelper {
Type *OpType,
LostDebugLocObserver &LocObserver);

LegalizeResult emitModfLibcall(MachineInstr &MI, MachineIRBuilder &MIRBuilder,
unsigned Size, Type *OpType,
LostDebugLocObserver &LocObserver);

public:
/// Return the alignment to use for a stack temporary object with the given
/// type.
Expand Down
7 changes: 7 additions & 0 deletions llvm/include/llvm/CodeGen/GlobalISel/MachineIRBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -2184,6 +2184,13 @@ class LLVM_ABI MachineIRBuilder {
return buildInstr(TargetOpcode::G_FSINCOS, {Sin, Cos}, {Src}, Flags);
}

/// Build and insert \p Fract, \p Int = G_FMODF \p Src
MachineInstrBuilder buildModf(const DstOp &Fract, const DstOp &Int,
const SrcOp &Src,
std::optional<unsigned> Flags = std::nullopt) {
return buildInstr(TargetOpcode::G_FMODF, {Fract, Int}, {Src}, Flags);
}

/// Build and insert \p Res = G_FCOPYSIGN \p Op0, \p Op1
MachineInstrBuilder buildFCopysign(const DstOp &Dst, const SrcOp &Src0,
const SrcOp &Src1) {
Expand Down
3 changes: 3 additions & 0 deletions llvm/include/llvm/Support/TargetOpcodes.def
Original file line number Diff line number Diff line change
Expand Up @@ -650,6 +650,9 @@ HANDLE_TARGET_OPCODE(G_FDIV)
/// Generic FP remainder.
HANDLE_TARGET_OPCODE(G_FREM)

/// Generic FP modf
HANDLE_TARGET_OPCODE(G_FMODF)

/// Generic FP exponentiation.
HANDLE_TARGET_OPCODE(G_FPOW)

Expand Down
7 changes: 7 additions & 0 deletions llvm/include/llvm/Target/GenericOpcodes.td
Original file line number Diff line number Diff line change
Expand Up @@ -981,6 +981,13 @@ def G_FREM : GenericInstruction {
let hasSideEffects = false;
}

/// Generic FP modf
def G_FMODF : GenericInstruction {
let OutOperandList = (outs type0:$dst1, type0:$dst2);
let InOperandList = (ins type0:$src1);
let hasSideEffects = false;
}

// Floating point exponentiation.
def G_FPOW : GenericInstruction {
let OutOperandList = (outs type0:$dst);
Expand Down
7 changes: 7 additions & 0 deletions llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2362,6 +2362,13 @@ bool IRTranslator::translateKnownIntrinsic(const CallInst &CI, Intrinsic::ID ID,
MachineInstr::copyFlagsFromInstruction(CI));
return true;
}
case Intrinsic::modf: {
ArrayRef<Register> VRegs = getOrCreateVRegs(CI);
MIRBuilder.buildModf(VRegs[0], VRegs[1],
getOrCreateVReg(*CI.getArgOperand(0)),
MachineInstr::copyFlagsFromInstruction(CI));
return true;
}
case Intrinsic::sincos: {
ArrayRef<Register> VRegs = getOrCreateVRegs(CI);
MIRBuilder.buildFSincos(VRegs[0], VRegs[1],
Expand Down
63 changes: 63 additions & 0 deletions llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -471,6 +471,8 @@ static RTLIB::Libcall getRTLibDesc(unsigned Opcode, unsigned Size) {
RTLIBCASE(TANH_F);
case TargetOpcode::G_FSINCOS:
RTLIBCASE(SINCOS_F);
case TargetOpcode::G_FMODF:
RTLIBCASE(MODF_F);
case TargetOpcode::G_FLOG10:
RTLIBCASE(LOG10_F);
case TargetOpcode::G_FLOG:
Expand Down Expand Up @@ -702,6 +704,46 @@ LegalizerHelper::LegalizeResult LegalizerHelper::emitSincosLibcall(
return LegalizerHelper::Legalized;
}

LegalizerHelper::LegalizeResult
LegalizerHelper::emitModfLibcall(MachineInstr &MI, MachineIRBuilder &MIRBuilder,
unsigned Size, Type *OpType,
LostDebugLocObserver &LocObserver) {
MachineFunction &MF = MIRBuilder.getMF();
MachineRegisterInfo &MRI = MF.getRegInfo();

Register DstFrac = MI.getOperand(0).getReg();
Register DstInt = MI.getOperand(1).getReg();
Register Src = MI.getOperand(2).getReg();
LLT DstTy = MRI.getType(DstFrac);

int MemSize = DstTy.getSizeInBytes();
Align Alignment = getStackTemporaryAlignment(DstTy);
const DataLayout &DL = MIRBuilder.getDataLayout();
unsigned AddrSpace = DL.getAllocaAddrSpace();
MachinePointerInfo PtrInfo;

Register StackPtrInt =
createStackTemporary(TypeSize::getFixed(MemSize), Alignment, PtrInfo)
.getReg(0);

auto &Ctx = MF.getFunction().getContext();
auto LibcallResult = createLibcall(
MIRBuilder, getRTLibDesc(MI.getOpcode(), Size), {DstFrac, OpType, 0},
{{Src, OpType, 0}, {StackPtrInt, PointerType::get(Ctx, AddrSpace), 1}},
LocObserver, &MI);

if (LibcallResult != LegalizeResult::Legalized)
return LegalizerHelper::UnableToLegalize;

MachineMemOperand *LoadMMOInt = MF.getMachineMemOperand(
PtrInfo, MachineMemOperand::MOLoad, MemSize, Alignment);

MIRBuilder.buildLoad(DstInt, StackPtrInt, *LoadMMOInt);
MI.eraseFromParent();

return LegalizerHelper::Legalized;
}

LegalizerHelper::LegalizeResult
llvm::createMemLibcall(MachineIRBuilder &MIRBuilder, MachineRegisterInfo &MRI,
MachineInstr &MI, LostDebugLocObserver &LocObserver) {
Expand Down Expand Up @@ -1341,6 +1383,16 @@ LegalizerHelper::libcall(MachineInstr &MI, LostDebugLocObserver &LocObserver) {
}
return emitSincosLibcall(MI, MIRBuilder, Size, HLTy, LocObserver);
}
case TargetOpcode::G_FMODF: {
LLT LLTy = MRI.getType(MI.getOperand(0).getReg());
unsigned Size = LLTy.getSizeInBits();
Type *HLTy = getFloatTypeForLLT(Ctx, LLTy);
if (!HLTy || (Size != 32 && Size != 64 && Size != 80 && Size != 128)) {
LLVM_DEBUG(dbgs() << "No libcall available for type " << LLTy << ".\n");
return UnableToLegalize;
}
return emitModfLibcall(MI, MIRBuilder, Size, HLTy, LocObserver);
}
case TargetOpcode::G_LROUND:
case TargetOpcode::G_LLROUND:
case TargetOpcode::G_INTRINSIC_LRINT:
Expand Down Expand Up @@ -3333,6 +3385,16 @@ LegalizerHelper::widenScalar(MachineInstr &MI, unsigned TypeIdx, LLT WideTy) {
widenScalarDst(MI, WideTy, 0, TargetOpcode::G_FPTRUNC);
Observer.changedInstr(MI);
return Legalized;
case TargetOpcode::G_FMODF: {
Observer.changingInstr(MI);
widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_FPEXT);

widenScalarDst(MI, WideTy, 1, TargetOpcode::G_FPTRUNC);
MIRBuilder.setInsertPt(MIRBuilder.getMBB(), --MIRBuilder.getInsertPt());
widenScalarDst(MI, WideTy, 0, TargetOpcode::G_FPTRUNC);
Observer.changedInstr(MI);
return Legalized;
}
case TargetOpcode::G_FPOWI:
case TargetOpcode::G_FLDEXP:
case TargetOpcode::G_STRICT_FLDEXP: {
Expand Down Expand Up @@ -5472,6 +5534,7 @@ LegalizerHelper::fewerElementsVector(MachineInstr &MI, unsigned TypeIdx,
case G_LROUND:
case G_LLROUND:
case G_INTRINSIC_TRUNC:
case G_FMODF:
case G_FCOS:
case G_FSIN:
case G_FTAN:
Expand Down
2 changes: 1 addition & 1 deletion llvm/lib/Target/AArch64/GISel/AArch64LegalizerInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -438,7 +438,7 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST)
getActionDefinitionsBuilder({G_FCOS, G_FSIN, G_FPOW, G_FLOG, G_FLOG2,
G_FLOG10, G_FTAN, G_FEXP, G_FEXP2, G_FEXP10,
G_FACOS, G_FASIN, G_FATAN, G_FATAN2, G_FCOSH,
G_FSINH, G_FTANH})
G_FSINH, G_FTANH, G_FMODF})
// We need a call for these, so we always need to scalarize.
.scalarize(0)
// Regardless of FP16 support, widen 16-bit elements to 32-bits.
Expand Down
15 changes: 6 additions & 9 deletions llvm/lib/Target/SPIRV/SPIRVInstructionSelector.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -752,6 +752,8 @@ bool SPIRVInstructionSelector::spvSelect(Register ResVReg,
return selectExtInst(ResVReg, ResType, I, CL::exp, GL::Exp);
case TargetOpcode::G_FEXP2:
return selectExtInst(ResVReg, ResType, I, CL::exp2, GL::Exp2);
case TargetOpcode::G_FMODF:
return selectModf(ResVReg, ResType, I);

case TargetOpcode::G_FLOG:
return selectExtInst(ResVReg, ResType, I, CL::log, GL::Log);
Expand Down Expand Up @@ -3453,9 +3455,6 @@ bool SPIRVInstructionSelector::selectIntrinsic(Register ResVReg,
case Intrinsic::spv_discard: {
return selectDiscard(ResVReg, ResType, I);
}
case Intrinsic::modf: {
return selectModf(ResVReg, ResType, I);
}
default: {
std::string DiagMsg;
raw_string_ostream OS(DiagMsg);
Expand Down Expand Up @@ -4268,6 +4267,7 @@ bool SPIRVInstructionSelector::selectModf(Register ResVReg,
PtrTyReg,
LLT::pointer(storageClassToAddressSpace(SPIRV::StorageClass::Function),
GR.getPointerSize()));

// Assign SPIR-V type of the pointer type of the alloca variable to the
// new register.
GR.assignSPIRVTypeToVReg(PtrType, PtrTyReg, MIRBuilder.getMF());
Expand All @@ -4280,10 +4280,7 @@ bool SPIRVInstructionSelector::selectModf(Register ResVReg,
.addUse(GR.getSPIRVTypeID(PtrType))
.addImm(static_cast<uint32_t>(SPIRV::StorageClass::Function));
Register Variable = AllocaMIB->getOperand(0).getReg();
// Modf must have 4 operands, the first two are the 2 parts of the result,
// the third is the operand, and the last one is the floating point value.
assert(I.getNumOperands() == 4 &&
"Expected 4 operands for modf instruction");

MachineBasicBlock &BB = *I.getParent();
// Create the OpenCLLIB::modf instruction.
auto MIB =
Expand All @@ -4293,8 +4290,8 @@ bool SPIRVInstructionSelector::selectModf(Register ResVReg,
.addImm(static_cast<uint32_t>(SPIRV::InstructionSet::OpenCL_std))
.addImm(CL::modf)
.setMIFlags(I.getFlags())
.add(I.getOperand(3)) // Floating point value.
.addUse(Variable); // Pointer to integral part.
.add(I.getOperand(I.getNumExplicitDefs())) // Floating point value.
.addUse(Variable); // Pointer to integral part.
// Assign the integral part stored in the ptr to the second element of the
// result.
Register IntegralPartReg = I.getOperand(1).getReg();
Expand Down
1 change: 1 addition & 0 deletions llvm/lib/Target/SPIRV/SPIRVLegalizerInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -300,6 +300,7 @@ SPIRVLegalizerInfo::SPIRVLegalizerInfo(const SPIRVSubtarget &ST) {
getActionDefinitionsBuilder({G_STRICT_FSQRT,
G_FPOW,
G_FEXP,
G_FMODF,
G_FEXP2,
G_FLOG,
G_FLOG2,
Expand Down
Loading