Skip to content

Commit 4860acd

Browse files
authored
Merge branch 'main' into fix-loop-disposition-crash
2 parents 4ee925e + 831e79a commit 4860acd

File tree

26 files changed

+511
-296
lines changed

26 files changed

+511
-296
lines changed

clang/include/clang/CIR/Dialect/IR/CIROps.td

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4191,6 +4191,16 @@ def CIR_CosOp : CIR_UnaryFPToFPBuiltinOp<"cos", "CosOp"> {
41914191
}];
41924192
}
41934193

4194+
def CIR_ExpOp : CIR_UnaryFPToFPBuiltinOp<"exp", "ExpOp"> {
4195+
let summary = "Computes the floating-point base-e exponential value";
4196+
let description = [{
4197+
`cir.exp` computes the exponential of a floating-point operand and returns
4198+
a result of the same type.
4199+
4200+
Floating-point exceptions are ignored, and it does not set `errno`.
4201+
}];
4202+
}
4203+
41944204
def CIR_FAbsOp : CIR_UnaryFPToFPBuiltinOp<"fabs", "FAbsOp"> {
41954205
let summary = "Computes the floating-point absolute value";
41964206
let description = [{

clang/lib/CIR/CodeGen/CIRGenBuiltin.cpp

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,17 @@ RValue CIRGenFunction::emitBuiltinExpr(const GlobalDecl &gd, unsigned builtinID,
222222
assert(!cir::MissingFeatures::fastMathFlags());
223223
return emitUnaryMaybeConstrainedFPBuiltin<cir::CeilOp>(*this, *e);
224224

225+
case Builtin::BIexp:
226+
case Builtin::BIexpf:
227+
case Builtin::BIexpl:
228+
case Builtin::BI__builtin_exp:
229+
case Builtin::BI__builtin_expf:
230+
case Builtin::BI__builtin_expf16:
231+
case Builtin::BI__builtin_expl:
232+
case Builtin::BI__builtin_expf128:
233+
assert(!cir::MissingFeatures::fastMathFlags());
234+
return emitUnaryMaybeConstrainedFPBuiltin<cir::ExpOp>(*this, *e);
235+
225236
case Builtin::BIfabs:
226237
case Builtin::BIfabsf:
227238
case Builtin::BIfabsl:

clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,14 @@ mlir::LogicalResult CIRToLLVMCosOpLowering::matchAndRewrite(
194194
return mlir::success();
195195
}
196196

197+
mlir::LogicalResult CIRToLLVMExpOpLowering::matchAndRewrite(
198+
cir::ExpOp op, OpAdaptor adaptor,
199+
mlir::ConversionPatternRewriter &rewriter) const {
200+
mlir::Type resTy = typeConverter->convertType(op.getType());
201+
rewriter.replaceOpWithNewOp<mlir::LLVM::ExpOp>(op, resTy, adaptor.getSrc());
202+
return mlir::success();
203+
}
204+
197205
static mlir::Value getLLVMIntCast(mlir::ConversionPatternRewriter &rewriter,
198206
mlir::Value llvmSrc, mlir::Type llvmDstIntTy,
199207
bool isUnsigned, uint64_t cirSrcWidth,

clang/test/Analysis/LifetimeSafety/CMakeLists.txt

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,14 +15,21 @@ set(LIFETIME_BENCHMARK_REQUIREMENTS
1515
set(LIFETIME_BENCHMARK_OUTPUT_DIR
1616
"${CMAKE_CURRENT_BINARY_DIR}/benchmark_results")
1717

18+
if(WIN32)
19+
set(LIFETIME_BENCHMARK_VENV_PYTHON_EXECUTABLE
20+
"${LIFETIME_BENCHMARK_VENV_DIR}/Scripts/python")
21+
else()
22+
set(LIFETIME_BENCHMARK_VENV_PYTHON_EXECUTABLE
23+
"${LIFETIME_BENCHMARK_VENV_DIR}/bin/python")
24+
endif()
1825

1926
if(EXISTS ${LIFETIME_BENCHMARK_SCRIPT} AND EXISTS ${LIFETIME_BENCHMARK_REQUIREMENTS})
2027

2128
# Set up the virtual environment and install packages
2229
add_custom_command(
2330
OUTPUT ${LIFETIME_BENCHMARK_VENV_DIR}/pyvenv.cfg
2431
COMMAND ${Python3_EXECUTABLE} -m venv ${LIFETIME_BENCHMARK_VENV_DIR}
25-
COMMAND ${LIFETIME_BENCHMARK_VENV_DIR}/bin/python -m pip install -r ${LIFETIME_BENCHMARK_REQUIREMENTS}
32+
COMMAND ${LIFETIME_BENCHMARK_VENV_PYTHON_EXECUTABLE} -m pip install -r ${LIFETIME_BENCHMARK_REQUIREMENTS}
2633
DEPENDS ${LIFETIME_BENCHMARK_REQUIREMENTS}
2734
COMMENT "Creating Python virtual environment and installing dependencies for benchmark..."
2835
)
@@ -32,7 +39,7 @@ if(EXISTS ${LIFETIME_BENCHMARK_SCRIPT} AND EXISTS ${LIFETIME_BENCHMARK_REQUIREME
3239

3340
# Main benchmark target
3441
add_custom_target(benchmark_lifetime_safety_analysis
35-
COMMAND ${LIFETIME_BENCHMARK_VENV_DIR}/bin/python ${LIFETIME_BENCHMARK_SCRIPT}
42+
COMMAND ${LIFETIME_BENCHMARK_VENV_PYTHON_EXECUTABLE} ${LIFETIME_BENCHMARK_SCRIPT}
3643
--clang-binary ${LLVM_BINARY_DIR}/bin/clang
3744
--output-dir ${LIFETIME_BENCHMARK_OUTPUT_DIR}
3845

clang/test/CIR/CodeGen/builtins-floating-point.c

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,3 +25,24 @@ float ceil(float f) {
2525
// LLVM: %{{.*}} = call float @llvm.ceil.f32(float %{{.*}})
2626
// OGCG: %{{.*}} = call float @llvm.ceil.f32(float %{{.*}})
2727
}
28+
29+
float expf(float f) {
30+
return __builtin_expf(f);
31+
// CIR: %{{.*}} = cir.exp {{.*}} : !cir.float
32+
// LLVM: %{{.*}} = call float @llvm.exp.f32(float %{{.*}})
33+
// OGCG: %{{.*}} = call float @llvm.exp.f32(float %{{.*}})
34+
}
35+
36+
double exp(double f) {
37+
return __builtin_exp(f);
38+
// CIR: %{{.*}} = cir.exp {{.*}} : !cir.double
39+
// LLVM: %{{.*}} = call double @llvm.exp.f64(double %{{.*}})
40+
// OGCG: %{{.*}} = call double @llvm.exp.f64(double %{{.*}})
41+
}
42+
43+
long double expl(long double f) {
44+
return __builtin_expl(f);
45+
// CIR: %{{.*}} = cir.exp {{.*}} : !cir.long_double<!cir.f128>
46+
// LLVM: %{{.*}} = call fp128 @llvm.exp.f128(fp128 %{{.*}})
47+
// OGCG: %{{.*}} = call fp128 @llvm.exp.f128(fp128 %{{.*}})
48+
}

llvm/include/llvm/CodeGen/BasicTTIImpl.h

Lines changed: 29 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -302,7 +302,6 @@ class BasicTTIImplBase : public TargetTransformInfoImplCRTPBase<T> {
302302
/// (e.g. scalarization).
303303
std::optional<InstructionCost> getMultipleResultIntrinsicVectorLibCallCost(
304304
const IntrinsicCostAttributes &ICA, TTI::TargetCostKind CostKind,
305-
RTLIB::Libcall LC,
306305
std::optional<unsigned> CallRetElementIndex = {}) const {
307306
Type *RetTy = ICA.getReturnType();
308307
// Vector variants of the intrinsic can be mapped to a vector library call.
@@ -311,12 +310,38 @@ class BasicTTIImplBase : public TargetTransformInfoImplCRTPBase<T> {
311310
!isVectorizedStructTy(cast<StructType>(RetTy)))
312311
return std::nullopt;
313312

313+
Type *Ty = getContainedTypes(RetTy).front();
314+
EVT VT = getTLI()->getValueType(DL, Ty);
315+
316+
EVT ScalarVT = VT.getScalarType();
317+
RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
318+
319+
switch (ICA.getID()) {
320+
case Intrinsic::modf:
321+
LC = RTLIB::getMODF(ScalarVT);
322+
break;
323+
case Intrinsic::sincospi:
324+
LC = RTLIB::getSINCOSPI(ScalarVT);
325+
break;
326+
case Intrinsic::sincos:
327+
LC = RTLIB::getSINCOS(ScalarVT);
328+
break;
329+
default:
330+
return std::nullopt;
331+
}
332+
314333
// Find associated libcall.
315-
const char *LCName = getTLI()->getLibcallName(LC);
316-
if (!LCName)
334+
RTLIB::LibcallImpl LibcallImpl = getTLI()->getLibcallImpl(LC);
335+
if (LibcallImpl == RTLIB::Unsupported)
317336
return std::nullopt;
318337

338+
StringRef LCName =
339+
RTLIB::RuntimeLibcallsInfo::getLibcallImplName(LibcallImpl);
340+
319341
// Search for a corresponding vector variant.
342+
//
343+
// FIXME: Should use RuntimeLibcallsInfo, not TargetLibraryInfo to get the
344+
// vector mapping.
320345
LLVMContext &Ctx = RetTy->getContext();
321346
ElementCount VF = getVectorizedTypeVF(RetTy);
322347
VecDesc const *VD = nullptr;
@@ -2137,30 +2162,14 @@ class BasicTTIImplBase : public TargetTransformInfoImplCRTPBase<T> {
21372162
case Intrinsic::modf:
21382163
case Intrinsic::sincos:
21392164
case Intrinsic::sincospi: {
2140-
Type *Ty = getContainedTypes(RetTy).front();
2141-
EVT VT = getTLI()->getValueType(DL, Ty);
2142-
2143-
RTLIB::Libcall LC = [&] {
2144-
switch (ICA.getID()) {
2145-
case Intrinsic::modf:
2146-
return RTLIB::getMODF;
2147-
case Intrinsic::sincos:
2148-
return RTLIB::getSINCOS;
2149-
case Intrinsic::sincospi:
2150-
return RTLIB::getSINCOSPI;
2151-
default:
2152-
llvm_unreachable("unexpected intrinsic");
2153-
}
2154-
}()(VT.getScalarType());
2155-
21562165
std::optional<unsigned> CallRetElementIndex;
21572166
// The first element of the modf result is returned by value in the
21582167
// libcall.
21592168
if (ICA.getID() == Intrinsic::modf)
21602169
CallRetElementIndex = 0;
21612170

21622171
if (auto Cost = getMultipleResultIntrinsicVectorLibCallCost(
2163-
ICA, CostKind, LC, CallRetElementIndex))
2172+
ICA, CostKind, CallRetElementIndex))
21642173
return *Cost;
21652174
// Otherwise, fallback to default scalarization cost.
21662175
break;

llvm/include/llvm/IR/RuntimeLibcalls.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -186,6 +186,13 @@ struct RuntimeLibcallsInfo {
186186
return RTLIB::Unsupported;
187187
}
188188

189+
/// \returns the function type and attributes for the \p LibcallImpl,
190+
/// depending on the target \p TT. If the function has incomplete type
191+
/// information, return nullptr for the function type.
192+
std::pair<FunctionType *, AttributeList>
193+
getFunctionTy(LLVMContext &Ctx, const Triple &TT, const DataLayout &DL,
194+
RTLIB::LibcallImpl LibcallImpl) const;
195+
189196
private:
190197
LLVM_ABI static iota_range<RTLIB::LibcallImpl>
191198
lookupLibcallImplNameImpl(StringRef Name);

llvm/lib/CodeGen/SelectionDAG/LegalizeDAG.cpp

Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,8 @@ class SelectionDAGLegalize {
163163
RTLIB::Libcall CallI128);
164164
void ExpandDivRemLibCall(SDNode *Node, SmallVectorImpl<SDValue> &Results);
165165

166+
SDValue ExpandSincosStretLibCall(SDNode *Node) const;
167+
166168
SDValue EmitStackConvert(SDValue SrcOp, EVT SlotVT, EVT DestVT,
167169
const SDLoc &dl);
168170
SDValue EmitStackConvert(SDValue SrcOp, EVT SlotVT, EVT DestVT,
@@ -2423,6 +2425,101 @@ static bool useSinCos(SDNode *Node) {
24232425
return false;
24242426
}
24252427

2428+
SDValue SelectionDAGLegalize::ExpandSincosStretLibCall(SDNode *Node) const {
2429+
// For iOS, we want to call an alternative entry point: __sincos_stret,
2430+
// which returns the values in two S / D registers.
2431+
SDLoc dl(Node);
2432+
SDValue Arg = Node->getOperand(0);
2433+
EVT ArgVT = Arg.getValueType();
2434+
RTLIB::Libcall LC = RTLIB::getSINCOS_STRET(ArgVT);
2435+
RTLIB::LibcallImpl SincosStret = TLI.getLibcallImpl(LC);
2436+
if (SincosStret == RTLIB::Unsupported)
2437+
return SDValue();
2438+
2439+
/// There are 3 different ABI cases to handle:
2440+
/// - Direct return of separate fields in registers
2441+
/// - Single return as vector elements
2442+
/// - sret struct
2443+
2444+
const RTLIB::RuntimeLibcallsInfo &CallsInfo = TLI.getRuntimeLibcallsInfo();
2445+
2446+
const DataLayout &DL = DAG.getDataLayout();
2447+
2448+
auto [FuncTy, FuncAttrs] = CallsInfo.getFunctionTy(
2449+
*DAG.getContext(), TM.getTargetTriple(), DL, SincosStret);
2450+
2451+
Type *SincosStretRetTy = FuncTy->getReturnType();
2452+
CallingConv::ID CallConv = CallsInfo.getLibcallImplCallingConv(SincosStret);
2453+
StringRef LibcallImplName = CallsInfo.getLibcallImplName(SincosStret);
2454+
2455+
SDValue Callee = DAG.getExternalSymbol(LibcallImplName.data(),
2456+
TLI.getProgramPointerTy(DL));
2457+
2458+
TargetLowering::ArgListTy Args;
2459+
SDValue SRet;
2460+
2461+
int FrameIdx;
2462+
if (FuncTy->getParamType(0)->isPointerTy()) {
2463+
// Uses sret
2464+
MachineFrameInfo &MFI = DAG.getMachineFunction().getFrameInfo();
2465+
2466+
AttributeSet PtrAttrs = FuncAttrs.getParamAttrs(0);
2467+
Type *StructTy = PtrAttrs.getStructRetType();
2468+
const uint64_t ByteSize = DL.getTypeAllocSize(StructTy);
2469+
const Align StackAlign = DL.getPrefTypeAlign(StructTy);
2470+
2471+
FrameIdx = MFI.CreateStackObject(ByteSize, StackAlign, false);
2472+
SRet = DAG.getFrameIndex(FrameIdx, TLI.getFrameIndexTy(DL));
2473+
2474+
TargetLowering::ArgListEntry Entry(SRet, FuncTy->getParamType(0));
2475+
Entry.IsSRet = true;
2476+
Entry.IndirectType = StructTy;
2477+
Entry.Alignment = StackAlign;
2478+
2479+
Args.push_back(Entry);
2480+
Args.emplace_back(Arg, FuncTy->getParamType(1));
2481+
} else {
2482+
Args.emplace_back(Arg, FuncTy->getParamType(0));
2483+
}
2484+
2485+
TargetLowering::CallLoweringInfo CLI(DAG);
2486+
CLI.setDebugLoc(dl)
2487+
.setChain(DAG.getEntryNode())
2488+
.setLibCallee(CallConv, SincosStretRetTy, Callee, std::move(Args))
2489+
.setIsPostTypeLegalization();
2490+
2491+
std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
2492+
2493+
if (SRet) {
2494+
MachinePointerInfo PtrInfo =
2495+
MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FrameIdx);
2496+
SDValue LoadSin = DAG.getLoad(ArgVT, dl, CallResult.second, SRet, PtrInfo);
2497+
2498+
TypeSize StoreSize = ArgVT.getStoreSize();
2499+
2500+
// Address of cos field.
2501+
SDValue Add = DAG.getObjectPtrOffset(dl, SRet, StoreSize);
2502+
SDValue LoadCos = DAG.getLoad(ArgVT, dl, LoadSin.getValue(1), Add,
2503+
PtrInfo.getWithOffset(StoreSize));
2504+
2505+
SDVTList Tys = DAG.getVTList(ArgVT, ArgVT);
2506+
return DAG.getNode(ISD::MERGE_VALUES, dl, Tys, LoadSin.getValue(0),
2507+
LoadCos.getValue(0));
2508+
}
2509+
2510+
if (!CallResult.first.getValueType().isVector())
2511+
return CallResult.first;
2512+
2513+
SDValue SinVal =
2514+
DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, ArgVT, CallResult.first,
2515+
DAG.getVectorIdxConstant(0, dl));
2516+
SDValue CosVal =
2517+
DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, ArgVT, CallResult.first,
2518+
DAG.getVectorIdxConstant(1, dl));
2519+
SDVTList Tys = DAG.getVTList(ArgVT, ArgVT);
2520+
return DAG.getNode(ISD::MERGE_VALUES, dl, Tys, SinVal, CosVal);
2521+
}
2522+
24262523
SDValue SelectionDAGLegalize::expandLdexp(SDNode *Node) const {
24272524
SDLoc dl(Node);
24282525
EVT VT = Node->getValueType(0);
@@ -4730,6 +4827,18 @@ void SelectionDAGLegalize::ConvertNodeToLibcall(SDNode *Node) {
47304827
case ISD::FSINCOS:
47314828
case ISD::FSINCOSPI: {
47324829
EVT VT = Node->getValueType(0);
4830+
4831+
if (Node->getOpcode() == ISD::FSINCOS) {
4832+
RTLIB::Libcall SincosStret = RTLIB::getSINCOS_STRET(VT);
4833+
if (SincosStret != RTLIB::UNKNOWN_LIBCALL) {
4834+
if (SDValue Expanded = ExpandSincosStretLibCall(Node)) {
4835+
Results.push_back(Expanded);
4836+
Results.push_back(Expanded.getValue(1));
4837+
break;
4838+
}
4839+
}
4840+
}
4841+
47334842
RTLIB::Libcall LC = Node->getOpcode() == ISD::FSINCOS
47344843
? RTLIB::getSINCOS(VT)
47354844
: RTLIB::getSINCOSPI(VT);

0 commit comments

Comments
 (0)