blob: 4b94bcfc432c67845f467d2e2570c6be84cbb0d2 [file] [log] [blame]
Reid Spencer5f016e22007-07-11 17:01:13 +00001//===--- Targets.cpp - Implement -arch option and targets -----------------===//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner0bc735f2007-12-29 19:59:25 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Reid Spencer5f016e22007-07-11 17:01:13 +00007//
8//===----------------------------------------------------------------------===//
9//
Anton Korobeynikova7c47172009-05-03 13:42:53 +000010// This file implements construction of a TargetInfo object from a
Ted Kremenekbbced582007-12-12 18:05:32 +000011// target triple.
Reid Spencer5f016e22007-07-11 17:01:13 +000012//
13//===----------------------------------------------------------------------===//
14
Douglas Gregorb1152d82009-02-16 21:58:21 +000015// FIXME: Layering violation
Reid Spencer5f016e22007-07-11 17:01:13 +000016#include "clang/AST/Builtins.h"
Anders Carlsson564f1de2007-12-09 23:17:02 +000017#include "clang/AST/TargetBuiltins.h"
Reid Spencer5f016e22007-07-11 17:01:13 +000018#include "clang/Basic/TargetInfo.h"
Chris Lattner8fc4dfb2008-12-04 22:54:33 +000019#include "clang/Basic/LangOptions.h"
Anders Carlsson3346ae62007-11-24 23:38:12 +000020#include "llvm/ADT/STLExtras.h"
Eli Friedman25531262008-05-20 14:27:34 +000021#include "llvm/ADT/APFloat.h"
Chris Lattnerca45cff2009-03-20 16:06:38 +000022#include "llvm/ADT/SmallString.h"
Reid Spencer5f016e22007-07-11 17:01:13 +000023using namespace clang;
24
Reid Spencer5f016e22007-07-11 17:01:13 +000025//===----------------------------------------------------------------------===//
26// Common code shared among targets.
27//===----------------------------------------------------------------------===//
28
Chris Lattnerd15fa822007-10-06 06:57:34 +000029static void Define(std::vector<char> &Buf, const char *Macro,
30 const char *Val = "1") {
31 const char *Def = "#define ";
32 Buf.insert(Buf.end(), Def, Def+strlen(Def));
33 Buf.insert(Buf.end(), Macro, Macro+strlen(Macro));
34 Buf.push_back(' ');
35 Buf.insert(Buf.end(), Val, Val+strlen(Val));
36 Buf.push_back('\n');
37}
38
Chris Lattnerca45cff2009-03-20 16:06:38 +000039/// DefineStd - Define a macro name and standard variants. For example if
40/// MacroName is "unix", then this will define "__unix", "__unix__", and "unix"
41/// when in GNU mode.
Anton Korobeynikova7c47172009-05-03 13:42:53 +000042static void DefineStd(std::vector<char> &Buf, const char *MacroName,
Chris Lattnerca45cff2009-03-20 16:06:38 +000043 const LangOptions &Opts) {
44 assert(MacroName[0] != '_' && "Identifier should be in the user's namespace");
Anton Korobeynikova7c47172009-05-03 13:42:53 +000045
Chris Lattnerca45cff2009-03-20 16:06:38 +000046 // If in GNU mode (e.g. -std=gnu99 but not -std=c99) define the raw identifier
47 // in the user's namespace.
48 if (Opts.GNUMode)
49 Define(Buf, MacroName);
Anton Korobeynikova7c47172009-05-03 13:42:53 +000050
Chris Lattnerca45cff2009-03-20 16:06:38 +000051 // Define __unix.
52 llvm::SmallString<20> TmpStr;
53 TmpStr = "__";
54 TmpStr += MacroName;
55 Define(Buf, TmpStr.c_str());
Anton Korobeynikova7c47172009-05-03 13:42:53 +000056
Chris Lattnerca45cff2009-03-20 16:06:38 +000057 // Define __unix__.
58 TmpStr += "__";
59 Define(Buf, TmpStr.c_str());
60}
61
Chris Lattnerd29b6302008-10-05 21:50:58 +000062//===----------------------------------------------------------------------===//
63// Defines specific to certain operating systems.
64//===----------------------------------------------------------------------===//
65
Douglas Gregor163a7c72009-05-21 23:51:30 +000066static void getSolarisDefines(const LangOptions &Opts, std::vector<char> &Defs) {
67 DefineStd(Defs, "sun", Opts);
68 DefineStd(Defs, "unix", Opts);
Eli Friedman09c3a6d2009-05-22 01:12:57 +000069 Define(Defs, "__ELF__");
70 Define(Defs, "__svr4__");
71 Define(Defs, "__SVR4");
Eli Friedman01b86682008-08-20 07:28:14 +000072}
Reid Spencer5f016e22007-07-11 17:01:13 +000073
Chris Lattner318ca712009-03-20 15:55:34 +000074static void getFreeBSDDefines(const LangOptions &Opts, bool is64Bit,
75 const char *Triple, std::vector<char> &Defs) {
Chris Lattnerfd0269d2008-10-16 17:04:31 +000076 // FreeBSD defines; list based off of gcc output
77
78 const char *FreeBSD = strstr(Triple, "-freebsd");
79 FreeBSD += strlen("-freebsd");
80 char release[] = "X";
81 release[0] = FreeBSD[0];
82 char version[] = "X00001";
83 version[0] = FreeBSD[0];
84
85 Define(Defs, "__FreeBSD__", release);
86 Define(Defs, "__FreeBSD_cc_version", version);
87 Define(Defs, "__KPRINTF_ATTRIBUTE__");
Chris Lattnerca45cff2009-03-20 16:06:38 +000088 DefineStd(Defs, "unix", Opts);
Anton Korobeynikov2793bda2009-02-14 16:42:50 +000089 Define(Defs, "__ELF__", "1");
Chris Lattnerfd0269d2008-10-16 17:04:31 +000090 if (is64Bit) {
91 Define(Defs, "__LP64__");
92 }
93}
94
Chris Lattner318ca712009-03-20 15:55:34 +000095static void getDragonFlyDefines(const LangOptions &Opts,
96 std::vector<char> &Defs) {
Chris Lattnerd29b6302008-10-05 21:50:58 +000097 // DragonFly defines; list based off of gcc output
98 Define(Defs, "__DragonFly__");
99 Define(Defs, "__DragonFly_cc_version", "100001");
100 Define(Defs, "__ELF__");
101 Define(Defs, "__KPRINTF_ATTRIBUTE__");
102 Define(Defs, "__tune_i386__");
Chris Lattnerca45cff2009-03-20 16:06:38 +0000103 DefineStd(Defs, "unix", Opts);
Chris Lattnerd29b6302008-10-05 21:50:58 +0000104}
105
Chris Lattner318ca712009-03-20 15:55:34 +0000106static void getLinuxDefines(const LangOptions &Opts, std::vector<char> &Defs) {
Chris Lattnerd29b6302008-10-05 21:50:58 +0000107 // Linux defines; list based off of gcc output
Chris Lattnerca45cff2009-03-20 16:06:38 +0000108 DefineStd(Defs, "unix", Opts);
109 DefineStd(Defs, "linux", Opts);
Chris Lattnerd29b6302008-10-05 21:50:58 +0000110 Define(Defs, "__gnu_linux__");
Argyrios Kyrtzidis487cdee2009-02-14 15:02:45 +0000111 Define(Defs, "__ELF__", "1");
Chris Lattnerd29b6302008-10-05 21:50:58 +0000112}
113
Chris Lattnerae0ee032008-12-04 23:20:07 +0000114/// getDarwinNumber - Parse the 'darwin number' out of the specific targe
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000115/// triple. For example, if we have darwin8.5 return 8,5,0. If any entry is
Chris Lattnerae0ee032008-12-04 23:20:07 +0000116/// not defined, return 0's. Return true if we have -darwin in the string or
117/// false otherwise.
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000118static bool getDarwinNumber(const char *Triple, unsigned &Maj, unsigned &Min, unsigned &Revision) {
119 Maj = Min = Revision = 0;
Chris Lattnerae0ee032008-12-04 23:20:07 +0000120 const char *Darwin = strstr(Triple, "-darwin");
121 if (Darwin == 0) return false;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000122
Chris Lattnerae0ee032008-12-04 23:20:07 +0000123 Darwin += strlen("-darwin");
124 if (Darwin[0] < '0' || Darwin[0] > '9')
125 return true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000126
Chris Lattnerae0ee032008-12-04 23:20:07 +0000127 Maj = Darwin[0]-'0';
128 ++Darwin;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000129
Chris Lattnerae0ee032008-12-04 23:20:07 +0000130 // Handle "darwin11".
131 if (Maj == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') {
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000132 Maj = Maj*10 + (Darwin[0] - '0');
Chris Lattnerae0ee032008-12-04 23:20:07 +0000133 ++Darwin;
134 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000135
Chris Lattnerae0ee032008-12-04 23:20:07 +0000136 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049"
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000137 if (Darwin[0] != '.')
138 return true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000139
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000140 ++Darwin;
141 if (Darwin[0] < '0' || Darwin[0] > '9')
142 return true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000143
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000144 Min = Darwin[0]-'0';
145 ++Darwin;
146
147 // Handle 10.4.11 -> darwin8.11
148 if (Min == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') {
149 Min = Min*10 + (Darwin[0] - '0');
150 ++Darwin;
151 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000152
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000153 // Handle revision darwin8.9.1
154 if (Darwin[0] != '.')
155 return true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000156
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000157 ++Darwin;
158 if (Darwin[0] < '0' || Darwin[0] > '9')
159 return true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000160
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000161 Revision = Darwin[0]-'0';
162 ++Darwin;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000163
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000164 if (Revision == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') {
165 Revision = Revision*10 + (Darwin[0] - '0');
166 ++Darwin;
167 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000168
Chris Lattnerae0ee032008-12-04 23:20:07 +0000169 return true;
170}
171
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000172static void getDarwinDefines(std::vector<char> &Defs, const LangOptions &Opts) {
Eli Friedman618234a2008-08-20 02:34:37 +0000173 Define(Defs, "__APPLE__");
174 Define(Defs, "__MACH__");
Chris Lattnerd427ad42009-02-05 07:19:24 +0000175 Define(Defs, "OBJC_NEW_PROPERTIES");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000176
Chris Lattner10d24272009-04-07 16:50:40 +0000177 // __weak is always defined, for use in blocks and with objc pointers.
178 Define(Defs, "__weak", "__attribute__((objc_gc(weak)))");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000179
Chris Lattner10d24272009-04-07 16:50:40 +0000180 // Darwin defines __strong even in C mode (just to nothing).
181 if (!Opts.ObjC1 || Opts.getGCMode() == LangOptions::NonGC)
Chris Lattner3a5cbd32009-04-07 04:48:21 +0000182 Define(Defs, "__strong", "");
Chris Lattner10d24272009-04-07 16:50:40 +0000183 else
Chris Lattner3a5cbd32009-04-07 04:48:21 +0000184 Define(Defs, "__strong", "__attribute__((objc_gc(strong)))");
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000185}
186
187static void getDarwinOSXDefines(std::vector<char> &Defs, const char *Triple) {
Chris Lattner8b30c412008-09-30 01:00:25 +0000188 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5.
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000189 unsigned Maj, Min, Rev;
190 if (getDarwinNumber(Triple, Maj, Min, Rev)) {
191 char MacOSXStr[] = "1000";
Chris Lattnerae0ee032008-12-04 23:20:07 +0000192 if (Maj >= 4 && Maj <= 13) { // 10.0-10.9
193 // darwin7 -> 1030, darwin8 -> 1040, darwin9 -> 1050, etc.
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000194 MacOSXStr[2] = '0' + Maj-4;
195 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000196
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000197 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049"
198 // Cap 10.4.11 -> darwin8.11 -> "1049"
199 MacOSXStr[3] = std::min(Min, 9U)+'0';
200 Define(Defs, "__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", MacOSXStr);
201 }
202}
203
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000204static void getDarwinIPhoneOSDefines(std::vector<char> &Defs,
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000205 const char *Triple) {
206 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5.
207 unsigned Maj, Min, Rev;
208 if (getDarwinNumber(Triple, Maj, Min, Rev)) {
209 // When targetting iPhone OS, interpret the minor version and
210 // revision as the iPhone OS version
211 char iPhoneOSStr[] = "10000";
212 if (Min >= 2 && Min <= 9) { // iPhone OS 2.0-9.0
213 // darwin9.2.0 -> 20000, darwin9.3.0 -> 30000, etc.
214 iPhoneOSStr[0] = '0' + Min;
Chris Lattner8b30c412008-09-30 01:00:25 +0000215 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000216
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000217 // Handle minor version: 2.2 -> darwin9.2.2 -> 20200
218 iPhoneOSStr[2] = std::min(Rev, 9U)+'0';
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000219 Define(Defs, "__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__",
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000220 iPhoneOSStr);
Chris Lattner8b30c412008-09-30 01:00:25 +0000221 }
Eli Friedman618234a2008-08-20 02:34:37 +0000222}
Reid Spencer5f016e22007-07-11 17:01:13 +0000223
Chris Lattnerae0ee032008-12-04 23:20:07 +0000224/// GetDarwinLanguageOptions - Set the default language options for darwin.
225static void GetDarwinLanguageOptions(LangOptions &Opts,
226 const char *Triple) {
227 Opts.NeXTRuntime = true;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000228
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000229 unsigned Maj, Min, Rev;
230 if (!getDarwinNumber(Triple, Maj, Min, Rev))
Chris Lattnerae0ee032008-12-04 23:20:07 +0000231 return;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000232
Chris Lattnerae0ee032008-12-04 23:20:07 +0000233 // Blocks default to on for 10.6 (darwin10) and beyond.
Fariborz Jahaniana30b17b2009-02-12 17:54:33 +0000234 // As does nonfragile-abi for 64bit mode
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000235 if (Maj > 9)
Chris Lattnerae0ee032008-12-04 23:20:07 +0000236 Opts.Blocks = 1;
Fariborz Jahanian66a5c2c2009-02-24 23:34:44 +0000237
Fariborz Jahanian84d01332009-02-24 23:38:42 +0000238 if (Maj >= 9 && Opts.ObjC1 && !strncmp(Triple, "x86_64", 6))
239 Opts.ObjCNonFragileABI = 1;
Chris Lattnerae0ee032008-12-04 23:20:07 +0000240}
241
242
Chris Lattnerd29b6302008-10-05 21:50:58 +0000243//===----------------------------------------------------------------------===//
Eli Friedmane4277982008-08-20 23:11:40 +0000244// Specific target implementations.
245//===----------------------------------------------------------------------===//
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000246
Eli Friedmane4277982008-08-20 23:11:40 +0000247namespace {
248// PPC abstract base class
249class PPCTargetInfo : public TargetInfo {
250 static const Builtin::Info BuiltinInfo[];
251 static const char * const GCCRegNames[];
252 static const TargetInfo::GCCRegAlias GCCRegAliases[];
253
254public:
255 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) {
256 CharIsSigned = false;
257 }
258 virtual void getTargetBuiltins(const Builtin::Info *&Records,
259 unsigned &NumRecords) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000260 Records = BuiltinInfo;
Eli Friedmane4277982008-08-20 23:11:40 +0000261 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000262 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000263
Chris Lattner33328642009-03-20 15:52:06 +0000264 virtual void getTargetDefines(const LangOptions &Opts,
265 std::vector<char> &Defines) const;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000266
Eli Friedmane4277982008-08-20 23:11:40 +0000267 virtual const char *getVAListDeclaration() const {
Chris Lattnerd5998502008-10-27 01:11:29 +0000268 return "typedef char* __builtin_va_list;";
269 // This is the right definition for ABI/V4: System V.4/eabi.
270 /*return "typedef struct __va_list_tag {"
Eli Friedmane4277982008-08-20 23:11:40 +0000271 " unsigned char gpr;"
272 " unsigned char fpr;"
273 " unsigned short reserved;"
274 " void* overflow_arg_area;"
275 " void* reg_save_area;"
Chris Lattnerd5998502008-10-27 01:11:29 +0000276 "} __builtin_va_list[1];";*/
Anders Carlsson3346ae62007-11-24 23:38:12 +0000277 }
Eli Friedmane4277982008-08-20 23:11:40 +0000278 virtual const char *getTargetPrefix() const {
279 return "ppc";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000280 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000281 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedmane4277982008-08-20 23:11:40 +0000282 unsigned &NumNames) const;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000283 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Eli Friedmane4277982008-08-20 23:11:40 +0000284 unsigned &NumAliases) const;
Anders Carlsson066d2ea2009-02-28 17:11:49 +0000285 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattner44def072009-04-26 07:16:29 +0000286 TargetInfo::ConstraintInfo &Info) const {
Anders Carlsson066d2ea2009-02-28 17:11:49 +0000287 switch (*Name) {
Anders Carlssond04c6e22007-11-27 04:11:28 +0000288 default: return false;
289 case 'O': // Zero
290 return true;
291 case 'b': // Base register
292 case 'f': // Floating point register
Chris Lattner44def072009-04-26 07:16:29 +0000293 Info.setAllowsRegister();
Anders Carlssond04c6e22007-11-27 04:11:28 +0000294 return true;
295 }
296 }
Eli Friedmane4277982008-08-20 23:11:40 +0000297 virtual const char *getClobbers() const {
298 return "";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000299 }
Eli Friedmane4277982008-08-20 23:11:40 +0000300};
Anders Carlssond04c6e22007-11-27 04:11:28 +0000301
Eli Friedmane4277982008-08-20 23:11:40 +0000302const Builtin::Info PPCTargetInfo::BuiltinInfo[] = {
Douglas Gregorb1152d82009-02-16 21:58:21 +0000303#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false },
304#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false },
Eli Friedmane4277982008-08-20 23:11:40 +0000305#include "clang/AST/PPCBuiltins.def"
306};
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000307
308
Chris Lattnerc0f59212009-03-02 22:27:17 +0000309/// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific
310/// #defines that are not tied to a specific subtarget.
Chris Lattner33328642009-03-20 15:52:06 +0000311void PPCTargetInfo::getTargetDefines(const LangOptions &Opts,
312 std::vector<char> &Defs) const {
Chris Lattnerc0f59212009-03-02 22:27:17 +0000313 // Target identification.
314 Define(Defs, "__ppc__");
315 Define(Defs, "_ARCH_PPC");
316 Define(Defs, "__POWERPC__");
317 if (PointerWidth == 64) {
318 Define(Defs, "_ARCH_PPC64");
319 Define(Defs, "_LP64");
320 Define(Defs, "__LP64__");
321 Define(Defs, "__ppc64__");
322 } else {
323 Define(Defs, "__ppc__");
324 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000325
Chris Lattnerc0f59212009-03-02 22:27:17 +0000326 // Target properties.
327 Define(Defs, "_BIG_ENDIAN");
328 Define(Defs, "__BIG_ENDIAN__");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000329
Chris Lattnerc0f59212009-03-02 22:27:17 +0000330 // Subtarget options.
331 Define(Defs, "__NATURAL_ALIGNMENT__");
332 Define(Defs, "__REGISTER_PREFIX__", "");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000333
Chris Lattnerc0f59212009-03-02 22:27:17 +0000334 // FIXME: Should be controlled by command line option.
335 Define(Defs, "__LONG_DOUBLE_128__");
336}
337
Chris Lattner393ff042008-04-21 18:56:49 +0000338
Eli Friedmane4277982008-08-20 23:11:40 +0000339const char * const PPCTargetInfo::GCCRegNames[] = {
340 "0", "1", "2", "3", "4", "5", "6", "7",
341 "8", "9", "10", "11", "12", "13", "14", "15",
342 "16", "17", "18", "19", "20", "21", "22", "23",
343 "24", "25", "26", "27", "28", "29", "30", "31",
344 "0", "1", "2", "3", "4", "5", "6", "7",
345 "8", "9", "10", "11", "12", "13", "14", "15",
346 "16", "17", "18", "19", "20", "21", "22", "23",
347 "24", "25", "26", "27", "28", "29", "30", "31",
348 "mq", "lr", "ctr", "ap",
349 "0", "1", "2", "3", "4", "5", "6", "7",
350 "xer",
351 "0", "1", "2", "3", "4", "5", "6", "7",
352 "8", "9", "10", "11", "12", "13", "14", "15",
353 "16", "17", "18", "19", "20", "21", "22", "23",
354 "24", "25", "26", "27", "28", "29", "30", "31",
355 "vrsave", "vscr",
356 "spe_acc", "spefscr",
357 "sfp"
358};
Reid Spencer5f016e22007-07-11 17:01:13 +0000359
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000360void PPCTargetInfo::getGCCRegNames(const char * const *&Names,
Eli Friedmane4277982008-08-20 23:11:40 +0000361 unsigned &NumNames) const {
362 Names = GCCRegNames;
363 NumNames = llvm::array_lengthof(GCCRegNames);
364}
Reid Spencer5f016e22007-07-11 17:01:13 +0000365
Eli Friedmane4277982008-08-20 23:11:40 +0000366const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = {
367 // While some of these aliases do map to different registers
368 // they still share the same register name.
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000369 { { "cc", "cr0", "fr0", "r0", "v0"}, "0" },
370 { { "cr1", "fr1", "r1", "sp", "v1"}, "1" },
371 { { "cr2", "fr2", "r2", "toc", "v2"}, "2" },
372 { { "cr3", "fr3", "r3", "v3"}, "3" },
373 { { "cr4", "fr4", "r4", "v4"}, "4" },
374 { { "cr5", "fr5", "r5", "v5"}, "5" },
375 { { "cr6", "fr6", "r6", "v6"}, "6" },
376 { { "cr7", "fr7", "r7", "v7"}, "7" },
377 { { "fr8", "r8", "v8"}, "8" },
378 { { "fr9", "r9", "v9"}, "9" },
379 { { "fr10", "r10", "v10"}, "10" },
380 { { "fr11", "r11", "v11"}, "11" },
381 { { "fr12", "r12", "v12"}, "12" },
382 { { "fr13", "r13", "v13"}, "13" },
383 { { "fr14", "r14", "v14"}, "14" },
384 { { "fr15", "r15", "v15"}, "15" },
385 { { "fr16", "r16", "v16"}, "16" },
386 { { "fr17", "r17", "v17"}, "17" },
387 { { "fr18", "r18", "v18"}, "18" },
388 { { "fr19", "r19", "v19"}, "19" },
389 { { "fr20", "r20", "v20"}, "20" },
390 { { "fr21", "r21", "v21"}, "21" },
391 { { "fr22", "r22", "v22"}, "22" },
392 { { "fr23", "r23", "v23"}, "23" },
393 { { "fr24", "r24", "v24"}, "24" },
394 { { "fr25", "r25", "v25"}, "25" },
395 { { "fr26", "r26", "v26"}, "26" },
396 { { "fr27", "r27", "v27"}, "27" },
397 { { "fr28", "r28", "v28"}, "28" },
398 { { "fr29", "r29", "v29"}, "29" },
399 { { "fr30", "r30", "v30"}, "30" },
400 { { "fr31", "r31", "v31"}, "31" },
Eli Friedmane4277982008-08-20 23:11:40 +0000401};
402
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000403void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
Eli Friedmane4277982008-08-20 23:11:40 +0000404 unsigned &NumAliases) const {
405 Aliases = GCCRegAliases;
406 NumAliases = llvm::array_lengthof(GCCRegAliases);
407}
408} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +0000409
410namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000411class PPC32TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000412public:
Eli Friedmaned855cb2008-08-21 00:13:15 +0000413 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
414 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
415 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
416 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000417};
418} // end anonymous namespace.
419
420namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000421class PPC64TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000422public:
Eli Friedmane4277982008-08-20 23:11:40 +0000423 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000424 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000425 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
426 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
Chris Lattnerf291b102008-05-09 06:17:04 +0000427 }
Eli Friedmane4277982008-08-20 23:11:40 +0000428};
429} // end anonymous namespace.
430
Chris Lattnerae0ee032008-12-04 23:20:07 +0000431
Eli Friedmane4277982008-08-20 23:11:40 +0000432namespace {
433class DarwinPPCTargetInfo : public PPC32TargetInfo {
434public:
435 DarwinPPCTargetInfo(const std::string& triple) : PPC32TargetInfo(triple) {}
Chris Lattner33328642009-03-20 15:52:06 +0000436 virtual void getTargetDefines(const LangOptions &Opts,
437 std::vector<char> &Defines) const {
438 PPC32TargetInfo::getTargetDefines(Opts, Defines);
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000439 getDarwinDefines(Defines, Opts);
440 getDarwinOSXDefines(Defines, getTargetTriple());
Reid Spencer5f016e22007-07-11 17:01:13 +0000441 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000442
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000443 /// getDefaultLangOptions - Allow the target to specify default settings for
444 /// various language options. These may be overridden by command line
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000445 /// options.
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000446 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000447 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000448 }
Eli Friedmane4277982008-08-20 23:11:40 +0000449};
450} // end anonymous namespace.
451
452namespace {
453class DarwinPPC64TargetInfo : public PPC64TargetInfo {
454public:
455 DarwinPPC64TargetInfo(const std::string& triple) : PPC64TargetInfo(triple) {}
Chris Lattner33328642009-03-20 15:52:06 +0000456 virtual void getTargetDefines(const LangOptions &Opts,
457 std::vector<char> &Defines) const {
458 PPC64TargetInfo::getTargetDefines(Opts, Defines);
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000459 getDarwinDefines(Defines, Opts);
460 getDarwinOSXDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +0000461 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000462
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000463 /// getDefaultLangOptions - Allow the target to specify default settings for
464 /// various language options. These may be overridden by command line
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000465 /// options.
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000466 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000467 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000468 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000469};
470} // end anonymous namespace.
471
472namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000473// Namespace for x86 abstract base class
474const Builtin::Info BuiltinInfo[] = {
Douglas Gregorb1152d82009-02-16 21:58:21 +0000475#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false },
476#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false },
Eli Friedman618234a2008-08-20 02:34:37 +0000477#include "clang/AST/X86Builtins.def"
478};
Eli Friedman61538a72008-05-20 14:21:01 +0000479
Eli Friedman618234a2008-08-20 02:34:37 +0000480const char *GCCRegNames[] = {
481 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp",
482 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)",
483 "argp", "flags", "fspr", "dirflag", "frame",
484 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7",
485 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7",
486 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
487 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
488};
489
490const TargetInfo::GCCRegAlias GCCRegAliases[] = {
491 { { "al", "ah", "eax", "rax" }, "ax" },
492 { { "bl", "bh", "ebx", "rbx" }, "bx" },
493 { { "cl", "ch", "ecx", "rcx" }, "cx" },
494 { { "dl", "dh", "edx", "rdx" }, "dx" },
495 { { "esi", "rsi" }, "si" },
496 { { "edi", "rdi" }, "di" },
497 { { "esp", "rsp" }, "sp" },
498 { { "ebp", "rbp" }, "bp" },
499};
500
501// X86 target abstract base class; x86-32 and x86-64 are very close, so
502// most of the implementation can be shared.
503class X86TargetInfo : public TargetInfo {
Chris Lattner84f0ea82009-03-02 22:40:39 +0000504 enum X86SSEEnum {
505 NoMMXSSE, MMX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42
506 } SSELevel;
Eli Friedman618234a2008-08-20 02:34:37 +0000507public:
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000508 X86TargetInfo(const std::string& triple)
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000509 : TargetInfo(triple), SSELevel(NoMMXSSE) {
Eli Friedman618234a2008-08-20 02:34:37 +0000510 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended;
Reid Spencer5f016e22007-07-11 17:01:13 +0000511 }
512 virtual void getTargetBuiltins(const Builtin::Info *&Records,
513 unsigned &NumRecords) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000514 Records = BuiltinInfo;
515 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000516 }
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000517 virtual const char *getTargetPrefix() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000518 return "x86";
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000519 }
520 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedman618234a2008-08-20 02:34:37 +0000521 unsigned &NumNames) const {
522 Names = GCCRegNames;
523 NumNames = llvm::array_lengthof(GCCRegNames);
Anders Carlsson3346ae62007-11-24 23:38:12 +0000524 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000525 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Anders Carlsson3346ae62007-11-24 23:38:12 +0000526 unsigned &NumAliases) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000527 Aliases = GCCRegAliases;
528 NumAliases = llvm::array_lengthof(GCCRegAliases);
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000529 }
Anders Carlsson066d2ea2009-02-28 17:11:49 +0000530 virtual bool validateAsmConstraint(const char *&Name,
Eli Friedman618234a2008-08-20 02:34:37 +0000531 TargetInfo::ConstraintInfo &info) const;
532 virtual std::string convertConstraint(const char Constraint) const;
Anders Carlssond04c6e22007-11-27 04:11:28 +0000533 virtual const char *getClobbers() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000534 return "~{dirflag},~{fpsr},~{flags}";
535 }
Chris Lattner33328642009-03-20 15:52:06 +0000536 virtual void getTargetDefines(const LangOptions &Opts,
537 std::vector<char> &Defines) const;
Daniel Dunbar17ca3632009-05-06 21:07:50 +0000538 virtual bool setFeatureEnabled(llvm::StringMap<bool> &Features,
539 const std::string &Name,
540 bool Enabled) const;
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000541 virtual void getDefaultFeatures(const std::string &CPU,
Daniel Dunbar17ca3632009-05-06 21:07:50 +0000542 llvm::StringMap<bool> &Features) const;
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000543 virtual void HandleTargetFeatures(const llvm::StringMap<bool> &Features);
Reid Spencer5f016e22007-07-11 17:01:13 +0000544};
Chris Lattner3daed522009-03-02 22:20:04 +0000545
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000546void X86TargetInfo::getDefaultFeatures(const std::string &CPU,
Daniel Dunbar17ca3632009-05-06 21:07:50 +0000547 llvm::StringMap<bool> &Features) const {
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000548 // FIXME: This should not be here.
549 Features["3dnow"] = false;
550 Features["3dnowa"] = false;
551 Features["mmx"] = false;
552 Features["sse"] = false;
553 Features["sse2"] = false;
554 Features["sse3"] = false;
555 Features["ssse3"] = false;
556 Features["sse41"] = false;
557 Features["sse42"] = false;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000558
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000559 // LLVM does not currently recognize this.
560 // Features["sse4a"] = false;
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000561
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000562 // FIXME: This *really* should not be here.
563
564 // X86_64 always has SSE2.
565 if (PointerWidth == 64)
566 Features["sse2"] = Features["sse"] = Features["mmx"] = true;
567
Daniel Dunbar3ac79042009-05-06 21:56:32 +0000568 if (CPU == "generic" || CPU == "i386" || CPU == "i486" || CPU == "i586" ||
569 CPU == "pentium" || CPU == "i686" || CPU == "pentiumpro")
570 ;
571 else if (CPU == "pentium-mmx" || CPU == "pentium2")
572 setFeatureEnabled(Features, "mmx", true);
573 else if (CPU == "pentium3")
574 setFeatureEnabled(Features, "sse", true);
575 else if (CPU == "pentium-m" || CPU == "pentium4" || CPU == "x86-64")
576 setFeatureEnabled(Features, "sse2", true);
577 else if (CPU == "yonah" || CPU == "prescott" || CPU == "nocona")
578 setFeatureEnabled(Features, "sse3", true);
579 else if (CPU == "core2")
580 setFeatureEnabled(Features, "ssse3", true);
581 else if (CPU == "penryn") {
582 setFeatureEnabled(Features, "sse4", true);
583 Features["sse42"] = false;
584 } else if (CPU == "atom")
585 setFeatureEnabled(Features, "sse3", true);
586 else if (CPU == "corei7")
587 setFeatureEnabled(Features, "sse4", true);
588 else if (CPU == "k6" || CPU == "winchip-c6")
589 setFeatureEnabled(Features, "mmx", true);
590 else if (CPU == "k6-2" || CPU == "k6-3" || CPU == "athlon" ||
591 CPU == "athlon-tbird" || CPU == "winchip2" || CPU == "c3") {
592 setFeatureEnabled(Features, "mmx", true);
593 setFeatureEnabled(Features, "3dnow", true);
594 } else if (CPU == "athlon-4" || CPU == "athlon-xp" || CPU == "athlon-mp") {
595 setFeatureEnabled(Features, "sse", true);
596 setFeatureEnabled(Features, "3dnowa", true);
597 } else if (CPU == "k8" || CPU == "opteron" || CPU == "athlon64" ||
598 CPU == "athlon-fx") {
599 setFeatureEnabled(Features, "sse2", true);
600 setFeatureEnabled(Features, "3dnowa", true);
601 } else if (CPU == "c3-2")
602 setFeatureEnabled(Features, "sse", true);
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000603}
604
Daniel Dunbar17ca3632009-05-06 21:07:50 +0000605bool X86TargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features,
606 const std::string &Name,
607 bool Enabled) const {
608 // FIXME: This *really* should not be here.
609 if (!Features.count(Name) && Name != "sse4")
610 return false;
611
612 if (Enabled) {
613 if (Name == "mmx")
614 Features["mmx"] = true;
615 else if (Name == "sse")
616 Features["mmx"] = Features["sse"] = true;
617 else if (Name == "sse2")
618 Features["mmx"] = Features["sse"] = Features["sse2"] = true;
619 else if (Name == "sse3")
620 Features["mmx"] = Features["sse"] = Features["sse2"] =
621 Features["sse3"] = true;
622 else if (Name == "ssse3")
623 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
624 Features["ssse3"] = true;
625 else if (Name == "sse4")
626 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
627 Features["ssse3"] = Features["sse41"] = Features["sse42"] = true;
628 else if (Name == "3dnow")
629 Features["3dnowa"] = true;
630 else if (Name == "3dnowa")
631 Features["3dnow"] = Features["3dnowa"] = true;
632 } else {
633 if (Name == "mmx")
634 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
635 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
636 else if (Name == "sse")
637 Features["sse"] = Features["sse2"] = Features["sse3"] =
638 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
639 else if (Name == "sse2")
640 Features["sse2"] = Features["sse3"] = Features["ssse3"] =
641 Features["sse41"] = Features["sse42"] = false;
642 else if (Name == "sse3")
643 Features["sse3"] = Features["ssse3"] = Features["sse41"] =
644 Features["sse42"] = false;
645 else if (Name == "ssse3")
646 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
647 else if (Name == "sse4")
648 Features["sse41"] = Features["sse42"] = false;
649 else if (Name == "3dnow")
650 Features["3dnow"] = Features["3dnowa"] = false;
651 else if (Name == "3dnowa")
652 Features["3dnowa"] = false;
653 }
654
655 return true;
656}
657
Daniel Dunbar868bd0a2009-05-06 03:16:41 +0000658/// HandleTargetOptions - Perform initialization based on the user
659/// configured set of features.
660void X86TargetInfo::HandleTargetFeatures(const llvm::StringMap<bool>&Features) {
661 if (Features.lookup("sse42"))
662 SSELevel = SSE42;
663 else if (Features.lookup("sse41"))
664 SSELevel = SSE41;
665 else if (Features.lookup("ssse3"))
666 SSELevel = SSSE3;
667 else if (Features.lookup("sse3"))
668 SSELevel = SSE3;
669 else if (Features.lookup("sse2"))
670 SSELevel = SSE2;
671 else if (Features.lookup("sse"))
672 SSELevel = SSE1;
673 else if (Features.lookup("mmx"))
674 SSELevel = MMX;
Chris Lattner3daed522009-03-02 22:20:04 +0000675}
Chris Lattnerc0f59212009-03-02 22:27:17 +0000676
677/// X86TargetInfo::getTargetDefines - Return a set of the X86-specific #defines
678/// that are not tied to a specific subtarget.
Chris Lattner33328642009-03-20 15:52:06 +0000679void X86TargetInfo::getTargetDefines(const LangOptions &Opts,
680 std::vector<char> &Defs) const {
Chris Lattnerc0f59212009-03-02 22:27:17 +0000681 // Target identification.
682 if (PointerWidth == 64) {
683 Define(Defs, "_LP64");
684 Define(Defs, "__LP64__");
685 Define(Defs, "__amd64__");
686 Define(Defs, "__amd64");
687 Define(Defs, "__x86_64");
688 Define(Defs, "__x86_64__");
Chris Lattnerc0f59212009-03-02 22:27:17 +0000689 } else {
Chris Lattnerca45cff2009-03-20 16:06:38 +0000690 DefineStd(Defs, "i386", Opts);
Chris Lattnerc0f59212009-03-02 22:27:17 +0000691 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000692
Chris Lattnerc0f59212009-03-02 22:27:17 +0000693 // Target properties.
694 Define(Defs, "__LITTLE_ENDIAN__");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000695
Chris Lattnerc0f59212009-03-02 22:27:17 +0000696 // Subtarget options.
697 Define(Defs, "__nocona");
698 Define(Defs, "__nocona__");
699 Define(Defs, "__tune_nocona__");
Chris Lattnerc0f59212009-03-02 22:27:17 +0000700 Define(Defs, "__REGISTER_PREFIX__", "");
Chris Lattner84f0ea82009-03-02 22:40:39 +0000701
Chris Lattner54175442009-04-19 17:32:33 +0000702 // Define __NO_MATH_INLINES on linux/x86 so that we don't get inline
703 // functions in glibc header files that use FP Stack inline asm which the
704 // backend can't deal with (PR879).
705 Define(Defs, "__NO_MATH_INLINES");
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000706
Chris Lattner84f0ea82009-03-02 22:40:39 +0000707 // Each case falls through to the previous one here.
708 switch (SSELevel) {
709 case SSE42:
710 Define(Defs, "__SSE4_2__");
711 case SSE41:
712 Define(Defs, "__SSE4_1__");
713 case SSSE3:
714 Define(Defs, "__SSSE3__");
715 case SSE3:
716 Define(Defs, "__SSE3__");
717 case SSE2:
718 Define(Defs, "__SSE2__");
719 Define(Defs, "__SSE2_MATH__"); // -mfp-math=sse always implied.
720 case SSE1:
721 Define(Defs, "__SSE__");
722 Define(Defs, "__SSE_MATH__"); // -mfp-math=sse always implied.
723 case MMX:
724 Define(Defs, "__MMX__");
725 case NoMMXSSE:
726 break;
727 }
Chris Lattnerc0f59212009-03-02 22:27:17 +0000728}
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000729
730
Eli Friedman618234a2008-08-20 02:34:37 +0000731bool
Anders Carlsson066d2ea2009-02-28 17:11:49 +0000732X86TargetInfo::validateAsmConstraint(const char *&Name,
Chris Lattner44def072009-04-26 07:16:29 +0000733 TargetInfo::ConstraintInfo &Info) const {
Anders Carlsson066d2ea2009-02-28 17:11:49 +0000734 switch (*Name) {
Eli Friedman618234a2008-08-20 02:34:37 +0000735 default: return false;
736 case 'a': // eax.
737 case 'b': // ebx.
738 case 'c': // ecx.
739 case 'd': // edx.
740 case 'S': // esi.
741 case 'D': // edi.
742 case 'A': // edx:eax.
743 case 't': // top of floating point stack.
744 case 'u': // second from top of floating point stack.
745 case 'q': // Any register accessible as [r]l: a, b, c, and d.
Anders Carlssonfce09342008-10-06 00:41:45 +0000746 case 'y': // Any MMX register.
Anders Carlssona7406d42008-10-06 19:17:39 +0000747 case 'x': // Any SSE register.
Eli Friedman618234a2008-08-20 02:34:37 +0000748 case 'Q': // Any register accessible as [r]h: a, b, c, and d.
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000749 case 'e': // 32-bit signed integer constant for use with zero-extending
Anders Carlsson79bc64c2009-01-24 18:03:09 +0000750 // x86_64 instructions.
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000751 case 'Z': // 32-bit unsigned integer constant for use with zero-extending
Anders Carlsson79bc64c2009-01-24 18:03:09 +0000752 // x86_64 instructions.
Eli Friedman618234a2008-08-20 02:34:37 +0000753 case 'N': // unsigned 8-bit integer constant for use with in and out
754 // instructions.
Chris Lattner44def072009-04-26 07:16:29 +0000755 Info.setAllowsRegister();
Eli Friedman618234a2008-08-20 02:34:37 +0000756 return true;
757 }
758}
759
760std::string
761X86TargetInfo::convertConstraint(const char Constraint) const {
762 switch (Constraint) {
763 case 'a': return std::string("{ax}");
764 case 'b': return std::string("{bx}");
765 case 'c': return std::string("{cx}");
766 case 'd': return std::string("{dx}");
767 case 'S': return std::string("{si}");
768 case 'D': return std::string("{di}");
769 case 't': // top of floating point stack.
770 return std::string("{st}");
771 case 'u': // second from top of floating point stack.
772 return std::string("{st(1)}"); // second from top of floating point stack.
773 default:
774 return std::string(1, Constraint);
775 }
776}
Eli Friedman618234a2008-08-20 02:34:37 +0000777} // end anonymous namespace
Reid Spencer5f016e22007-07-11 17:01:13 +0000778
779namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000780// X86-32 generic target
781class X86_32TargetInfo : public X86TargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000782public:
Eli Friedman618234a2008-08-20 02:34:37 +0000783 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
784 DoubleAlign = LongLongAlign = 32;
785 LongDoubleWidth = 96;
786 LongDoubleAlign = 32;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000787 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
788 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
789 "a0:0:64-f80:32:32";
Eli Friedman1afabd92009-03-29 20:31:09 +0000790 SizeType = UnsignedInt;
791 PtrDiffType = SignedInt;
792 IntPtrType = SignedInt;
Anton Korobeynikov264a76c2009-04-03 23:38:25 +0000793 RegParmMax = 3;
Eli Friedman618234a2008-08-20 02:34:37 +0000794 }
795 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000796 return "typedef char* __builtin_va_list;";
Eli Friedman618234a2008-08-20 02:34:37 +0000797 }
Eli Friedman618234a2008-08-20 02:34:37 +0000798};
799} // end anonymous namespace
800
801namespace {
802// x86-32 Darwin (OS X) target
803class DarwinI386TargetInfo : public X86_32TargetInfo {
804public:
805 DarwinI386TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
806 LongDoubleWidth = 128;
807 LongDoubleAlign = 128;
Eli Friedman1afabd92009-03-29 20:31:09 +0000808 SizeType = UnsignedLong;
809 IntPtrType = SignedLong;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000810 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
811 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
812 "a0:0:64-f80:128:128";
Eli Friedmanb030f022009-04-19 21:38:35 +0000813 TLSSupported = false;
Eli Friedman618234a2008-08-20 02:34:37 +0000814 }
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +0000815
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000816 virtual const char *getStringSymbolPrefix(bool IsConstant) const {
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +0000817 return IsConstant ? "\01LC" : "\01lC";
818 }
819
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000820 virtual const char *getUnicodeStringSymbolPrefix() const {
Daniel Dunbara9668e02009-04-03 00:57:44 +0000821 return "__utf16_string_";
822 }
823
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000824 virtual const char *getUnicodeStringSection() const {
Daniel Dunbara9668e02009-04-03 00:57:44 +0000825 return "__TEXT,__ustring";
826 }
827
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000828 virtual const char *getCFStringSymbolPrefix() const {
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +0000829 return "\01LC";
830 }
831
Chris Lattner33328642009-03-20 15:52:06 +0000832 virtual void getTargetDefines(const LangOptions &Opts,
833 std::vector<char> &Defines) const {
834 X86_32TargetInfo::getTargetDefines(Opts, Defines);
Daniel Dunbar8d33cd72009-04-10 19:52:24 +0000835 getDarwinDefines(Defines, Opts);
836 getDarwinOSXDefines(Defines, getTargetTriple());
Eli Friedman618234a2008-08-20 02:34:37 +0000837 }
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +0000838
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000839 /// getDefaultLangOptions - Allow the target to specify default settings for
840 /// various language options. These may be overridden by command line
Anton Korobeynikova7c47172009-05-03 13:42:53 +0000841 /// options.
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000842 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000843 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000844 }
Eli Friedman618234a2008-08-20 02:34:37 +0000845};
846} // end anonymous namespace
847
848namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000849// x86-32 FreeBSD target
850class FreeBSDX86_32TargetInfo : public X86_32TargetInfo {
851public:
Eli Friedmanf509d732008-11-02 02:43:55 +0000852 FreeBSDX86_32TargetInfo(const std::string& triple) :
Eli Friedman1afabd92009-03-29 20:31:09 +0000853 X86_32TargetInfo(triple) { }
Chris Lattner33328642009-03-20 15:52:06 +0000854 virtual void getTargetDefines(const LangOptions &Opts,
855 std::vector<char> &Defines) const {
856 X86_32TargetInfo::getTargetDefines(Opts, Defines);
Chris Lattner318ca712009-03-20 15:55:34 +0000857 getFreeBSDDefines(Opts, 0, getTargetTriple(), Defines);
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000858 }
859};
860} // end anonymous namespace
861
862namespace {
Chris Lattnereac7aee2008-08-23 18:23:14 +0000863// x86-32 DragonFly target
864class DragonFlyX86_32TargetInfo : public X86_32TargetInfo {
865public:
Eli Friedmanf509d732008-11-02 02:43:55 +0000866 DragonFlyX86_32TargetInfo(const std::string& triple) :
Eli Friedman1afabd92009-03-29 20:31:09 +0000867 X86_32TargetInfo(triple) { }
Chris Lattner33328642009-03-20 15:52:06 +0000868 virtual void getTargetDefines(const LangOptions &Opts,
869 std::vector<char> &Defines) const {
870 X86_32TargetInfo::getTargetDefines(Opts, Defines);
Chris Lattner318ca712009-03-20 15:55:34 +0000871 getDragonFlyDefines(Opts, Defines);
Chris Lattnereac7aee2008-08-23 18:23:14 +0000872 }
873};
874} // end anonymous namespace
875
876namespace {
Eli Friedman0d4047b2008-08-21 00:24:02 +0000877// x86-32 Linux target
878class LinuxX86_32TargetInfo : public X86_32TargetInfo {
879public:
880 LinuxX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000881 UserLabelPrefix = "";
Eli Friedman0d4047b2008-08-21 00:24:02 +0000882 }
Chris Lattner33328642009-03-20 15:52:06 +0000883 virtual void getTargetDefines(const LangOptions &Opts,
884 std::vector<char> &Defines) const {
885 X86_32TargetInfo::getTargetDefines(Opts, Defines);
Chris Lattner318ca712009-03-20 15:55:34 +0000886 getLinuxDefines(Opts, Defines);
Eli Friedman0d4047b2008-08-21 00:24:02 +0000887 }
888};
889} // end anonymous namespace
890
891namespace {
Douglas Gregor163a7c72009-05-21 23:51:30 +0000892// x86-32 Solaris target
893class SolarisX86_32TargetInfo : public X86_32TargetInfo {
894public:
895 SolarisX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
896 UserLabelPrefix = "";
Eli Friedman09c3a6d2009-05-22 01:12:57 +0000897 WCharType = SignedLong;
898 // FIXME: WIntType should be SignedLong
Douglas Gregor163a7c72009-05-21 23:51:30 +0000899 }
900 virtual void getTargetDefines(const LangOptions &Opts,
901 std::vector<char> &Defines) const {
902 X86_32TargetInfo::getTargetDefines(Opts, Defines);
903 getSolarisDefines(Opts, Defines);
904 }
905};
906} // end anonymous namespace
907
908
909namespace {
Eli Friedman29a30502008-08-21 01:40:19 +0000910// x86-32 Windows target
911class WindowsX86_32TargetInfo : public X86_32TargetInfo {
912public:
913 WindowsX86_32TargetInfo(const std::string& triple)
914 : X86_32TargetInfo(triple) {
Eli Friedmanb030f022009-04-19 21:38:35 +0000915 TLSSupported = false;
Eli Friedman29a30502008-08-21 01:40:19 +0000916 // FIXME: Fix wchar_t.
917 // FIXME: We should probably enable -fms-extensions by default for
918 // this target.
919 }
Chris Lattner33328642009-03-20 15:52:06 +0000920 virtual void getTargetDefines(const LangOptions &Opts,
921 std::vector<char> &Defines) const {
922 X86_32TargetInfo::getTargetDefines(Opts, Defines);
Eli Friedman29a30502008-08-21 01:40:19 +0000923 // This list is based off of the the list of things MingW defines
Eli Friedman29a30502008-08-21 01:40:19 +0000924 Define(Defines, "_WIN32");
Chris Lattnerca45cff2009-03-20 16:06:38 +0000925 DefineStd(Defines, "WIN32", Opts);
926 DefineStd(Defines, "WINNT", Opts);
Eli Friedman29a30502008-08-21 01:40:19 +0000927 Define(Defines, "_X86_");
928 Define(Defines, "__MSVCRT__");
929 }
930};
931} // end anonymous namespace
932
933namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000934// x86-64 generic target
935class X86_64TargetInfo : public X86TargetInfo {
936public:
Chris Lattner33328642009-03-20 15:52:06 +0000937 X86_64TargetInfo(const std::string &triple) : X86TargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000938 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Chris Lattner778601f2009-01-28 06:58:19 +0000939 DoubleAlign = LongLongAlign = 64;
Eli Friedman61538a72008-05-20 14:21:01 +0000940 LongDoubleWidth = 128;
941 LongDoubleAlign = 128;
Chris Lattner06ebe862009-02-05 07:32:46 +0000942 IntMaxType = SignedLong;
943 UIntMaxType = UnsignedLong;
Anton Korobeynikov264a76c2009-04-03 23:38:25 +0000944 RegParmMax = 6;
Chris Lattner06ebe862009-02-05 07:32:46 +0000945
Eli Friedmaned855cb2008-08-21 00:13:15 +0000946 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
947 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-"
948 "a0:0:64-f80:128:128";
Reid Spencer5f016e22007-07-11 17:01:13 +0000949 }
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000950 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000951 return "typedef struct __va_list_tag {"
952 " unsigned gp_offset;"
953 " unsigned fp_offset;"
954 " void* overflow_arg_area;"
955 " void* reg_save_area;"
956 "} __builtin_va_list[1];";
Anders Carlsson3346ae62007-11-24 23:38:12 +0000957 }
Eli Friedman618234a2008-08-20 02:34:37 +0000958};
959} // end anonymous namespace
960
961namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000962// x86-64 FreeBSD target
963class FreeBSDX86_64TargetInfo : public X86_64TargetInfo {
964public:
Chris Lattner33328642009-03-20 15:52:06 +0000965 FreeBSDX86_64TargetInfo(const std::string &triple)
966 : X86_64TargetInfo(triple) {}
967 virtual void getTargetDefines(const LangOptions &Opts,
968 std::vector<char> &Defines) const {
969 X86_64TargetInfo::getTargetDefines(Opts, Defines);
Chris Lattner318ca712009-03-20 15:55:34 +0000970 getFreeBSDDefines(Opts, 1, getTargetTriple(), Defines);
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000971 }
972};
973} // end anonymous namespace
974
975namespace {
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000976// x86-64 Linux target
977class LinuxX86_64TargetInfo : public X86_64TargetInfo {
978public:
979 LinuxX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000980 UserLabelPrefix = "";
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000981 }
Chris Lattner33328642009-03-20 15:52:06 +0000982 virtual void getTargetDefines(const LangOptions &Opts,
983 std::vector<char> &Defines) const {
984 X86_64TargetInfo::getTargetDefines(Opts, Defines);
Chris Lattner318ca712009-03-20 15:55:34 +0000985 getLinuxDefines(Opts, Defines);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000986 }
987};
988} // end anonymous namespace
989
990namespace {
Douglas Gregor163a7c72009-05-21 23:51:30 +0000991// x86-64 Solaris target
992class SolarisX86_64TargetInfo : public X86_64TargetInfo {
993public:
994 SolarisX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
995 UserLabelPrefix = "";
Douglas Gregor163a7c72009-05-21 23:51:30 +0000996 }
997 virtual void getTargetDefines(const LangOptions &Opts,
998 std::vector<char> &Defines) const {
999 X86_64TargetInfo::getTargetDefines(Opts, Defines);
1000 getSolarisDefines(Opts, Defines);
1001 }
1002};
1003} // end anonymous namespace
1004
1005namespace {
Eli Friedman618234a2008-08-20 02:34:37 +00001006// x86-64 Darwin (OS X) target
1007class DarwinX86_64TargetInfo : public X86_64TargetInfo {
1008public:
Eli Friedmanb030f022009-04-19 21:38:35 +00001009 DarwinX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
1010 TLSSupported = false;
1011 }
Eli Friedman618234a2008-08-20 02:34:37 +00001012
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001013 virtual const char *getStringSymbolPrefix(bool IsConstant) const {
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +00001014 return IsConstant ? "\01LC" : "\01lC";
1015 }
1016
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001017 virtual const char *getUnicodeStringSymbolPrefix() const {
Daniel Dunbara9668e02009-04-03 00:57:44 +00001018 return "__utf16_string_";
1019 }
1020
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001021 virtual const char *getUnicodeStringSection() const {
Daniel Dunbara9668e02009-04-03 00:57:44 +00001022 return "__TEXT,__ustring";
1023 }
1024
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001025 virtual const char *getCFStringSymbolPrefix() const {
Daniel Dunbar8e5c2b82009-03-31 23:42:16 +00001026 return "\01L_unnamed_cfstring_";
1027 }
1028
Chris Lattner33328642009-03-20 15:52:06 +00001029 virtual void getTargetDefines(const LangOptions &Opts,
1030 std::vector<char> &Defines) const {
1031 X86_64TargetInfo::getTargetDefines(Opts, Defines);
Daniel Dunbar8d33cd72009-04-10 19:52:24 +00001032 getDarwinDefines(Defines, Opts);
1033 getDarwinOSXDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +00001034 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +00001035
Chris Lattner8fc4dfb2008-12-04 22:54:33 +00001036 /// getDefaultLangOptions - Allow the target to specify default settings for
1037 /// various language options. These may be overridden by command line
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001038 /// options.
Chris Lattner8fc4dfb2008-12-04 22:54:33 +00001039 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +00001040 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +00001041 }
Reid Spencer5f016e22007-07-11 17:01:13 +00001042};
1043} // end anonymous namespace.
1044
Chris Lattner393ff042008-04-21 18:56:49 +00001045namespace {
Eli Friedmana9f54962008-08-20 07:44:10 +00001046class ARMTargetInfo : public TargetInfo {
Mike Stump437bb4b2009-04-08 02:07:04 +00001047 enum {
1048 Armv4t,
1049 Armv5,
1050 Armv6,
1051 XScale
1052 } ArmArch;
Chris Lattner393ff042008-04-21 18:56:49 +00001053public:
Eli Friedmana9f54962008-08-20 07:44:10 +00001054 ARMTargetInfo(const std::string& triple) : TargetInfo(triple) {
1055 // FIXME: Are the defaults correct for ARM?
Eli Friedmaned855cb2008-08-21 00:13:15 +00001056 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1057 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:64";
Chris Lattner5b37dc02009-04-23 04:22:04 +00001058 if (triple.find("arm-") == 0 || triple.find("armv6-") == 0)
Mike Stump437bb4b2009-04-08 02:07:04 +00001059 ArmArch = Armv6;
Chris Lattner5b37dc02009-04-23 04:22:04 +00001060 else if (triple.find("armv5-") == 0)
Mike Stump437bb4b2009-04-08 02:07:04 +00001061 ArmArch = Armv5;
Chris Lattner5b37dc02009-04-23 04:22:04 +00001062 else if (triple.find("armv4t-") == 0)
Mike Stump437bb4b2009-04-08 02:07:04 +00001063 ArmArch = Armv4t;
Chris Lattner5b37dc02009-04-23 04:22:04 +00001064 else if (triple.find("xscale-") == 0)
Mike Stump437bb4b2009-04-08 02:07:04 +00001065 ArmArch = XScale;
Chris Lattner5b37dc02009-04-23 04:22:04 +00001066 else if (triple.find("armv") == 0) {
1067 // FIXME: fuzzy match for other random weird arm triples. This is useful
1068 // for the static analyzer and other clients, but probably should be
1069 // re-evaluated when codegen is brought up.
1070 ArmArch = Armv6;
1071 }
Eli Friedman61538a72008-05-20 14:21:01 +00001072 }
Chris Lattner33328642009-03-20 15:52:06 +00001073 virtual void getTargetDefines(const LangOptions &Opts,
1074 std::vector<char> &Defs) const {
Chris Lattnerc0f59212009-03-02 22:27:17 +00001075 // Target identification.
1076 Define(Defs, "__arm");
1077 Define(Defs, "__arm__");
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001078
Chris Lattnerc0f59212009-03-02 22:27:17 +00001079 // Target properties.
1080 Define(Defs, "__LITTLE_ENDIAN__");
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001081
Mike Stump437bb4b2009-04-08 02:07:04 +00001082 // Subtarget options.
1083 if (ArmArch == Armv6) {
1084 Define(Defs, "__ARM_ARCH_6K__");
1085 Define(Defs, "__THUMB_INTERWORK__");
1086 } else if (ArmArch == Armv5) {
1087 Define(Defs, "__ARM_ARCH_5TEJ__");
1088 Define(Defs, "__THUMB_INTERWORK__");
1089 Define(Defs, "__SOFTFP__");
1090 } else if (ArmArch == Armv4t) {
1091 Define(Defs, "__ARM_ARCH_4T__");
1092 Define(Defs, "__SOFTFP__");
1093 } else if (ArmArch == XScale) {
1094 Define(Defs, "__ARM_ARCH_5TE__");
1095 Define(Defs, "__XSCALE__");
1096 Define(Defs, "__SOFTFP__");
1097 }
Chris Lattnerc0f59212009-03-02 22:27:17 +00001098 Define(Defs, "__ARMEL__");
Eli Friedman19262422009-05-29 19:00:15 +00001099 Define(Defs, "__APCS_32__");
1100 Define(Defs, "__VFP_FP__");
Chris Lattner393ff042008-04-21 18:56:49 +00001101 }
1102 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1103 unsigned &NumRecords) const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001104 // FIXME: Implement.
1105 Records = 0;
Chris Lattner393ff042008-04-21 18:56:49 +00001106 NumRecords = 0;
1107 }
1108 virtual const char *getVAListDeclaration() const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001109 return "typedef char* __builtin_va_list;";
Chris Lattner393ff042008-04-21 18:56:49 +00001110 }
1111 virtual const char *getTargetPrefix() const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001112 return "arm";
Chris Lattner393ff042008-04-21 18:56:49 +00001113 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001114 virtual void getGCCRegNames(const char * const *&Names,
Chris Lattner393ff042008-04-21 18:56:49 +00001115 unsigned &NumNames) const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001116 // FIXME: Implement.
1117 Names = 0;
Chris Lattner393ff042008-04-21 18:56:49 +00001118 NumNames = 0;
1119 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001120 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattner393ff042008-04-21 18:56:49 +00001121 unsigned &NumAliases) const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001122 // FIXME: Implement.
1123 Aliases = 0;
Chris Lattner393ff042008-04-21 18:56:49 +00001124 NumAliases = 0;
1125 }
Anders Carlsson066d2ea2009-02-28 17:11:49 +00001126 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattner44def072009-04-26 07:16:29 +00001127 TargetInfo::ConstraintInfo &Info) const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001128 // FIXME: Check if this is complete
Anders Carlsson066d2ea2009-02-28 17:11:49 +00001129 switch (*Name) {
Eli Friedmana9f54962008-08-20 07:44:10 +00001130 default:
Nate Begemanad487f42008-04-22 05:03:19 +00001131 case 'l': // r0-r7
1132 case 'h': // r8-r15
1133 case 'w': // VFP Floating point register single precision
1134 case 'P': // VFP Floating point register double precision
Chris Lattner44def072009-04-26 07:16:29 +00001135 Info.setAllowsRegister();
Nate Begemanad487f42008-04-22 05:03:19 +00001136 return true;
1137 }
Chris Lattner393ff042008-04-21 18:56:49 +00001138 return false;
1139 }
1140 virtual const char *getClobbers() const {
Eli Friedmana9f54962008-08-20 07:44:10 +00001141 // FIXME: Is this really right?
Chris Lattner393ff042008-04-21 18:56:49 +00001142 return "";
1143 }
1144};
1145} // end anonymous namespace.
1146
Eli Friedmana9f54962008-08-20 07:44:10 +00001147
1148namespace {
1149class DarwinARMTargetInfo : public ARMTargetInfo {
1150public:
Eli Friedmanb030f022009-04-19 21:38:35 +00001151 DarwinARMTargetInfo(const std::string& triple) : ARMTargetInfo(triple) {
1152 TLSSupported = false;
1153 }
Eli Friedmana9f54962008-08-20 07:44:10 +00001154
Chris Lattner33328642009-03-20 15:52:06 +00001155 virtual void getTargetDefines(const LangOptions &Opts,
1156 std::vector<char> &Defines) const {
1157 ARMTargetInfo::getTargetDefines(Opts, Defines);
Daniel Dunbar8d33cd72009-04-10 19:52:24 +00001158 getDarwinDefines(Defines, Opts);
1159 getDarwinIPhoneOSDefines(Defines, getTargetTriple());
Eli Friedmana9f54962008-08-20 07:44:10 +00001160 }
1161};
1162} // end anonymous namespace.
1163
Reid Spencer5f016e22007-07-11 17:01:13 +00001164namespace {
Daniel Dunbar1e0107a2009-03-23 16:09:04 +00001165// arm FreeBSD target
1166class FreeBSDARMTargetInfo : public ARMTargetInfo {
1167public:
1168 FreeBSDARMTargetInfo(const std::string& triple) : ARMTargetInfo(triple) {}
1169 virtual void getTargetDefines(const LangOptions &Opts,
1170 std::vector<char> &Defines) const {
1171 ARMTargetInfo::getTargetDefines(Opts, Defines);
1172 getFreeBSDDefines(Opts, 0, getTargetTriple(), Defines);
1173 }
1174};
1175} // end anonymous namespace
1176
1177namespace {
Eli Friedman01b86682008-08-20 07:28:14 +00001178class SparcV8TargetInfo : public TargetInfo {
Chris Lattnere957f532009-01-27 01:58:38 +00001179 static const TargetInfo::GCCRegAlias GCCRegAliases[];
1180 static const char * const GCCRegNames[];
Gabor Greif26658672008-02-21 16:29:08 +00001181public:
Eli Friedman01b86682008-08-20 07:28:14 +00001182 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) {
1183 // FIXME: Support Sparc quad-precision long double?
Eli Friedmaned855cb2008-08-21 00:13:15 +00001184 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1185 "i64:64:64-f32:32:32-f64:64:64-v64:64:64";
Eli Friedman01b86682008-08-20 07:28:14 +00001186 }
Chris Lattner33328642009-03-20 15:52:06 +00001187 virtual void getTargetDefines(const LangOptions &Opts,
1188 std::vector<char> &Defines) const {
Eli Friedman09c3a6d2009-05-22 01:12:57 +00001189 DefineStd(Defines, "sparc", Opts);
Gabor Greif26658672008-02-21 16:29:08 +00001190 Define(Defines, "__sparcv8");
Eli Friedman09c3a6d2009-05-22 01:12:57 +00001191 Define(Defines, "__REGISTER_PREFIX__", "");
Gabor Greif26658672008-02-21 16:29:08 +00001192 }
1193 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1194 unsigned &NumRecords) const {
Eli Friedman01b86682008-08-20 07:28:14 +00001195 // FIXME: Implement!
Gabor Greif26658672008-02-21 16:29:08 +00001196 }
1197 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +00001198 return "typedef void* __builtin_va_list;";
Gabor Greif26658672008-02-21 16:29:08 +00001199 }
1200 virtual const char *getTargetPrefix() const {
Eli Friedman01b86682008-08-20 07:28:14 +00001201 return "sparc";
Gabor Greif26658672008-02-21 16:29:08 +00001202 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001203 virtual void getGCCRegNames(const char * const *&Names,
Chris Lattnere957f532009-01-27 01:58:38 +00001204 unsigned &NumNames) const;
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001205 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattnere957f532009-01-27 01:58:38 +00001206 unsigned &NumAliases) const;
Anders Carlsson066d2ea2009-02-28 17:11:49 +00001207 virtual bool validateAsmConstraint(const char *&Name,
Gabor Greif26658672008-02-21 16:29:08 +00001208 TargetInfo::ConstraintInfo &info) const {
Eli Friedman01b86682008-08-20 07:28:14 +00001209 // FIXME: Implement!
1210 return false;
Gabor Greif26658672008-02-21 16:29:08 +00001211 }
1212 virtual const char *getClobbers() const {
Eli Friedman01b86682008-08-20 07:28:14 +00001213 // FIXME: Implement!
1214 return "";
Gabor Greif26658672008-02-21 16:29:08 +00001215 }
1216};
1217
Chris Lattnere957f532009-01-27 01:58:38 +00001218const char * const SparcV8TargetInfo::GCCRegNames[] = {
1219 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1220 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
1221 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
1222 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31"
1223};
1224
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001225void SparcV8TargetInfo::getGCCRegNames(const char * const *&Names,
Chris Lattnere957f532009-01-27 01:58:38 +00001226 unsigned &NumNames) const {
1227 Names = GCCRegNames;
1228 NumNames = llvm::array_lengthof(GCCRegNames);
1229}
1230
1231const TargetInfo::GCCRegAlias SparcV8TargetInfo::GCCRegAliases[] = {
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001232 { { "g0" }, "r0" },
1233 { { "g1" }, "r1" },
1234 { { "g2" }, "r2" },
1235 { { "g3" }, "r3" },
1236 { { "g4" }, "r4" },
1237 { { "g5" }, "r5" },
1238 { { "g6" }, "r6" },
1239 { { "g7" }, "r7" },
1240 { { "o0" }, "r8" },
1241 { { "o1" }, "r9" },
1242 { { "o2" }, "r10" },
1243 { { "o3" }, "r11" },
1244 { { "o4" }, "r12" },
1245 { { "o5" }, "r13" },
1246 { { "o6", "sp" }, "r14" },
1247 { { "o7" }, "r15" },
1248 { { "l0" }, "r16" },
1249 { { "l1" }, "r17" },
1250 { { "l2" }, "r18" },
1251 { { "l3" }, "r19" },
1252 { { "l4" }, "r20" },
1253 { { "l5" }, "r21" },
1254 { { "l6" }, "r22" },
1255 { { "l7" }, "r23" },
1256 { { "i0" }, "r24" },
1257 { { "i1" }, "r25" },
1258 { { "i2" }, "r26" },
1259 { { "i3" }, "r27" },
1260 { { "i4" }, "r28" },
1261 { { "i5" }, "r29" },
1262 { { "i6", "fp" }, "r30" },
1263 { { "i7" }, "r31" },
Chris Lattnere957f532009-01-27 01:58:38 +00001264};
1265
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001266void SparcV8TargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattnere957f532009-01-27 01:58:38 +00001267 unsigned &NumAliases) const {
1268 Aliases = GCCRegAliases;
1269 NumAliases = llvm::array_lengthof(GCCRegAliases);
1270}
Gabor Greif26658672008-02-21 16:29:08 +00001271} // end anonymous namespace.
1272
Eli Friedman01b86682008-08-20 07:28:14 +00001273namespace {
1274class SolarisSparcV8TargetInfo : public SparcV8TargetInfo {
1275public:
1276 SolarisSparcV8TargetInfo(const std::string& triple) :
Eli Friedmanf509d732008-11-02 02:43:55 +00001277 SparcV8TargetInfo(triple) {
1278 SizeType = UnsignedInt;
1279 PtrDiffType = SignedInt;
Eli Friedman09c3a6d2009-05-22 01:12:57 +00001280 WCharType = SignedLong;
1281 // FIXME: WIntType should be SignedLong
1282 UserLabelPrefix = "";
Eli Friedmanf509d732008-11-02 02:43:55 +00001283 }
Eli Friedman01b86682008-08-20 07:28:14 +00001284
Chris Lattner33328642009-03-20 15:52:06 +00001285 virtual void getTargetDefines(const LangOptions &Opts,
1286 std::vector<char> &Defines) const {
1287 SparcV8TargetInfo::getTargetDefines(Opts, Defines);
Douglas Gregor163a7c72009-05-21 23:51:30 +00001288 getSolarisDefines(Opts, Defines);
Eli Friedman01b86682008-08-20 07:28:14 +00001289 }
1290};
1291} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +00001292
Chris Lattner2621fd12008-05-08 05:58:21 +00001293namespace {
1294 class PIC16TargetInfo : public TargetInfo{
1295 public:
1296 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) {
Eli Friedmanb030f022009-04-19 21:38:35 +00001297 TLSSupported = false;
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +00001298 IntWidth = 16;
1299 LongWidth = LongLongWidth = 32;
Eli Friedman3f7a5312009-05-16 23:30:57 +00001300 IntMaxTWidth = 32;
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +00001301 PointerWidth = 16;
1302 IntAlign = 8;
1303 LongAlign = LongLongAlign = 8;
Eli Friedman61538a72008-05-20 14:21:01 +00001304 PointerAlign = 8;
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +00001305 SizeType = UnsignedInt;
1306 IntMaxType = SignedLong;
1307 UIntMaxType = UnsignedLong;
Chris Lattner6ad474f2009-02-13 22:28:55 +00001308 IntPtrType = SignedShort;
Eli Friedmanf509d732008-11-02 02:43:55 +00001309 PtrDiffType = SignedInt;
Sanjiv Gupta9eb4cef2009-06-02 04:43:46 +00001310 FloatWidth = 32;
1311 FloatAlign = 32;
1312 DoubleWidth = 32;
1313 DoubleAlign = 32;
1314 LongDoubleWidth = 32;
1315 LongDoubleAlign = 32;
1316 FloatFormat = &llvm::APFloat::IEEEsingle;
1317 DoubleFormat = &llvm::APFloat::IEEEsingle;
1318 LongDoubleFormat = &llvm::APFloat::IEEEsingle;
1319 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8-f32:32:32";
1320
Chris Lattner2621fd12008-05-08 05:58:21 +00001321 }
Chris Lattner927686f2008-05-09 06:08:39 +00001322 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; }
1323 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; }
Chris Lattner33328642009-03-20 15:52:06 +00001324 virtual void getTargetDefines(const LangOptions &Opts,
1325 std::vector<char> &Defines) const {
Chris Lattner2621fd12008-05-08 05:58:21 +00001326 Define(Defines, "__pic16");
1327 }
1328 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1329 unsigned &NumRecords) const {}
1330 virtual const char *getVAListDeclaration() const { return "";}
1331 virtual const char *getClobbers() const {return "";}
Sanjiv Gupta70aa5f92009-04-21 06:01:16 +00001332 virtual const char *getTargetPrefix() const {return "pic16";}
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001333 virtual void getGCCRegNames(const char * const *&Names,
1334 unsigned &NumNames) const {}
1335 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattner2621fd12008-05-08 05:58:21 +00001336 TargetInfo::ConstraintInfo &info) const {
1337 return true;
1338 }
Anton Korobeynikova7c47172009-05-03 13:42:53 +00001339 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattner2621fd12008-05-08 05:58:21 +00001340 unsigned &NumAliases) const {}
1341 virtual bool useGlobalsForAutomaticVariables() const {return true;}
1342 };
1343}
1344
Anton Korobeynikov73c64e52009-05-03 13:43:08 +00001345namespace {
1346 class MSP430TargetInfo : public TargetInfo {
1347 static const char * const GCCRegNames[];
1348 public:
1349 MSP430TargetInfo(const std::string& triple) : TargetInfo(triple) {
1350 TLSSupported = false;
1351 IntWidth = 16;
1352 LongWidth = LongLongWidth = 32;
Eli Friedman3f7a5312009-05-16 23:30:57 +00001353 IntMaxTWidth = 32;
Anton Korobeynikov73c64e52009-05-03 13:43:08 +00001354 PointerWidth = 16;
1355 IntAlign = 8;
1356 LongAlign = LongLongAlign = 8;
1357 PointerAlign = 8;
1358 SizeType = UnsignedInt;
1359 IntMaxType = SignedLong;
1360 UIntMaxType = UnsignedLong;
1361 IntPtrType = SignedShort;
1362 PtrDiffType = SignedInt;
1363 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8";
1364 }
1365 virtual void getTargetDefines(const LangOptions &Opts,
1366 std::vector<char> &Defines) const {
1367 Define(Defines, "MSP430");
1368 Define(Defines, "__MSP430__");
1369 // FIXME: defines for different 'flavours' of MCU
1370 }
1371 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1372 unsigned &NumRecords) const {
1373 // FIXME: Implement.
1374 Records = 0;
1375 NumRecords = 0;
1376 }
1377 virtual const char *getTargetPrefix() const {
1378 return "msp430";
1379 }
1380 virtual void getGCCRegNames(const char * const *&Names,
1381 unsigned &NumNames) const;
1382 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1383 unsigned &NumAliases) const {
1384 // No aliases.
1385 Aliases = 0;
1386 NumAliases = 0;
1387 }
1388 virtual bool validateAsmConstraint(const char *&Name,
1389 TargetInfo::ConstraintInfo &info) const {
1390 // FIXME: implement
1391 return true;
1392 }
1393 virtual const char *getClobbers() const {
1394 // FIXME: Is this really right?
1395 return "";
1396 }
1397 virtual const char *getVAListDeclaration() const {
1398 // FIXME: implement
Anton Korobeynikoveb716852009-05-08 18:24:57 +00001399 return "typedef char* __builtin_va_list;";
Anton Korobeynikov73c64e52009-05-03 13:43:08 +00001400 }
1401 };
1402
1403 const char * const MSP430TargetInfo::GCCRegNames[] = {
1404 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1405 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
1406 };
1407
1408 void MSP430TargetInfo::getGCCRegNames(const char * const *&Names,
1409 unsigned &NumNames) const {
1410 Names = GCCRegNames;
1411 NumNames = llvm::array_lengthof(GCCRegNames);
1412 }
1413}
1414
1415
Reid Spencer5f016e22007-07-11 17:01:13 +00001416//===----------------------------------------------------------------------===//
1417// Driver code
1418//===----------------------------------------------------------------------===//
1419
Ted Kremenek8448d382007-12-04 17:07:35 +00001420static inline bool IsX86(const std::string& TT) {
Ted Kremenekae360762007-12-03 22:06:55 +00001421 return (TT.size() >= 5 && TT[0] == 'i' && TT[2] == '8' && TT[3] == '6' &&
1422 TT[4] == '-' && TT[1] - '3' < 6);
1423}
1424
Chris Lattner42e67372008-03-05 01:18:20 +00001425/// CreateTargetInfo - Return the target info object for the specified target
1426/// triple.
1427TargetInfo* TargetInfo::CreateTargetInfo(const std::string &T) {
Eli Friedmaned855cb2008-08-21 00:13:15 +00001428 // OS detection; this isn't really anywhere near complete.
1429 // Additions and corrections are welcome.
1430 bool isDarwin = T.find("-darwin") != std::string::npos;
Chris Lattnereac7aee2008-08-23 18:23:14 +00001431 bool isDragonFly = T.find("-dragonfly") != std::string::npos;
Chris Lattnerfd0269d2008-10-16 17:04:31 +00001432 bool isFreeBSD = T.find("-freebsd") != std::string::npos;
Eli Friedmaned855cb2008-08-21 00:13:15 +00001433 bool isSolaris = T.find("-solaris") != std::string::npos;
1434 bool isLinux = T.find("-linux") != std::string::npos;
1435 bool isWindows = T.find("-windows") != std::string::npos ||
1436 T.find("-win32") != std::string::npos ||
1437 T.find("-mingw") != std::string::npos;
Eli Friedman61538a72008-05-20 14:21:01 +00001438
Eli Friedmaned855cb2008-08-21 00:13:15 +00001439 if (T.find("ppc-") == 0 || T.find("powerpc-") == 0) {
1440 if (isDarwin)
1441 return new DarwinPPCTargetInfo(T);
1442 return new PPC32TargetInfo(T);
1443 }
Eli Friedman61538a72008-05-20 14:21:01 +00001444
Eli Friedmaned855cb2008-08-21 00:13:15 +00001445 if (T.find("ppc64-") == 0 || T.find("powerpc64-") == 0) {
1446 if (isDarwin)
1447 return new DarwinPPC64TargetInfo(T);
1448 return new PPC64TargetInfo(T);
1449 }
Chris Lattner393ff042008-04-21 18:56:49 +00001450
Chris Lattner5b37dc02009-04-23 04:22:04 +00001451 if (T.find("armv") == 0 || T.find("arm-") == 0 || T.find("xscale") == 0) {
Eli Friedmaned855cb2008-08-21 00:13:15 +00001452 if (isDarwin)
1453 return new DarwinARMTargetInfo(T);
Daniel Dunbar1e0107a2009-03-23 16:09:04 +00001454 if (isFreeBSD)
1455 return new FreeBSDARMTargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +00001456 return new ARMTargetInfo(T);
1457 }
Eli Friedman61538a72008-05-20 14:21:01 +00001458
Eli Friedmaned855cb2008-08-21 00:13:15 +00001459 if (T.find("sparc-") == 0) {
1460 if (isSolaris)
1461 return new SolarisSparcV8TargetInfo(T);
1462 return new SparcV8TargetInfo(T);
1463 }
1464
Chris Lattner54fefbe2009-02-20 17:04:14 +00001465 if (T.find("x86_64-") == 0 || T.find("amd64-") == 0) {
Eli Friedmaned855cb2008-08-21 00:13:15 +00001466 if (isDarwin)
1467 return new DarwinX86_64TargetInfo(T);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +00001468 if (isLinux)
1469 return new LinuxX86_64TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +00001470 if (isFreeBSD)
1471 return new FreeBSDX86_64TargetInfo(T);
Douglas Gregor163a7c72009-05-21 23:51:30 +00001472 if (isSolaris)
1473 return new SolarisX86_64TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +00001474 return new X86_64TargetInfo(T);
1475 }
Eli Friedman61538a72008-05-20 14:21:01 +00001476
Chris Lattner2621fd12008-05-08 05:58:21 +00001477 if (T.find("pic16-") == 0)
1478 return new PIC16TargetInfo(T);
1479
Anton Korobeynikov73c64e52009-05-03 13:43:08 +00001480 if (T.find("msp430-") == 0)
1481 return new MSP430TargetInfo(T);
1482
Eli Friedmaned855cb2008-08-21 00:13:15 +00001483 if (IsX86(T)) {
1484 if (isDarwin)
1485 return new DarwinI386TargetInfo(T);
Eli Friedman0d4047b2008-08-21 00:24:02 +00001486 if (isLinux)
1487 return new LinuxX86_32TargetInfo(T);
Chris Lattnereac7aee2008-08-23 18:23:14 +00001488 if (isDragonFly)
1489 return new DragonFlyX86_32TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +00001490 if (isFreeBSD)
1491 return new FreeBSDX86_32TargetInfo(T);
Douglas Gregor163a7c72009-05-21 23:51:30 +00001492 if (isSolaris)
1493 return new SolarisX86_32TargetInfo(T);
Eli Friedman29a30502008-08-21 01:40:19 +00001494 if (isWindows)
1495 return new WindowsX86_32TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +00001496 return new X86_32TargetInfo(T);
1497 }
Eli Friedman61538a72008-05-20 14:21:01 +00001498
Chris Lattner42e67372008-03-05 01:18:20 +00001499 return NULL;
Reid Spencer5f016e22007-07-11 17:01:13 +00001500}