1//===- RuntimeLibcalls.h - Interface for runtime libcalls -------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file implements a common interface to work with library calls into a
10// runtime that may be emitted by a given backend.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_IR_RUNTIME_LIBCALLS_H
15#define LLVM_IR_RUNTIME_LIBCALLS_H
16
17#include "llvm/ADT/ArrayRef.h"
18#include "llvm/IR/CallingConv.h"
19#include "llvm/Support/AtomicOrdering.h"
20#include "llvm/TargetParser/Triple.h"
21
22namespace llvm {
23namespace RTLIB {
24
25/// RTLIB::Libcall enum - This enum defines all of the runtime library calls
26/// the backend can emit. The various long double types cannot be merged,
27/// because 80-bit library functions use "xf" and 128-bit use "tf".
28///
29/// When adding PPCF128 functions here, note that their names generally need
30/// to be overridden for Darwin with the xxx$LDBL128 form. See
31/// PPCISelLowering.cpp.
32///
33enum Libcall {
34#define HANDLE_LIBCALL(code, name) code,
35#include "llvm/IR/RuntimeLibcalls.def"
36#undef HANDLE_LIBCALL
37};
38
39/// A simple container for information about the supported runtime calls.
40struct RuntimeLibcallsInfo {
41 explicit RuntimeLibcallsInfo(const Triple &TT) {
42 initLibcalls(TT);
43 }
44
45 /// Rename the default libcall routine name for the specified libcall.
46 void setLibcallName(RTLIB::Libcall Call, const char *Name) {
47 LibcallRoutineNames[Call] = Name;
48 }
49
50 void setLibcallName(ArrayRef<RTLIB::Libcall> Calls, const char *Name) {
51 for (auto Call : Calls)
52 setLibcallName(Call, Name);
53 }
54
55 /// Get the libcall routine name for the specified libcall.
56 const char *getLibcallName(RTLIB::Libcall Call) const {
57 return LibcallRoutineNames[Call];
58 }
59
60 /// Set the CallingConv that should be used for the specified libcall.
61 void setLibcallCallingConv(RTLIB::Libcall Call, CallingConv::ID CC) {
62 LibcallCallingConvs[Call] = CC;
63 }
64
65 /// Get the CallingConv that should be used for the specified libcall.
66 CallingConv::ID getLibcallCallingConv(RTLIB::Libcall Call) const {
67 return LibcallCallingConvs[Call];
68 }
69
70 iterator_range<const char **> getLibcallNames() {
71 return llvm::make_range(x: LibcallRoutineNames,
72 y: LibcallRoutineNames + RTLIB::UNKNOWN_LIBCALL);
73 }
74
75private:
76 /// Stores the name each libcall.
77 const char *LibcallRoutineNames[RTLIB::UNKNOWN_LIBCALL + 1];
78
79 /// Stores the CallingConv that should be used for each libcall.
80 CallingConv::ID LibcallCallingConvs[RTLIB::UNKNOWN_LIBCALL];
81
82 static bool darwinHasSinCos(const Triple &TT) {
83 assert(TT.isOSDarwin() && "should be called with darwin triple");
84 // Don't bother with 32 bit x86.
85 if (TT.getArch() == Triple::x86)
86 return false;
87 // Macos < 10.9 has no sincos_stret.
88 if (TT.isMacOSX())
89 return !TT.isMacOSXVersionLT(Major: 10, Minor: 9) && TT.isArch64Bit();
90 // iOS < 7.0 has no sincos_stret.
91 if (TT.isiOS())
92 return !TT.isOSVersionLT(Major: 7, Minor: 0);
93 // Any other darwin such as WatchOS/TvOS is new enough.
94 return true;
95 }
96
97 /// Set default libcall names. If a target wants to opt-out of a libcall it
98 /// should be placed here.
99 void initLibcalls(const Triple &TT);
100};
101
102} // namespace RTLIB
103} // namespace llvm
104
105#endif // LLVM_IR_RUNTIME_LIBCALLS_H
106