blob: 9e81ed7db2fd5a11d3c3dcdc6707ca2335de4143 [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//
Ted Kremenekbbced582007-12-12 18:05:32 +000010// This file implements construction of a TargetInfo object from a
11// target triple.
Reid Spencer5f016e22007-07-11 17:01:13 +000012//
13//===----------------------------------------------------------------------===//
14
Reid Spencer5f016e22007-07-11 17:01:13 +000015#include "clang/AST/Builtins.h"
Anders Carlsson564f1de2007-12-09 23:17:02 +000016#include "clang/AST/TargetBuiltins.h"
Reid Spencer5f016e22007-07-11 17:01:13 +000017#include "clang/Basic/TargetInfo.h"
Chris Lattner8fc4dfb2008-12-04 22:54:33 +000018#include "clang/Basic/LangOptions.h"
Anders Carlsson3346ae62007-11-24 23:38:12 +000019#include "llvm/ADT/STLExtras.h"
Eli Friedman25531262008-05-20 14:27:34 +000020#include "llvm/ADT/APFloat.h"
Reid Spencer5f016e22007-07-11 17:01:13 +000021using namespace clang;
22
Reid Spencer5f016e22007-07-11 17:01:13 +000023//===----------------------------------------------------------------------===//
24// Common code shared among targets.
25//===----------------------------------------------------------------------===//
26
Chris Lattnerd15fa822007-10-06 06:57:34 +000027static void Define(std::vector<char> &Buf, const char *Macro,
28 const char *Val = "1") {
29 const char *Def = "#define ";
30 Buf.insert(Buf.end(), Def, Def+strlen(Def));
31 Buf.insert(Buf.end(), Macro, Macro+strlen(Macro));
32 Buf.push_back(' ');
33 Buf.insert(Buf.end(), Val, Val+strlen(Val));
34 Buf.push_back('\n');
35}
36
Chris Lattnerd29b6302008-10-05 21:50:58 +000037//===----------------------------------------------------------------------===//
38// Defines specific to certain operating systems.
39//===----------------------------------------------------------------------===//
40
Eli Friedman01b86682008-08-20 07:28:14 +000041static void getSolarisDefines(std::vector<char> &Defs) {
42 Define(Defs, "__SUN__");
43 Define(Defs, "__SOLARIS__");
44}
Reid Spencer5f016e22007-07-11 17:01:13 +000045
Nate Begemanca013422009-01-18 01:08:03 +000046static void getFreeBSDDefines(std::vector<char> &Defs, bool is64Bit,
47 const char *Triple) {
Chris Lattnerfd0269d2008-10-16 17:04:31 +000048 // FreeBSD defines; list based off of gcc output
49
50 const char *FreeBSD = strstr(Triple, "-freebsd");
51 FreeBSD += strlen("-freebsd");
52 char release[] = "X";
53 release[0] = FreeBSD[0];
54 char version[] = "X00001";
55 version[0] = FreeBSD[0];
56
57 Define(Defs, "__FreeBSD__", release);
58 Define(Defs, "__FreeBSD_cc_version", version);
59 Define(Defs, "__KPRINTF_ATTRIBUTE__");
60 Define(Defs, "unix");
61 Define(Defs, "bsd");
62 if (is64Bit) {
63 Define(Defs, "__LP64__");
64 }
65}
66
Chris Lattnerd29b6302008-10-05 21:50:58 +000067static void getDragonFlyDefines(std::vector<char> &Defs) {
68 // DragonFly defines; list based off of gcc output
69 Define(Defs, "__DragonFly__");
70 Define(Defs, "__DragonFly_cc_version", "100001");
71 Define(Defs, "__ELF__");
72 Define(Defs, "__KPRINTF_ATTRIBUTE__");
73 Define(Defs, "__tune_i386__");
74 Define(Defs, "unix");
75 Define(Defs, "__unix");
76 Define(Defs, "__unix__");
77}
78
79static void getLinuxDefines(std::vector<char> &Defs) {
80 // Linux defines; list based off of gcc output
81 Define(Defs, "__unix__");
82 Define(Defs, "__unix");
83 Define(Defs, "unix");
84 Define(Defs, "__linux__");
85 Define(Defs, "__linux");
86 Define(Defs, "linux");
87 Define(Defs, "__gnu_linux__");
88}
89
Chris Lattnerae0ee032008-12-04 23:20:07 +000090/// getDarwinNumber - Parse the 'darwin number' out of the specific targe
91/// triple. For example, if we have darwin8.5 return 8,5,4. If any entry is
92/// not defined, return 0's. Return true if we have -darwin in the string or
93/// false otherwise.
94static bool getDarwinNumber(const char *Triple, unsigned &Maj, unsigned &Min) {
95 Maj = Min = 0;
96 const char *Darwin = strstr(Triple, "-darwin");
97 if (Darwin == 0) return false;
98
99 Darwin += strlen("-darwin");
100 if (Darwin[0] < '0' || Darwin[0] > '9')
101 return true;
102
103 Maj = Darwin[0]-'0';
104 ++Darwin;
105
106 // Handle "darwin11".
107 if (Maj == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') {
108 Maj = 10+Darwin[0]-'0';
109 ++Darwin;
110 }
111
112 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049"
113 if (Darwin[0] == '.' && Darwin[1] >= '0' && Darwin[1] <= '9' &&
114 Darwin[2] == '\0')
115 Min = Darwin[1]-'0';
116
117 return true;
118}
119
Chris Lattner8b30c412008-09-30 01:00:25 +0000120static void getDarwinDefines(std::vector<char> &Defs, const char *Triple) {
Eli Friedman618234a2008-08-20 02:34:37 +0000121 Define(Defs, "__APPLE__");
122 Define(Defs, "__MACH__");
Chris Lattnerd427ad42009-02-05 07:19:24 +0000123 Define(Defs, "OBJC_NEW_PROPERTIES");
124
125 // FIXME: OBJC_ZEROCOST_EXCEPTIONS when using zero cost eh.
Chris Lattner8b30c412008-09-30 01:00:25 +0000126
127 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5.
Chris Lattnerae0ee032008-12-04 23:20:07 +0000128 unsigned Maj, Min;
129 if (getDarwinNumber(Triple, Maj, Min)) {
Chris Lattner079f2c462008-09-30 20:30:12 +0000130 char DarwinStr[] = "1000";
Chris Lattnerae0ee032008-12-04 23:20:07 +0000131 if (Maj >= 4 && Maj <= 13) { // 10.0-10.9
132 // darwin7 -> 1030, darwin8 -> 1040, darwin9 -> 1050, etc.
133 DarwinStr[2] = '0' + Maj-4;
Chris Lattner8b30c412008-09-30 01:00:25 +0000134 }
Chris Lattnerae0ee032008-12-04 23:20:07 +0000135
136 // Handle minor version: 10.4.9 -> darwin8.9 -> "1049"
137 DarwinStr[3] = Min+'0';
Chris Lattner079f2c462008-09-30 20:30:12 +0000138 Define(Defs, "__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", DarwinStr);
Chris Lattner8b30c412008-09-30 01:00:25 +0000139 }
Eli Friedman618234a2008-08-20 02:34:37 +0000140}
Reid Spencer5f016e22007-07-11 17:01:13 +0000141
Chris Lattnerae0ee032008-12-04 23:20:07 +0000142/// GetDarwinLanguageOptions - Set the default language options for darwin.
143static void GetDarwinLanguageOptions(LangOptions &Opts,
144 const char *Triple) {
145 Opts.NeXTRuntime = true;
146
147 unsigned Maj, Min;
148 if (!getDarwinNumber(Triple, Maj, Min))
149 return;
150
151 // Blocks default to on for 10.6 (darwin10) and beyond.
Fariborz Jahaniana30b17b2009-02-12 17:54:33 +0000152 // As does nonfragile-abi for 64bit mode
153 if (Maj > 9) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000154 Opts.Blocks = 1;
Fariborz Jahaniana30b17b2009-02-12 17:54:33 +0000155 if (Opts.ObjC1 && !strncmp(Triple, "x86_64", 6))
156 Opts.ObjCNonFragileABI = 1;
157 }
Chris Lattnerae0ee032008-12-04 23:20:07 +0000158}
159
160
Chris Lattnerd29b6302008-10-05 21:50:58 +0000161//===----------------------------------------------------------------------===//
162// Defines specific to certain architectures.
163//===----------------------------------------------------------------------===//
Eli Friedman0d4047b2008-08-21 00:24:02 +0000164
Reid Spencer5f016e22007-07-11 17:01:13 +0000165/// getPowerPCDefines - Return a set of the PowerPC-specific #defines that are
166/// not tied to a specific subtarget.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000167static void getPowerPCDefines(std::vector<char> &Defs, bool is64Bit) {
Reid Spencer5f016e22007-07-11 17:01:13 +0000168 // Target identification.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000169 Define(Defs, "__ppc__");
170 Define(Defs, "_ARCH_PPC");
171 Define(Defs, "__POWERPC__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000172 if (is64Bit) {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000173 Define(Defs, "_ARCH_PPC64");
174 Define(Defs, "_LP64");
175 Define(Defs, "__LP64__");
176 Define(Defs, "__ppc64__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000177 } else {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000178 Define(Defs, "__ppc__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000179 }
180
181 // Target properties.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000182 Define(Defs, "_BIG_ENDIAN");
183 Define(Defs, "__BIG_ENDIAN__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000184
Reid Spencer5f016e22007-07-11 17:01:13 +0000185 // Subtarget options.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000186 Define(Defs, "__NATURAL_ALIGNMENT__");
187 Define(Defs, "__REGISTER_PREFIX__", "");
Reid Spencer5f016e22007-07-11 17:01:13 +0000188
Chris Lattner12f09262008-10-05 21:49:27 +0000189 // FIXME: Should be controlled by command line option.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000190 Define(Defs, "__LONG_DOUBLE_128__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000191}
192
193/// getX86Defines - Return a set of the X86-specific #defines that are
194/// not tied to a specific subtarget.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000195static void getX86Defines(std::vector<char> &Defs, bool is64Bit) {
Reid Spencer5f016e22007-07-11 17:01:13 +0000196 // Target identification.
197 if (is64Bit) {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000198 Define(Defs, "_LP64");
199 Define(Defs, "__LP64__");
200 Define(Defs, "__amd64__");
201 Define(Defs, "__amd64");
202 Define(Defs, "__x86_64");
203 Define(Defs, "__x86_64__");
Chris Lattner06ebe862009-02-05 07:32:46 +0000204 Define(Defs, "__SSE3__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000205 } else {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000206 Define(Defs, "__i386__");
207 Define(Defs, "__i386");
208 Define(Defs, "i386");
Reid Spencer5f016e22007-07-11 17:01:13 +0000209 }
210
211 // Target properties.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000212 Define(Defs, "__LITTLE_ENDIAN__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000213
Reid Spencer5f016e22007-07-11 17:01:13 +0000214 // Subtarget options.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000215 Define(Defs, "__nocona");
216 Define(Defs, "__nocona__");
217 Define(Defs, "__tune_nocona__");
218 Define(Defs, "__SSE2_MATH__");
219 Define(Defs, "__SSE2__");
220 Define(Defs, "__SSE_MATH__");
221 Define(Defs, "__SSE__");
222 Define(Defs, "__MMX__");
223 Define(Defs, "__REGISTER_PREFIX__", "");
Reid Spencer5f016e22007-07-11 17:01:13 +0000224}
225
Chris Lattnerd0c33d32008-04-21 20:19:54 +0000226/// getARMDefines - Return a set of the ARM-specific #defines that are
Chris Lattner393ff042008-04-21 18:56:49 +0000227/// not tied to a specific subtarget.
228static void getARMDefines(std::vector<char> &Defs) {
229 // Target identification.
230 Define(Defs, "__arm");
231 Define(Defs, "__arm__");
232
233 // Target properties.
234 Define(Defs, "__LITTLE_ENDIAN__");
235
Chris Lattner393ff042008-04-21 18:56:49 +0000236 // Subtarget options. [hard coded to v6 for now]
237 Define(Defs, "__ARM_ARCH_6K__");
238 Define(Defs, "__ARMEL__");
239 Define(Defs, "__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__", "20000");
Chris Lattner393ff042008-04-21 18:56:49 +0000240}
241
Eli Friedmane4277982008-08-20 23:11:40 +0000242//===----------------------------------------------------------------------===//
243// Specific target implementations.
244//===----------------------------------------------------------------------===//
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000245
Eli Friedmane4277982008-08-20 23:11:40 +0000246namespace {
247// PPC abstract base class
248class PPCTargetInfo : public TargetInfo {
249 static const Builtin::Info BuiltinInfo[];
250 static const char * const GCCRegNames[];
251 static const TargetInfo::GCCRegAlias GCCRegAliases[];
252
253public:
254 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) {
255 CharIsSigned = false;
256 }
257 virtual void getTargetBuiltins(const Builtin::Info *&Records,
258 unsigned &NumRecords) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000259 Records = BuiltinInfo;
Eli Friedmane4277982008-08-20 23:11:40 +0000260 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000261 }
Eli Friedmane4277982008-08-20 23:11:40 +0000262 virtual const char *getVAListDeclaration() const {
Chris Lattnerd5998502008-10-27 01:11:29 +0000263 return "typedef char* __builtin_va_list;";
264 // This is the right definition for ABI/V4: System V.4/eabi.
265 /*return "typedef struct __va_list_tag {"
Eli Friedmane4277982008-08-20 23:11:40 +0000266 " unsigned char gpr;"
267 " unsigned char fpr;"
268 " unsigned short reserved;"
269 " void* overflow_arg_area;"
270 " void* reg_save_area;"
Chris Lattnerd5998502008-10-27 01:11:29 +0000271 "} __builtin_va_list[1];";*/
Anders Carlsson3346ae62007-11-24 23:38:12 +0000272 }
Eli Friedmane4277982008-08-20 23:11:40 +0000273 virtual const char *getTargetPrefix() const {
274 return "ppc";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000275 }
Eli Friedmane4277982008-08-20 23:11:40 +0000276 virtual void getGCCRegNames(const char * const *&Names,
277 unsigned &NumNames) const;
278 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
279 unsigned &NumAliases) const;
280 virtual bool validateAsmConstraint(char c,
281 TargetInfo::ConstraintInfo &info) const {
Anders Carlssond04c6e22007-11-27 04:11:28 +0000282 switch (c) {
283 default: return false;
284 case 'O': // Zero
285 return true;
286 case 'b': // Base register
287 case 'f': // Floating point register
288 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
289 return true;
290 }
291 }
Eli Friedmane4277982008-08-20 23:11:40 +0000292 virtual const char *getClobbers() const {
293 return "";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000294 }
Eli Friedmane4277982008-08-20 23:11:40 +0000295};
Anders Carlssond04c6e22007-11-27 04:11:28 +0000296
Eli Friedmane4277982008-08-20 23:11:40 +0000297const Builtin::Info PPCTargetInfo::BuiltinInfo[] = {
298#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
299#include "clang/AST/PPCBuiltins.def"
300};
Chris Lattner393ff042008-04-21 18:56:49 +0000301
Eli Friedmane4277982008-08-20 23:11:40 +0000302const char * const PPCTargetInfo::GCCRegNames[] = {
303 "0", "1", "2", "3", "4", "5", "6", "7",
304 "8", "9", "10", "11", "12", "13", "14", "15",
305 "16", "17", "18", "19", "20", "21", "22", "23",
306 "24", "25", "26", "27", "28", "29", "30", "31",
307 "0", "1", "2", "3", "4", "5", "6", "7",
308 "8", "9", "10", "11", "12", "13", "14", "15",
309 "16", "17", "18", "19", "20", "21", "22", "23",
310 "24", "25", "26", "27", "28", "29", "30", "31",
311 "mq", "lr", "ctr", "ap",
312 "0", "1", "2", "3", "4", "5", "6", "7",
313 "xer",
314 "0", "1", "2", "3", "4", "5", "6", "7",
315 "8", "9", "10", "11", "12", "13", "14", "15",
316 "16", "17", "18", "19", "20", "21", "22", "23",
317 "24", "25", "26", "27", "28", "29", "30", "31",
318 "vrsave", "vscr",
319 "spe_acc", "spefscr",
320 "sfp"
321};
Reid Spencer5f016e22007-07-11 17:01:13 +0000322
Eli Friedmane4277982008-08-20 23:11:40 +0000323void PPCTargetInfo::getGCCRegNames(const char * const *&Names,
324 unsigned &NumNames) const {
325 Names = GCCRegNames;
326 NumNames = llvm::array_lengthof(GCCRegNames);
327}
Reid Spencer5f016e22007-07-11 17:01:13 +0000328
Eli Friedmane4277982008-08-20 23:11:40 +0000329const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = {
330 // While some of these aliases do map to different registers
331 // they still share the same register name.
332 { { "cc", "cr0", "fr0", "r0", "v0"}, "0" },
333 { { "cr1", "fr1", "r1", "sp", "v1"}, "1" },
334 { { "cr2", "fr2", "r2", "toc", "v2"}, "2" },
335 { { "cr3", "fr3", "r3", "v3"}, "3" },
336 { { "cr4", "fr4", "r4", "v4"}, "4" },
337 { { "cr5", "fr5", "r5", "v5"}, "5" },
338 { { "cr6", "fr6", "r6", "v6"}, "6" },
339 { { "cr7", "fr7", "r7", "v7"}, "7" },
340 { { "fr8", "r8", "v8"}, "8" },
341 { { "fr9", "r9", "v9"}, "9" },
342 { { "fr10", "r10", "v10"}, "10" },
343 { { "fr11", "r11", "v11"}, "11" },
344 { { "fr12", "r12", "v12"}, "12" },
345 { { "fr13", "r13", "v13"}, "13" },
346 { { "fr14", "r14", "v14"}, "14" },
347 { { "fr15", "r15", "v15"}, "15" },
348 { { "fr16", "r16", "v16"}, "16" },
349 { { "fr17", "r17", "v17"}, "17" },
350 { { "fr18", "r18", "v18"}, "18" },
351 { { "fr19", "r19", "v19"}, "19" },
352 { { "fr20", "r20", "v20"}, "20" },
353 { { "fr21", "r21", "v21"}, "21" },
354 { { "fr22", "r22", "v22"}, "22" },
355 { { "fr23", "r23", "v23"}, "23" },
356 { { "fr24", "r24", "v24"}, "24" },
357 { { "fr25", "r25", "v25"}, "25" },
358 { { "fr26", "r26", "v26"}, "26" },
359 { { "fr27", "r27", "v27"}, "27" },
360 { { "fr28", "r28", "v28"}, "28" },
361 { { "fr29", "r29", "v29"}, "29" },
362 { { "fr30", "r30", "v30"}, "30" },
363 { { "fr31", "r31", "v31"}, "31" },
364};
365
366void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
367 unsigned &NumAliases) const {
368 Aliases = GCCRegAliases;
369 NumAliases = llvm::array_lengthof(GCCRegAliases);
370}
371} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +0000372
373namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000374class PPC32TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000375public:
Eli Friedmaned855cb2008-08-21 00:13:15 +0000376 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
377 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
378 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
379 }
Chris Lattnerd15fa822007-10-06 06:57:34 +0000380 virtual void getTargetDefines(std::vector<char> &Defines) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000381 getPowerPCDefines(Defines, false);
382 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000383};
384} // end anonymous namespace.
385
386namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000387class PPC64TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000388public:
Eli Friedmane4277982008-08-20 23:11:40 +0000389 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000390 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000391 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
392 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
Chris Lattnerf291b102008-05-09 06:17:04 +0000393 }
Chris Lattnerd15fa822007-10-06 06:57:34 +0000394 virtual void getTargetDefines(std::vector<char> &Defines) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000395 getPowerPCDefines(Defines, true);
396 }
Eli Friedmane4277982008-08-20 23:11:40 +0000397};
398} // end anonymous namespace.
399
Chris Lattnerae0ee032008-12-04 23:20:07 +0000400
Eli Friedmane4277982008-08-20 23:11:40 +0000401namespace {
402class DarwinPPCTargetInfo : public PPC32TargetInfo {
403public:
404 DarwinPPCTargetInfo(const std::string& triple) : PPC32TargetInfo(triple) {}
405 virtual void getTargetDefines(std::vector<char> &Defines) const {
406 PPC32TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000407 getDarwinDefines(Defines, getTargetTriple());
Reid Spencer5f016e22007-07-11 17:01:13 +0000408 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000409
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000410 /// getDefaultLangOptions - Allow the target to specify default settings for
411 /// various language options. These may be overridden by command line
412 /// options.
413 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000414 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000415 }
Eli Friedmane4277982008-08-20 23:11:40 +0000416};
417} // end anonymous namespace.
418
419namespace {
420class DarwinPPC64TargetInfo : public PPC64TargetInfo {
421public:
422 DarwinPPC64TargetInfo(const std::string& triple) : PPC64TargetInfo(triple) {}
423 virtual void getTargetDefines(std::vector<char> &Defines) const {
424 PPC64TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000425 getDarwinDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +0000426 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000427
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000428 /// getDefaultLangOptions - Allow the target to specify default settings for
429 /// various language options. These may be overridden by command line
430 /// options.
431 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000432 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000433 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000434};
435} // end anonymous namespace.
436
437namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000438// Namespace for x86 abstract base class
439const Builtin::Info BuiltinInfo[] = {
440#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
441#include "clang/AST/X86Builtins.def"
442};
Eli Friedman61538a72008-05-20 14:21:01 +0000443
Eli Friedman618234a2008-08-20 02:34:37 +0000444const char *GCCRegNames[] = {
445 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp",
446 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)",
447 "argp", "flags", "fspr", "dirflag", "frame",
448 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7",
449 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7",
450 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
451 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
452};
453
454const TargetInfo::GCCRegAlias GCCRegAliases[] = {
455 { { "al", "ah", "eax", "rax" }, "ax" },
456 { { "bl", "bh", "ebx", "rbx" }, "bx" },
457 { { "cl", "ch", "ecx", "rcx" }, "cx" },
458 { { "dl", "dh", "edx", "rdx" }, "dx" },
459 { { "esi", "rsi" }, "si" },
460 { { "edi", "rdi" }, "di" },
461 { { "esp", "rsp" }, "sp" },
462 { { "ebp", "rbp" }, "bp" },
463};
464
465// X86 target abstract base class; x86-32 and x86-64 are very close, so
466// most of the implementation can be shared.
467class X86TargetInfo : public TargetInfo {
468public:
469 X86TargetInfo(const std::string& triple) : TargetInfo(triple) {
470 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended;
Reid Spencer5f016e22007-07-11 17:01:13 +0000471 }
472 virtual void getTargetBuiltins(const Builtin::Info *&Records,
473 unsigned &NumRecords) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000474 Records = BuiltinInfo;
475 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000476 }
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000477 virtual const char *getTargetPrefix() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000478 return "x86";
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000479 }
Anders Carlsson3346ae62007-11-24 23:38:12 +0000480 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedman618234a2008-08-20 02:34:37 +0000481 unsigned &NumNames) const {
482 Names = GCCRegNames;
483 NumNames = llvm::array_lengthof(GCCRegNames);
Anders Carlsson3346ae62007-11-24 23:38:12 +0000484 }
485 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
486 unsigned &NumAliases) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000487 Aliases = GCCRegAliases;
488 NumAliases = llvm::array_lengthof(GCCRegAliases);
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000489 }
Anders Carlssond04c6e22007-11-27 04:11:28 +0000490 virtual bool validateAsmConstraint(char c,
Eli Friedman618234a2008-08-20 02:34:37 +0000491 TargetInfo::ConstraintInfo &info) const;
492 virtual std::string convertConstraint(const char Constraint) const;
Anders Carlssond04c6e22007-11-27 04:11:28 +0000493 virtual const char *getClobbers() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000494 return "~{dirflag},~{fpsr},~{flags}";
495 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000496};
Eli Friedman618234a2008-08-20 02:34:37 +0000497
498bool
499X86TargetInfo::validateAsmConstraint(char c,
500 TargetInfo::ConstraintInfo &info) const {
501 switch (c) {
502 default: return false;
503 case 'a': // eax.
504 case 'b': // ebx.
505 case 'c': // ecx.
506 case 'd': // edx.
507 case 'S': // esi.
508 case 'D': // edi.
509 case 'A': // edx:eax.
510 case 't': // top of floating point stack.
511 case 'u': // second from top of floating point stack.
512 case 'q': // Any register accessible as [r]l: a, b, c, and d.
Anders Carlssonfce09342008-10-06 00:41:45 +0000513 case 'y': // Any MMX register.
Anders Carlssona7406d42008-10-06 19:17:39 +0000514 case 'x': // Any SSE register.
Eli Friedman618234a2008-08-20 02:34:37 +0000515 case 'Q': // Any register accessible as [r]h: a, b, c, and d.
Anders Carlsson79bc64c2009-01-24 18:03:09 +0000516 case 'e': // 32-bit signed integer constant for use with zero-extending
517 // x86_64 instructions.
518 case 'Z': // 32-bit unsigned integer constant for use with zero-extending
519 // x86_64 instructions.
Eli Friedman618234a2008-08-20 02:34:37 +0000520 case 'N': // unsigned 8-bit integer constant for use with in and out
521 // instructions.
522 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
523 return true;
524 }
525}
526
527std::string
528X86TargetInfo::convertConstraint(const char Constraint) const {
529 switch (Constraint) {
530 case 'a': return std::string("{ax}");
531 case 'b': return std::string("{bx}");
532 case 'c': return std::string("{cx}");
533 case 'd': return std::string("{dx}");
534 case 'S': return std::string("{si}");
535 case 'D': return std::string("{di}");
536 case 't': // top of floating point stack.
537 return std::string("{st}");
538 case 'u': // second from top of floating point stack.
539 return std::string("{st(1)}"); // second from top of floating point stack.
540 default:
541 return std::string(1, Constraint);
542 }
543}
Eli Friedman618234a2008-08-20 02:34:37 +0000544} // end anonymous namespace
Reid Spencer5f016e22007-07-11 17:01:13 +0000545
546namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000547// X86-32 generic target
548class X86_32TargetInfo : public X86TargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000549public:
Eli Friedman618234a2008-08-20 02:34:37 +0000550 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
551 DoubleAlign = LongLongAlign = 32;
552 LongDoubleWidth = 96;
553 LongDoubleAlign = 32;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000554 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
555 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
556 "a0:0:64-f80:32:32";
Eli Friedman618234a2008-08-20 02:34:37 +0000557 }
558 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000559 return "typedef char* __builtin_va_list;";
Eli Friedman618234a2008-08-20 02:34:37 +0000560 }
561 virtual void getTargetDefines(std::vector<char> &Defines) const {
562 getX86Defines(Defines, false);
563 }
564};
565} // end anonymous namespace
566
567namespace {
568// x86-32 Darwin (OS X) target
569class DarwinI386TargetInfo : public X86_32TargetInfo {
570public:
571 DarwinI386TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
572 LongDoubleWidth = 128;
573 LongDoubleAlign = 128;
Chris Lattnerd427ad42009-02-05 07:19:24 +0000574 PtrDiffType = SignedInt;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000575 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
576 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
577 "a0:0:64-f80:128:128";
Eli Friedman618234a2008-08-20 02:34:37 +0000578 }
579 virtual void getTargetDefines(std::vector<char> &Defines) const {
580 X86_32TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000581 getDarwinDefines(Defines, getTargetTriple());
Eli Friedman618234a2008-08-20 02:34:37 +0000582 }
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000583 /// getDefaultLangOptions - Allow the target to specify default settings for
584 /// various language options. These may be overridden by command line
585 /// options.
586 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000587 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000588 }
Eli Friedman618234a2008-08-20 02:34:37 +0000589};
590} // end anonymous namespace
591
592namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000593// x86-32 FreeBSD target
594class FreeBSDX86_32TargetInfo : public X86_32TargetInfo {
595public:
Eli Friedmanf509d732008-11-02 02:43:55 +0000596 FreeBSDX86_32TargetInfo(const std::string& triple) :
597 X86_32TargetInfo(triple) {
598 SizeType = UnsignedInt;
599 PtrDiffType = SignedInt;
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000600 }
601 virtual void getTargetDefines(std::vector<char> &Defines) const {
602 X86_32TargetInfo::getTargetDefines(Defines);
603 getFreeBSDDefines(Defines, 0, getTargetTriple());
604 }
605};
606} // end anonymous namespace
607
608namespace {
Chris Lattnereac7aee2008-08-23 18:23:14 +0000609// x86-32 DragonFly target
610class DragonFlyX86_32TargetInfo : public X86_32TargetInfo {
611public:
Eli Friedmanf509d732008-11-02 02:43:55 +0000612 DragonFlyX86_32TargetInfo(const std::string& triple) :
613 X86_32TargetInfo(triple) {
614 SizeType = UnsignedInt;
615 PtrDiffType = SignedInt;
Chris Lattnereac7aee2008-08-23 18:23:14 +0000616 }
617 virtual void getTargetDefines(std::vector<char> &Defines) const {
618 X86_32TargetInfo::getTargetDefines(Defines);
619 getDragonFlyDefines(Defines);
620 }
621};
622} // end anonymous namespace
623
624namespace {
Eli Friedman0d4047b2008-08-21 00:24:02 +0000625// x86-32 Linux target
626class LinuxX86_32TargetInfo : public X86_32TargetInfo {
627public:
628 LinuxX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000629 UserLabelPrefix = "";
Eli Friedmanf509d732008-11-02 02:43:55 +0000630 SizeType = UnsignedInt;
631 PtrDiffType = SignedInt;
Chris Lattner6ad474f2009-02-13 22:28:55 +0000632 IntPtrType = SignedInt;
Eli Friedman0d4047b2008-08-21 00:24:02 +0000633 }
634 virtual void getTargetDefines(std::vector<char> &Defines) const {
635 X86_32TargetInfo::getTargetDefines(Defines);
636 getLinuxDefines(Defines);
637 }
638};
639} // end anonymous namespace
640
641namespace {
Eli Friedman29a30502008-08-21 01:40:19 +0000642// x86-32 Windows target
643class WindowsX86_32TargetInfo : public X86_32TargetInfo {
644public:
645 WindowsX86_32TargetInfo(const std::string& triple)
646 : X86_32TargetInfo(triple) {
647 // FIXME: Fix wchar_t.
648 // FIXME: We should probably enable -fms-extensions by default for
649 // this target.
Eli Friedmanf509d732008-11-02 02:43:55 +0000650 SizeType = UnsignedInt;
651 PtrDiffType = SignedInt;
Eli Friedman29a30502008-08-21 01:40:19 +0000652 }
653 virtual void getTargetDefines(std::vector<char> &Defines) const {
654 X86_32TargetInfo::getTargetDefines(Defines);
655 // This list is based off of the the list of things MingW defines
656 Define(Defines, "__WIN32__");
657 Define(Defines, "__WIN32");
658 Define(Defines, "_WIN32");
659 Define(Defines, "WIN32");
660 Define(Defines, "__WINNT__");
661 Define(Defines, "__WINNT");
662 Define(Defines, "WINNT");
Eli Friedman29a30502008-08-21 01:40:19 +0000663 Define(Defines, "_X86_");
664 Define(Defines, "__MSVCRT__");
665 }
666};
667} // end anonymous namespace
668
669namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000670// x86-64 generic target
671class X86_64TargetInfo : public X86TargetInfo {
672public:
673 X86_64TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000674 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Chris Lattner778601f2009-01-28 06:58:19 +0000675 DoubleAlign = LongLongAlign = 64;
Eli Friedman61538a72008-05-20 14:21:01 +0000676 LongDoubleWidth = 128;
677 LongDoubleAlign = 128;
Chris Lattner06ebe862009-02-05 07:32:46 +0000678 IntMaxType = SignedLong;
679 UIntMaxType = UnsignedLong;
680
Eli Friedmaned855cb2008-08-21 00:13:15 +0000681 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
682 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-"
683 "a0:0:64-f80:128:128";
Reid Spencer5f016e22007-07-11 17:01:13 +0000684 }
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000685 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000686 return "typedef struct __va_list_tag {"
687 " unsigned gp_offset;"
688 " unsigned fp_offset;"
689 " void* overflow_arg_area;"
690 " void* reg_save_area;"
691 "} __builtin_va_list[1];";
Anders Carlsson3346ae62007-11-24 23:38:12 +0000692 }
Eli Friedman618234a2008-08-20 02:34:37 +0000693 virtual void getTargetDefines(std::vector<char> &Defines) const {
694 getX86Defines(Defines, true);
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000695 }
Eli Friedman618234a2008-08-20 02:34:37 +0000696};
697} // end anonymous namespace
698
699namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000700// x86-64 FreeBSD target
701class FreeBSDX86_64TargetInfo : public X86_64TargetInfo {
702public:
Eli Friedmanf509d732008-11-02 02:43:55 +0000703 FreeBSDX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {}
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000704 virtual void getTargetDefines(std::vector<char> &Defines) const {
705 X86_64TargetInfo::getTargetDefines(Defines);
706 getFreeBSDDefines(Defines, 1, getTargetTriple());
707 }
708};
709} // end anonymous namespace
710
711namespace {
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000712// x86-64 Linux target
713class LinuxX86_64TargetInfo : public X86_64TargetInfo {
714public:
715 LinuxX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000716 UserLabelPrefix = "";
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000717 }
718 virtual void getTargetDefines(std::vector<char> &Defines) const {
719 X86_64TargetInfo::getTargetDefines(Defines);
720 getLinuxDefines(Defines);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000721 }
722};
723} // end anonymous namespace
724
725namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000726// x86-64 Darwin (OS X) target
727class DarwinX86_64TargetInfo : public X86_64TargetInfo {
728public:
729 DarwinX86_64TargetInfo(const std::string& triple) :
730 X86_64TargetInfo(triple) {}
731
732 virtual void getTargetDefines(std::vector<char> &Defines) const {
733 X86_64TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000734 getDarwinDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +0000735 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000736
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000737 /// getDefaultLangOptions - Allow the target to specify default settings for
738 /// various language options. These may be overridden by command line
739 /// options.
740 virtual void getDefaultLangOptions(LangOptions &Opts) {
Chris Lattnerae0ee032008-12-04 23:20:07 +0000741 GetDarwinLanguageOptions(Opts, getTargetTriple());
Chris Lattner8fc4dfb2008-12-04 22:54:33 +0000742 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000743};
744} // end anonymous namespace.
745
Chris Lattner393ff042008-04-21 18:56:49 +0000746namespace {
Eli Friedmana9f54962008-08-20 07:44:10 +0000747class ARMTargetInfo : public TargetInfo {
Chris Lattner393ff042008-04-21 18:56:49 +0000748public:
Eli Friedmana9f54962008-08-20 07:44:10 +0000749 ARMTargetInfo(const std::string& triple) : TargetInfo(triple) {
750 // FIXME: Are the defaults correct for ARM?
Eli Friedmaned855cb2008-08-21 00:13:15 +0000751 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
752 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:64";
Eli Friedman61538a72008-05-20 14:21:01 +0000753 }
Chris Lattner393ff042008-04-21 18:56:49 +0000754 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner393ff042008-04-21 18:56:49 +0000755 getARMDefines(Defines);
756 }
757 virtual void getTargetBuiltins(const Builtin::Info *&Records,
758 unsigned &NumRecords) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000759 // FIXME: Implement.
760 Records = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000761 NumRecords = 0;
762 }
763 virtual const char *getVAListDeclaration() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000764 return "typedef char* __builtin_va_list;";
Chris Lattner393ff042008-04-21 18:56:49 +0000765 }
766 virtual const char *getTargetPrefix() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000767 return "arm";
Chris Lattner393ff042008-04-21 18:56:49 +0000768 }
Chris Lattner393ff042008-04-21 18:56:49 +0000769 virtual void getGCCRegNames(const char * const *&Names,
770 unsigned &NumNames) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000771 // FIXME: Implement.
772 Names = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000773 NumNames = 0;
774 }
775 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
776 unsigned &NumAliases) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000777 // FIXME: Implement.
778 Aliases = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000779 NumAliases = 0;
780 }
781 virtual bool validateAsmConstraint(char c,
Nate Begemanad487f42008-04-22 05:03:19 +0000782 TargetInfo::ConstraintInfo &info) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000783 // FIXME: Check if this is complete
Nate Begemanad487f42008-04-22 05:03:19 +0000784 switch (c) {
Eli Friedmana9f54962008-08-20 07:44:10 +0000785 default:
Nate Begemanad487f42008-04-22 05:03:19 +0000786 case 'l': // r0-r7
787 case 'h': // r8-r15
788 case 'w': // VFP Floating point register single precision
789 case 'P': // VFP Floating point register double precision
790 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
791 return true;
792 }
Chris Lattner393ff042008-04-21 18:56:49 +0000793 return false;
794 }
795 virtual const char *getClobbers() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000796 // FIXME: Is this really right?
Chris Lattner393ff042008-04-21 18:56:49 +0000797 return "";
798 }
799};
800} // end anonymous namespace.
801
Eli Friedmana9f54962008-08-20 07:44:10 +0000802
803namespace {
804class DarwinARMTargetInfo : public ARMTargetInfo {
805public:
806 DarwinARMTargetInfo(const std::string& triple) : ARMTargetInfo(triple) {}
807
808 virtual void getTargetDefines(std::vector<char> &Defines) const {
809 ARMTargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000810 getDarwinDefines(Defines, getTargetTriple());
Eli Friedmana9f54962008-08-20 07:44:10 +0000811 }
812};
813} // end anonymous namespace.
814
Reid Spencer5f016e22007-07-11 17:01:13 +0000815namespace {
Eli Friedman01b86682008-08-20 07:28:14 +0000816class SparcV8TargetInfo : public TargetInfo {
Chris Lattnere957f532009-01-27 01:58:38 +0000817 static const TargetInfo::GCCRegAlias GCCRegAliases[];
818 static const char * const GCCRegNames[];
Gabor Greif26658672008-02-21 16:29:08 +0000819public:
Eli Friedman01b86682008-08-20 07:28:14 +0000820 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) {
821 // FIXME: Support Sparc quad-precision long double?
Eli Friedmaned855cb2008-08-21 00:13:15 +0000822 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
823 "i64:64:64-f32:32:32-f64:64:64-v64:64:64";
Eli Friedman01b86682008-08-20 07:28:14 +0000824 }
Gabor Greif26658672008-02-21 16:29:08 +0000825 virtual void getTargetDefines(std::vector<char> &Defines) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000826 // FIXME: This is missing a lot of important defines; some of the
827 // missing stuff is likely to break system headers.
Gabor Greif26658672008-02-21 16:29:08 +0000828 Define(Defines, "__sparc");
Eli Friedmanbf0c9bd2008-05-25 05:26:09 +0000829 Define(Defines, "__sparc__");
Gabor Greif26658672008-02-21 16:29:08 +0000830 Define(Defines, "__sparcv8");
831 }
832 virtual void getTargetBuiltins(const Builtin::Info *&Records,
833 unsigned &NumRecords) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000834 // FIXME: Implement!
Gabor Greif26658672008-02-21 16:29:08 +0000835 }
836 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000837 return "typedef void* __builtin_va_list;";
Gabor Greif26658672008-02-21 16:29:08 +0000838 }
839 virtual const char *getTargetPrefix() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000840 return "sparc";
Gabor Greif26658672008-02-21 16:29:08 +0000841 }
842 virtual void getGCCRegNames(const char * const *&Names,
Chris Lattnere957f532009-01-27 01:58:38 +0000843 unsigned &NumNames) const;
Gabor Greif26658672008-02-21 16:29:08 +0000844 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattnere957f532009-01-27 01:58:38 +0000845 unsigned &NumAliases) const;
Gabor Greif26658672008-02-21 16:29:08 +0000846 virtual bool validateAsmConstraint(char c,
847 TargetInfo::ConstraintInfo &info) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000848 // FIXME: Implement!
849 return false;
Gabor Greif26658672008-02-21 16:29:08 +0000850 }
851 virtual const char *getClobbers() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000852 // FIXME: Implement!
853 return "";
Gabor Greif26658672008-02-21 16:29:08 +0000854 }
855};
856
Chris Lattnere957f532009-01-27 01:58:38 +0000857const char * const SparcV8TargetInfo::GCCRegNames[] = {
858 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
859 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
860 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
861 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31"
862};
863
864void SparcV8TargetInfo::getGCCRegNames(const char * const *&Names,
865 unsigned &NumNames) const {
866 Names = GCCRegNames;
867 NumNames = llvm::array_lengthof(GCCRegNames);
868}
869
870const TargetInfo::GCCRegAlias SparcV8TargetInfo::GCCRegAliases[] = {
871 { { "g0" }, "r0" },
872 { { "g1" }, "r1" },
873 { { "g2" }, "r2" },
874 { { "g3" }, "r3" },
875 { { "g4" }, "r4" },
876 { { "g5" }, "r5" },
877 { { "g6" }, "r6" },
878 { { "g7" }, "r7" },
879 { { "o0" }, "r8" },
880 { { "o1" }, "r9" },
881 { { "o2" }, "r10" },
882 { { "o3" }, "r11" },
883 { { "o4" }, "r12" },
884 { { "o5" }, "r13" },
885 { { "o6", "sp" }, "r14" },
886 { { "o7" }, "r15" },
887 { { "l0" }, "r16" },
888 { { "l1" }, "r17" },
889 { { "l2" }, "r18" },
890 { { "l3" }, "r19" },
891 { { "l4" }, "r20" },
892 { { "l5" }, "r21" },
893 { { "l6" }, "r22" },
894 { { "l7" }, "r23" },
895 { { "i0" }, "r24" },
896 { { "i1" }, "r25" },
897 { { "i2" }, "r26" },
898 { { "i3" }, "r27" },
899 { { "i4" }, "r28" },
900 { { "i5" }, "r29" },
901 { { "i6", "fp" }, "r30" },
902 { { "i7" }, "r31" },
903};
904
905void SparcV8TargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
906 unsigned &NumAliases) const {
907 Aliases = GCCRegAliases;
908 NumAliases = llvm::array_lengthof(GCCRegAliases);
909}
Gabor Greif26658672008-02-21 16:29:08 +0000910} // end anonymous namespace.
911
Eli Friedman01b86682008-08-20 07:28:14 +0000912namespace {
913class SolarisSparcV8TargetInfo : public SparcV8TargetInfo {
914public:
915 SolarisSparcV8TargetInfo(const std::string& triple) :
Eli Friedmanf509d732008-11-02 02:43:55 +0000916 SparcV8TargetInfo(triple) {
917 SizeType = UnsignedInt;
918 PtrDiffType = SignedInt;
919 }
Eli Friedman01b86682008-08-20 07:28:14 +0000920
921 virtual void getTargetDefines(std::vector<char> &Defines) const {
922 SparcV8TargetInfo::getTargetDefines(Defines);
923 getSolarisDefines(Defines);
924 }
925};
926} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +0000927
Chris Lattner2621fd12008-05-08 05:58:21 +0000928namespace {
929 class PIC16TargetInfo : public TargetInfo{
930 public:
931 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) {
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +0000932 IntWidth = 16;
933 LongWidth = LongLongWidth = 32;
934 PointerWidth = 16;
935 IntAlign = 8;
936 LongAlign = LongLongAlign = 8;
Eli Friedman61538a72008-05-20 14:21:01 +0000937 PointerAlign = 8;
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +0000938 SizeType = UnsignedInt;
939 IntMaxType = SignedLong;
940 UIntMaxType = UnsignedLong;
Chris Lattner6ad474f2009-02-13 22:28:55 +0000941 IntPtrType = SignedShort;
Eli Friedmanf509d732008-11-02 02:43:55 +0000942 PtrDiffType = SignedInt;
Sanjiv Gupta364af812008-08-18 10:05:22 +0000943 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8";
Chris Lattner2621fd12008-05-08 05:58:21 +0000944 }
Chris Lattner927686f2008-05-09 06:08:39 +0000945 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; }
946 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; }
Chris Lattner2621fd12008-05-08 05:58:21 +0000947 virtual void getTargetDefines(std::vector<char> &Defines) const {
948 Define(Defines, "__pic16");
949 }
950 virtual void getTargetBuiltins(const Builtin::Info *&Records,
951 unsigned &NumRecords) const {}
952 virtual const char *getVAListDeclaration() const { return "";}
953 virtual const char *getClobbers() const {return "";}
954 virtual const char *getTargetPrefix() const {return "";}
955 virtual void getGCCRegNames(const char * const *&Names,
956 unsigned &NumNames) const {}
957 virtual bool validateAsmConstraint(char c,
958 TargetInfo::ConstraintInfo &info) const {
959 return true;
960 }
961 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
962 unsigned &NumAliases) const {}
963 virtual bool useGlobalsForAutomaticVariables() const {return true;}
964 };
965}
966
Reid Spencer5f016e22007-07-11 17:01:13 +0000967//===----------------------------------------------------------------------===//
968// Driver code
969//===----------------------------------------------------------------------===//
970
Ted Kremenek8448d382007-12-04 17:07:35 +0000971static inline bool IsX86(const std::string& TT) {
Ted Kremenekae360762007-12-03 22:06:55 +0000972 return (TT.size() >= 5 && TT[0] == 'i' && TT[2] == '8' && TT[3] == '6' &&
973 TT[4] == '-' && TT[1] - '3' < 6);
974}
975
Chris Lattner42e67372008-03-05 01:18:20 +0000976/// CreateTargetInfo - Return the target info object for the specified target
977/// triple.
978TargetInfo* TargetInfo::CreateTargetInfo(const std::string &T) {
Eli Friedmaned855cb2008-08-21 00:13:15 +0000979 // OS detection; this isn't really anywhere near complete.
980 // Additions and corrections are welcome.
981 bool isDarwin = T.find("-darwin") != std::string::npos;
Chris Lattnereac7aee2008-08-23 18:23:14 +0000982 bool isDragonFly = T.find("-dragonfly") != std::string::npos;
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000983 bool isFreeBSD = T.find("-freebsd") != std::string::npos;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000984 bool isSolaris = T.find("-solaris") != std::string::npos;
985 bool isLinux = T.find("-linux") != std::string::npos;
986 bool isWindows = T.find("-windows") != std::string::npos ||
987 T.find("-win32") != std::string::npos ||
988 T.find("-mingw") != std::string::npos;
Eli Friedman61538a72008-05-20 14:21:01 +0000989
Eli Friedmaned855cb2008-08-21 00:13:15 +0000990 if (T.find("ppc-") == 0 || T.find("powerpc-") == 0) {
991 if (isDarwin)
992 return new DarwinPPCTargetInfo(T);
993 return new PPC32TargetInfo(T);
994 }
Eli Friedman61538a72008-05-20 14:21:01 +0000995
Eli Friedmaned855cb2008-08-21 00:13:15 +0000996 if (T.find("ppc64-") == 0 || T.find("powerpc64-") == 0) {
997 if (isDarwin)
998 return new DarwinPPC64TargetInfo(T);
999 return new PPC64TargetInfo(T);
1000 }
Chris Lattner393ff042008-04-21 18:56:49 +00001001
Eli Friedmaned855cb2008-08-21 00:13:15 +00001002 if (T.find("armv6-") == 0 || T.find("arm-") == 0) {
1003 if (isDarwin)
1004 return new DarwinARMTargetInfo(T);
1005 return new ARMTargetInfo(T);
1006 }
Eli Friedman61538a72008-05-20 14:21:01 +00001007
Eli Friedmaned855cb2008-08-21 00:13:15 +00001008 if (T.find("sparc-") == 0) {
1009 if (isSolaris)
1010 return new SolarisSparcV8TargetInfo(T);
1011 return new SparcV8TargetInfo(T);
1012 }
1013
1014 if (T.find("x86_64-") == 0) {
1015 if (isDarwin)
1016 return new DarwinX86_64TargetInfo(T);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +00001017 if (isLinux)
1018 return new LinuxX86_64TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +00001019 if (isFreeBSD)
1020 return new FreeBSDX86_64TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +00001021 return new X86_64TargetInfo(T);
1022 }
Eli Friedman61538a72008-05-20 14:21:01 +00001023
Chris Lattner2621fd12008-05-08 05:58:21 +00001024 if (T.find("pic16-") == 0)
1025 return new PIC16TargetInfo(T);
1026
Eli Friedmaned855cb2008-08-21 00:13:15 +00001027 if (IsX86(T)) {
1028 if (isDarwin)
1029 return new DarwinI386TargetInfo(T);
Eli Friedman0d4047b2008-08-21 00:24:02 +00001030 if (isLinux)
1031 return new LinuxX86_32TargetInfo(T);
Chris Lattnereac7aee2008-08-23 18:23:14 +00001032 if (isDragonFly)
1033 return new DragonFlyX86_32TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +00001034 if (isFreeBSD)
1035 return new FreeBSDX86_32TargetInfo(T);
Eli Friedman29a30502008-08-21 01:40:19 +00001036 if (isWindows)
1037 return new WindowsX86_32TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +00001038 return new X86_32TargetInfo(T);
1039 }
Eli Friedman61538a72008-05-20 14:21:01 +00001040
Chris Lattner42e67372008-03-05 01:18:20 +00001041 return NULL;
Reid Spencer5f016e22007-07-11 17:01:13 +00001042}
Ted Kremenekfb79f7c2008-03-04 17:47:18 +00001043