blob: 456c1f8f35308534341deecd32fa9595f80f6ddd [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"
Anders Carlsson3346ae62007-11-24 23:38:12 +000018#include "llvm/ADT/STLExtras.h"
Eli Friedman25531262008-05-20 14:27:34 +000019#include "llvm/ADT/APFloat.h"
Reid Spencer5f016e22007-07-11 17:01:13 +000020using namespace clang;
21
Reid Spencer5f016e22007-07-11 17:01:13 +000022//===----------------------------------------------------------------------===//
23// Common code shared among targets.
24//===----------------------------------------------------------------------===//
25
Chris Lattnerd15fa822007-10-06 06:57:34 +000026static void Define(std::vector<char> &Buf, const char *Macro,
27 const char *Val = "1") {
28 const char *Def = "#define ";
29 Buf.insert(Buf.end(), Def, Def+strlen(Def));
30 Buf.insert(Buf.end(), Macro, Macro+strlen(Macro));
31 Buf.push_back(' ');
32 Buf.insert(Buf.end(), Val, Val+strlen(Val));
33 Buf.push_back('\n');
34}
35
Chris Lattnerd29b6302008-10-05 21:50:58 +000036//===----------------------------------------------------------------------===//
37// Defines specific to certain operating systems.
38//===----------------------------------------------------------------------===//
39
Eli Friedman01b86682008-08-20 07:28:14 +000040static void getSolarisDefines(std::vector<char> &Defs) {
41 Define(Defs, "__SUN__");
42 Define(Defs, "__SOLARIS__");
43}
Reid Spencer5f016e22007-07-11 17:01:13 +000044
Chris Lattnerfd0269d2008-10-16 17:04:31 +000045static void getFreeBSDDefines(std::vector<char> &Defs, bool is64Bit, const char *Triple) {
46 // FreeBSD defines; list based off of gcc output
47
48 const char *FreeBSD = strstr(Triple, "-freebsd");
49 FreeBSD += strlen("-freebsd");
50 char release[] = "X";
51 release[0] = FreeBSD[0];
52 char version[] = "X00001";
53 version[0] = FreeBSD[0];
54
55 Define(Defs, "__FreeBSD__", release);
56 Define(Defs, "__FreeBSD_cc_version", version);
57 Define(Defs, "__KPRINTF_ATTRIBUTE__");
58 Define(Defs, "unix");
59 Define(Defs, "bsd");
60 if (is64Bit) {
61 Define(Defs, "__LP64__");
62 }
63}
64
Chris Lattnerd29b6302008-10-05 21:50:58 +000065static void getDragonFlyDefines(std::vector<char> &Defs) {
66 // DragonFly defines; list based off of gcc output
67 Define(Defs, "__DragonFly__");
68 Define(Defs, "__DragonFly_cc_version", "100001");
69 Define(Defs, "__ELF__");
70 Define(Defs, "__KPRINTF_ATTRIBUTE__");
71 Define(Defs, "__tune_i386__");
72 Define(Defs, "unix");
73 Define(Defs, "__unix");
74 Define(Defs, "__unix__");
75}
76
77static void getLinuxDefines(std::vector<char> &Defs) {
78 // Linux defines; list based off of gcc output
79 Define(Defs, "__unix__");
80 Define(Defs, "__unix");
81 Define(Defs, "unix");
82 Define(Defs, "__linux__");
83 Define(Defs, "__linux");
84 Define(Defs, "linux");
85 Define(Defs, "__gnu_linux__");
86}
87
Chris Lattner8b30c412008-09-30 01:00:25 +000088static void getDarwinDefines(std::vector<char> &Defs, const char *Triple) {
Eli Friedman618234a2008-08-20 02:34:37 +000089 Define(Defs, "__APPLE__");
90 Define(Defs, "__MACH__");
Chris Lattner8b30c412008-09-30 01:00:25 +000091
92 // Figure out which "darwin number" the target triple is. "darwin9" -> 10.5.
93 const char *Darwin = strstr(Triple, "-darwin");
94 if (Darwin) {
Chris Lattner079f2c462008-09-30 20:30:12 +000095 char DarwinStr[] = "1000";
Chris Lattner8b30c412008-09-30 01:00:25 +000096 Darwin += strlen("-darwin");
Chris Lattner079f2c462008-09-30 20:30:12 +000097 if (Darwin[0] >= '0' && Darwin[0] <= '9') {
98 unsigned DarwinNo = Darwin[0]-'0';
99 ++Darwin;
100
101 // Handle "darwin11".
102 if (DarwinNo == 1 && Darwin[0] >= '0' && Darwin[0] <= '9') {
103 DarwinNo = 10+Darwin[0]-'0';
104 ++Darwin;
105 }
106
107 if (DarwinNo >= 4 && DarwinNo <= 13) { // 10.0-10.9
Chris Lattner8b30c412008-09-30 01:00:25 +0000108 // darwin7 -> 1030, darwin8 -> 1040, darwin9 -> 1050, etc.
109 DarwinStr[2] = '0' + DarwinNo-4;
Chris Lattner8b30c412008-09-30 01:00:25 +0000110 }
Chris Lattner079f2c462008-09-30 20:30:12 +0000111
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 DarwinStr[3] = Darwin[1];
116
Chris Lattner8b30c412008-09-30 01:00:25 +0000117 }
Chris Lattner079f2c462008-09-30 20:30:12 +0000118 Define(Defs, "__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", DarwinStr);
Chris Lattner8b30c412008-09-30 01:00:25 +0000119 }
Eli Friedman618234a2008-08-20 02:34:37 +0000120}
Reid Spencer5f016e22007-07-11 17:01:13 +0000121
Chris Lattnerd29b6302008-10-05 21:50:58 +0000122//===----------------------------------------------------------------------===//
123// Defines specific to certain architectures.
124//===----------------------------------------------------------------------===//
Eli Friedman0d4047b2008-08-21 00:24:02 +0000125
Reid Spencer5f016e22007-07-11 17:01:13 +0000126/// getPowerPCDefines - Return a set of the PowerPC-specific #defines that are
127/// not tied to a specific subtarget.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000128static void getPowerPCDefines(std::vector<char> &Defs, bool is64Bit) {
Reid Spencer5f016e22007-07-11 17:01:13 +0000129 // Target identification.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000130 Define(Defs, "__ppc__");
131 Define(Defs, "_ARCH_PPC");
132 Define(Defs, "__POWERPC__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000133 if (is64Bit) {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000134 Define(Defs, "_ARCH_PPC64");
135 Define(Defs, "_LP64");
136 Define(Defs, "__LP64__");
137 Define(Defs, "__ppc64__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000138 } else {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000139 Define(Defs, "__ppc__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000140 }
141
142 // Target properties.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000143 Define(Defs, "_BIG_ENDIAN");
144 Define(Defs, "__BIG_ENDIAN__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000145
Reid Spencer5f016e22007-07-11 17:01:13 +0000146 // Subtarget options.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000147 Define(Defs, "__NATURAL_ALIGNMENT__");
148 Define(Defs, "__REGISTER_PREFIX__", "");
Reid Spencer5f016e22007-07-11 17:01:13 +0000149
Chris Lattner12f09262008-10-05 21:49:27 +0000150 // FIXME: Should be controlled by command line option.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000151 Define(Defs, "__LONG_DOUBLE_128__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000152}
153
154/// getX86Defines - Return a set of the X86-specific #defines that are
155/// not tied to a specific subtarget.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000156static void getX86Defines(std::vector<char> &Defs, bool is64Bit) {
Reid Spencer5f016e22007-07-11 17:01:13 +0000157 // Target identification.
158 if (is64Bit) {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000159 Define(Defs, "_LP64");
160 Define(Defs, "__LP64__");
161 Define(Defs, "__amd64__");
162 Define(Defs, "__amd64");
163 Define(Defs, "__x86_64");
164 Define(Defs, "__x86_64__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000165 } else {
Chris Lattnerd15fa822007-10-06 06:57:34 +0000166 Define(Defs, "__i386__");
167 Define(Defs, "__i386");
168 Define(Defs, "i386");
Reid Spencer5f016e22007-07-11 17:01:13 +0000169 }
170
171 // Target properties.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000172 Define(Defs, "__LITTLE_ENDIAN__");
Reid Spencer5f016e22007-07-11 17:01:13 +0000173
Reid Spencer5f016e22007-07-11 17:01:13 +0000174 // Subtarget options.
Chris Lattnerd15fa822007-10-06 06:57:34 +0000175 Define(Defs, "__nocona");
176 Define(Defs, "__nocona__");
177 Define(Defs, "__tune_nocona__");
178 Define(Defs, "__SSE2_MATH__");
179 Define(Defs, "__SSE2__");
180 Define(Defs, "__SSE_MATH__");
181 Define(Defs, "__SSE__");
182 Define(Defs, "__MMX__");
183 Define(Defs, "__REGISTER_PREFIX__", "");
Reid Spencer5f016e22007-07-11 17:01:13 +0000184}
185
Chris Lattnerd0c33d32008-04-21 20:19:54 +0000186/// getARMDefines - Return a set of the ARM-specific #defines that are
Chris Lattner393ff042008-04-21 18:56:49 +0000187/// not tied to a specific subtarget.
188static void getARMDefines(std::vector<char> &Defs) {
189 // Target identification.
190 Define(Defs, "__arm");
191 Define(Defs, "__arm__");
192
193 // Target properties.
194 Define(Defs, "__LITTLE_ENDIAN__");
195
Chris Lattner393ff042008-04-21 18:56:49 +0000196 // Subtarget options. [hard coded to v6 for now]
197 Define(Defs, "__ARM_ARCH_6K__");
198 Define(Defs, "__ARMEL__");
199 Define(Defs, "__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__", "20000");
Chris Lattner393ff042008-04-21 18:56:49 +0000200}
201
Eli Friedmane4277982008-08-20 23:11:40 +0000202//===----------------------------------------------------------------------===//
203// Specific target implementations.
204//===----------------------------------------------------------------------===//
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000205
Eli Friedmane4277982008-08-20 23:11:40 +0000206namespace {
207// PPC abstract base class
208class PPCTargetInfo : public TargetInfo {
209 static const Builtin::Info BuiltinInfo[];
210 static const char * const GCCRegNames[];
211 static const TargetInfo::GCCRegAlias GCCRegAliases[];
212
213public:
214 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) {
215 CharIsSigned = false;
216 }
217 virtual void getTargetBuiltins(const Builtin::Info *&Records,
218 unsigned &NumRecords) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000219 Records = BuiltinInfo;
Eli Friedmane4277982008-08-20 23:11:40 +0000220 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000221 }
Eli Friedmane4277982008-08-20 23:11:40 +0000222 virtual const char *getVAListDeclaration() const {
Chris Lattnerd5998502008-10-27 01:11:29 +0000223 return "typedef char* __builtin_va_list;";
224 // This is the right definition for ABI/V4: System V.4/eabi.
225 /*return "typedef struct __va_list_tag {"
Eli Friedmane4277982008-08-20 23:11:40 +0000226 " unsigned char gpr;"
227 " unsigned char fpr;"
228 " unsigned short reserved;"
229 " void* overflow_arg_area;"
230 " void* reg_save_area;"
Chris Lattnerd5998502008-10-27 01:11:29 +0000231 "} __builtin_va_list[1];";*/
Anders Carlsson3346ae62007-11-24 23:38:12 +0000232 }
Eli Friedmane4277982008-08-20 23:11:40 +0000233 virtual const char *getTargetPrefix() const {
234 return "ppc";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000235 }
Eli Friedmane4277982008-08-20 23:11:40 +0000236 virtual void getGCCRegNames(const char * const *&Names,
237 unsigned &NumNames) const;
238 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
239 unsigned &NumAliases) const;
240 virtual bool validateAsmConstraint(char c,
241 TargetInfo::ConstraintInfo &info) const {
Anders Carlssond04c6e22007-11-27 04:11:28 +0000242 switch (c) {
243 default: return false;
244 case 'O': // Zero
245 return true;
246 case 'b': // Base register
247 case 'f': // Floating point register
248 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
249 return true;
250 }
251 }
Eli Friedmane4277982008-08-20 23:11:40 +0000252 virtual const char *getClobbers() const {
253 return "";
Anders Carlssond04c6e22007-11-27 04:11:28 +0000254 }
Eli Friedmane4277982008-08-20 23:11:40 +0000255};
Anders Carlssond04c6e22007-11-27 04:11:28 +0000256
Eli Friedmane4277982008-08-20 23:11:40 +0000257const Builtin::Info PPCTargetInfo::BuiltinInfo[] = {
258#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
259#include "clang/AST/PPCBuiltins.def"
260};
Chris Lattner393ff042008-04-21 18:56:49 +0000261
Eli Friedmane4277982008-08-20 23:11:40 +0000262const char * const PPCTargetInfo::GCCRegNames[] = {
263 "0", "1", "2", "3", "4", "5", "6", "7",
264 "8", "9", "10", "11", "12", "13", "14", "15",
265 "16", "17", "18", "19", "20", "21", "22", "23",
266 "24", "25", "26", "27", "28", "29", "30", "31",
267 "0", "1", "2", "3", "4", "5", "6", "7",
268 "8", "9", "10", "11", "12", "13", "14", "15",
269 "16", "17", "18", "19", "20", "21", "22", "23",
270 "24", "25", "26", "27", "28", "29", "30", "31",
271 "mq", "lr", "ctr", "ap",
272 "0", "1", "2", "3", "4", "5", "6", "7",
273 "xer",
274 "0", "1", "2", "3", "4", "5", "6", "7",
275 "8", "9", "10", "11", "12", "13", "14", "15",
276 "16", "17", "18", "19", "20", "21", "22", "23",
277 "24", "25", "26", "27", "28", "29", "30", "31",
278 "vrsave", "vscr",
279 "spe_acc", "spefscr",
280 "sfp"
281};
Reid Spencer5f016e22007-07-11 17:01:13 +0000282
Eli Friedmane4277982008-08-20 23:11:40 +0000283void PPCTargetInfo::getGCCRegNames(const char * const *&Names,
284 unsigned &NumNames) const {
285 Names = GCCRegNames;
286 NumNames = llvm::array_lengthof(GCCRegNames);
287}
Reid Spencer5f016e22007-07-11 17:01:13 +0000288
Eli Friedmane4277982008-08-20 23:11:40 +0000289const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = {
290 // While some of these aliases do map to different registers
291 // they still share the same register name.
292 { { "cc", "cr0", "fr0", "r0", "v0"}, "0" },
293 { { "cr1", "fr1", "r1", "sp", "v1"}, "1" },
294 { { "cr2", "fr2", "r2", "toc", "v2"}, "2" },
295 { { "cr3", "fr3", "r3", "v3"}, "3" },
296 { { "cr4", "fr4", "r4", "v4"}, "4" },
297 { { "cr5", "fr5", "r5", "v5"}, "5" },
298 { { "cr6", "fr6", "r6", "v6"}, "6" },
299 { { "cr7", "fr7", "r7", "v7"}, "7" },
300 { { "fr8", "r8", "v8"}, "8" },
301 { { "fr9", "r9", "v9"}, "9" },
302 { { "fr10", "r10", "v10"}, "10" },
303 { { "fr11", "r11", "v11"}, "11" },
304 { { "fr12", "r12", "v12"}, "12" },
305 { { "fr13", "r13", "v13"}, "13" },
306 { { "fr14", "r14", "v14"}, "14" },
307 { { "fr15", "r15", "v15"}, "15" },
308 { { "fr16", "r16", "v16"}, "16" },
309 { { "fr17", "r17", "v17"}, "17" },
310 { { "fr18", "r18", "v18"}, "18" },
311 { { "fr19", "r19", "v19"}, "19" },
312 { { "fr20", "r20", "v20"}, "20" },
313 { { "fr21", "r21", "v21"}, "21" },
314 { { "fr22", "r22", "v22"}, "22" },
315 { { "fr23", "r23", "v23"}, "23" },
316 { { "fr24", "r24", "v24"}, "24" },
317 { { "fr25", "r25", "v25"}, "25" },
318 { { "fr26", "r26", "v26"}, "26" },
319 { { "fr27", "r27", "v27"}, "27" },
320 { { "fr28", "r28", "v28"}, "28" },
321 { { "fr29", "r29", "v29"}, "29" },
322 { { "fr30", "r30", "v30"}, "30" },
323 { { "fr31", "r31", "v31"}, "31" },
324};
325
326void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
327 unsigned &NumAliases) const {
328 Aliases = GCCRegAliases;
329 NumAliases = llvm::array_lengthof(GCCRegAliases);
330}
331} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +0000332
333namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000334class PPC32TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000335public:
Eli Friedmaned855cb2008-08-21 00:13:15 +0000336 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
337 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
338 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
339 }
Chris Lattnerd15fa822007-10-06 06:57:34 +0000340 virtual void getTargetDefines(std::vector<char> &Defines) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000341 getPowerPCDefines(Defines, false);
342 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000343};
344} // end anonymous namespace.
345
346namespace {
Eli Friedmane4277982008-08-20 23:11:40 +0000347class PPC64TargetInfo : public PPCTargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000348public:
Eli Friedmane4277982008-08-20 23:11:40 +0000349 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000350 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000351 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
352 "i64:64:64-f32:32:32-f64:64:64-v128:128:128";
Chris Lattnerf291b102008-05-09 06:17:04 +0000353 }
Chris Lattnerd15fa822007-10-06 06:57:34 +0000354 virtual void getTargetDefines(std::vector<char> &Defines) const {
Reid Spencer5f016e22007-07-11 17:01:13 +0000355 getPowerPCDefines(Defines, true);
356 }
Eli Friedmane4277982008-08-20 23:11:40 +0000357};
358} // end anonymous namespace.
359
360namespace {
361class DarwinPPCTargetInfo : public PPC32TargetInfo {
362public:
363 DarwinPPCTargetInfo(const std::string& triple) : PPC32TargetInfo(triple) {}
364 virtual void getTargetDefines(std::vector<char> &Defines) const {
365 PPC32TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000366 getDarwinDefines(Defines, getTargetTriple());
Reid Spencer5f016e22007-07-11 17:01:13 +0000367 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000368
369 virtual bool useNeXTRuntimeAsDefault() const { return true; }
Eli Friedmane4277982008-08-20 23:11:40 +0000370};
371} // end anonymous namespace.
372
373namespace {
374class DarwinPPC64TargetInfo : public PPC64TargetInfo {
375public:
376 DarwinPPC64TargetInfo(const std::string& triple) : PPC64TargetInfo(triple) {}
377 virtual void getTargetDefines(std::vector<char> &Defines) const {
378 PPC64TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000379 getDarwinDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +0000380 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000381
382 virtual bool useNeXTRuntimeAsDefault() const { return true; }
Reid Spencer5f016e22007-07-11 17:01:13 +0000383};
384} // end anonymous namespace.
385
386namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000387// Namespace for x86 abstract base class
388const Builtin::Info BuiltinInfo[] = {
389#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
390#include "clang/AST/X86Builtins.def"
391};
Eli Friedman61538a72008-05-20 14:21:01 +0000392
Eli Friedman618234a2008-08-20 02:34:37 +0000393const char *GCCRegNames[] = {
394 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp",
395 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)",
396 "argp", "flags", "fspr", "dirflag", "frame",
397 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7",
398 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7",
399 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
400 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
401};
402
403const TargetInfo::GCCRegAlias GCCRegAliases[] = {
404 { { "al", "ah", "eax", "rax" }, "ax" },
405 { { "bl", "bh", "ebx", "rbx" }, "bx" },
406 { { "cl", "ch", "ecx", "rcx" }, "cx" },
407 { { "dl", "dh", "edx", "rdx" }, "dx" },
408 { { "esi", "rsi" }, "si" },
409 { { "edi", "rdi" }, "di" },
410 { { "esp", "rsp" }, "sp" },
411 { { "ebp", "rbp" }, "bp" },
412};
413
414// X86 target abstract base class; x86-32 and x86-64 are very close, so
415// most of the implementation can be shared.
416class X86TargetInfo : public TargetInfo {
417public:
418 X86TargetInfo(const std::string& triple) : TargetInfo(triple) {
419 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended;
Reid Spencer5f016e22007-07-11 17:01:13 +0000420 }
421 virtual void getTargetBuiltins(const Builtin::Info *&Records,
422 unsigned &NumRecords) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000423 Records = BuiltinInfo;
424 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin;
Reid Spencer5f016e22007-07-11 17:01:13 +0000425 }
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000426 virtual const char *getTargetPrefix() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000427 return "x86";
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000428 }
Anders Carlsson3346ae62007-11-24 23:38:12 +0000429 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedman618234a2008-08-20 02:34:37 +0000430 unsigned &NumNames) const {
431 Names = GCCRegNames;
432 NumNames = llvm::array_lengthof(GCCRegNames);
Anders Carlsson3346ae62007-11-24 23:38:12 +0000433 }
434 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
435 unsigned &NumAliases) const {
Eli Friedman618234a2008-08-20 02:34:37 +0000436 Aliases = GCCRegAliases;
437 NumAliases = llvm::array_lengthof(GCCRegAliases);
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000438 }
Anders Carlssond04c6e22007-11-27 04:11:28 +0000439 virtual bool validateAsmConstraint(char c,
Eli Friedman618234a2008-08-20 02:34:37 +0000440 TargetInfo::ConstraintInfo &info) const;
441 virtual std::string convertConstraint(const char Constraint) const;
Anders Carlssond04c6e22007-11-27 04:11:28 +0000442 virtual const char *getClobbers() const {
Eli Friedman618234a2008-08-20 02:34:37 +0000443 return "~{dirflag},~{fpsr},~{flags}";
444 }
Reid Spencer5f016e22007-07-11 17:01:13 +0000445};
Eli Friedman618234a2008-08-20 02:34:37 +0000446
447bool
448X86TargetInfo::validateAsmConstraint(char c,
449 TargetInfo::ConstraintInfo &info) const {
450 switch (c) {
451 default: return false;
452 case 'a': // eax.
453 case 'b': // ebx.
454 case 'c': // ecx.
455 case 'd': // edx.
456 case 'S': // esi.
457 case 'D': // edi.
458 case 'A': // edx:eax.
459 case 't': // top of floating point stack.
460 case 'u': // second from top of floating point stack.
461 case 'q': // Any register accessible as [r]l: a, b, c, and d.
Anders Carlssonfce09342008-10-06 00:41:45 +0000462 case 'y': // Any MMX register.
Anders Carlssona7406d42008-10-06 19:17:39 +0000463 case 'x': // Any SSE register.
Eli Friedman618234a2008-08-20 02:34:37 +0000464 case 'Q': // Any register accessible as [r]h: a, b, c, and d.
465 case 'Z': // 32-bit integer constant for use with zero-extending x86_64
466 // instructions.
467 case 'N': // unsigned 8-bit integer constant for use with in and out
468 // instructions.
469 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
470 return true;
471 }
472}
473
474std::string
475X86TargetInfo::convertConstraint(const char Constraint) const {
476 switch (Constraint) {
477 case 'a': return std::string("{ax}");
478 case 'b': return std::string("{bx}");
479 case 'c': return std::string("{cx}");
480 case 'd': return std::string("{dx}");
481 case 'S': return std::string("{si}");
482 case 'D': return std::string("{di}");
483 case 't': // top of floating point stack.
484 return std::string("{st}");
485 case 'u': // second from top of floating point stack.
486 return std::string("{st(1)}"); // second from top of floating point stack.
487 default:
488 return std::string(1, Constraint);
489 }
490}
Eli Friedman618234a2008-08-20 02:34:37 +0000491} // end anonymous namespace
Reid Spencer5f016e22007-07-11 17:01:13 +0000492
493namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000494// X86-32 generic target
495class X86_32TargetInfo : public X86TargetInfo {
Reid Spencer5f016e22007-07-11 17:01:13 +0000496public:
Eli Friedman618234a2008-08-20 02:34:37 +0000497 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
498 DoubleAlign = LongLongAlign = 32;
499 LongDoubleWidth = 96;
500 LongDoubleAlign = 32;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000501 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
502 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
503 "a0:0:64-f80:32:32";
Eli Friedman618234a2008-08-20 02:34:37 +0000504 }
505 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000506 return "typedef char* __builtin_va_list;";
Eli Friedman618234a2008-08-20 02:34:37 +0000507 }
508 virtual void getTargetDefines(std::vector<char> &Defines) const {
509 getX86Defines(Defines, false);
510 }
511};
512} // end anonymous namespace
513
514namespace {
515// x86-32 Darwin (OS X) target
516class DarwinI386TargetInfo : public X86_32TargetInfo {
517public:
518 DarwinI386TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
519 LongDoubleWidth = 128;
520 LongDoubleAlign = 128;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000521 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
522 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
523 "a0:0:64-f80:128:128";
Eli Friedman618234a2008-08-20 02:34:37 +0000524 }
525 virtual void getTargetDefines(std::vector<char> &Defines) const {
526 X86_32TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000527 getDarwinDefines(Defines, getTargetTriple());
Eli Friedman618234a2008-08-20 02:34:37 +0000528 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000529 virtual bool useNeXTRuntimeAsDefault() const { return true; }
Eli Friedman618234a2008-08-20 02:34:37 +0000530};
531} // end anonymous namespace
532
533namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000534// x86-32 FreeBSD target
535class FreeBSDX86_32TargetInfo : public X86_32TargetInfo {
536public:
537 FreeBSDX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
538 }
539 virtual void getTargetDefines(std::vector<char> &Defines) const {
540 X86_32TargetInfo::getTargetDefines(Defines);
541 getFreeBSDDefines(Defines, 0, getTargetTriple());
542 }
543};
544} // end anonymous namespace
545
546namespace {
Chris Lattnereac7aee2008-08-23 18:23:14 +0000547// x86-32 DragonFly target
548class DragonFlyX86_32TargetInfo : public X86_32TargetInfo {
549public:
550 DragonFlyX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
551 }
552 virtual void getTargetDefines(std::vector<char> &Defines) const {
553 X86_32TargetInfo::getTargetDefines(Defines);
554 getDragonFlyDefines(Defines);
555 }
556};
557} // end anonymous namespace
558
559namespace {
Eli Friedman0d4047b2008-08-21 00:24:02 +0000560// x86-32 Linux target
561class LinuxX86_32TargetInfo : public X86_32TargetInfo {
562public:
563 LinuxX86_32TargetInfo(const std::string& triple) : X86_32TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000564 UserLabelPrefix = "";
Eli Friedman0d4047b2008-08-21 00:24:02 +0000565 }
566 virtual void getTargetDefines(std::vector<char> &Defines) const {
567 X86_32TargetInfo::getTargetDefines(Defines);
568 getLinuxDefines(Defines);
569 }
570};
571} // end anonymous namespace
572
573namespace {
Eli Friedman29a30502008-08-21 01:40:19 +0000574// x86-32 Windows target
575class WindowsX86_32TargetInfo : public X86_32TargetInfo {
576public:
577 WindowsX86_32TargetInfo(const std::string& triple)
578 : X86_32TargetInfo(triple) {
579 // FIXME: Fix wchar_t.
580 // FIXME: We should probably enable -fms-extensions by default for
581 // this target.
582 }
583 virtual void getTargetDefines(std::vector<char> &Defines) const {
584 X86_32TargetInfo::getTargetDefines(Defines);
585 // This list is based off of the the list of things MingW defines
586 Define(Defines, "__WIN32__");
587 Define(Defines, "__WIN32");
588 Define(Defines, "_WIN32");
589 Define(Defines, "WIN32");
590 Define(Defines, "__WINNT__");
591 Define(Defines, "__WINNT");
592 Define(Defines, "WINNT");
Eli Friedman29a30502008-08-21 01:40:19 +0000593 Define(Defines, "_X86_");
594 Define(Defines, "__MSVCRT__");
595 }
596};
597} // end anonymous namespace
598
599namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000600// x86-64 generic target
601class X86_64TargetInfo : public X86TargetInfo {
602public:
603 X86_64TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
Chris Lattnerf291b102008-05-09 06:17:04 +0000604 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedman61538a72008-05-20 14:21:01 +0000605 LongDoubleWidth = 128;
606 LongDoubleAlign = 128;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000607 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
608 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-"
609 "a0:0:64-f80:128:128";
Reid Spencer5f016e22007-07-11 17:01:13 +0000610 }
Anders Carlssonfb5e5ba2007-10-13 00:45:48 +0000611 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000612 return "typedef struct __va_list_tag {"
613 " unsigned gp_offset;"
614 " unsigned fp_offset;"
615 " void* overflow_arg_area;"
616 " void* reg_save_area;"
617 "} __builtin_va_list[1];";
Anders Carlsson3346ae62007-11-24 23:38:12 +0000618 }
Eli Friedman618234a2008-08-20 02:34:37 +0000619 virtual void getTargetDefines(std::vector<char> &Defines) const {
620 getX86Defines(Defines, true);
Anders Carlsson44fe49c2007-12-08 19:32:57 +0000621 }
Eli Friedman618234a2008-08-20 02:34:37 +0000622};
623} // end anonymous namespace
624
625namespace {
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000626// x86-64 FreeBSD target
627class FreeBSDX86_64TargetInfo : public X86_64TargetInfo {
628public:
629 FreeBSDX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
630 }
631 virtual void getTargetDefines(std::vector<char> &Defines) const {
632 X86_64TargetInfo::getTargetDefines(Defines);
633 getFreeBSDDefines(Defines, 1, getTargetTriple());
634 }
635};
636} // end anonymous namespace
637
638namespace {
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000639// x86-64 Linux target
640class LinuxX86_64TargetInfo : public X86_64TargetInfo {
641public:
642 LinuxX86_64TargetInfo(const std::string& triple) : X86_64TargetInfo(triple) {
Chris Lattner9b533162008-10-05 19:44:25 +0000643 UserLabelPrefix = "";
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000644 }
645 virtual void getTargetDefines(std::vector<char> &Defines) const {
646 X86_64TargetInfo::getTargetDefines(Defines);
647 getLinuxDefines(Defines);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000648 }
649};
650} // end anonymous namespace
651
652namespace {
Eli Friedman618234a2008-08-20 02:34:37 +0000653// x86-64 Darwin (OS X) target
654class DarwinX86_64TargetInfo : public X86_64TargetInfo {
655public:
656 DarwinX86_64TargetInfo(const std::string& triple) :
657 X86_64TargetInfo(triple) {}
658
659 virtual void getTargetDefines(std::vector<char> &Defines) const {
660 X86_64TargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000661 getDarwinDefines(Defines, getTargetTriple());
Anders Carlsson3346ae62007-11-24 23:38:12 +0000662 }
Daniel Dunbardcb4a1a2008-08-23 08:43:39 +0000663
664 virtual bool useNeXTRuntimeAsDefault() const { return true; }
Reid Spencer5f016e22007-07-11 17:01:13 +0000665};
666} // end anonymous namespace.
667
Chris Lattner393ff042008-04-21 18:56:49 +0000668namespace {
Eli Friedmana9f54962008-08-20 07:44:10 +0000669class ARMTargetInfo : public TargetInfo {
Chris Lattner393ff042008-04-21 18:56:49 +0000670public:
Eli Friedmana9f54962008-08-20 07:44:10 +0000671 ARMTargetInfo(const std::string& triple) : TargetInfo(triple) {
672 // FIXME: Are the defaults correct for ARM?
Eli Friedmaned855cb2008-08-21 00:13:15 +0000673 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
674 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:64";
Eli Friedman61538a72008-05-20 14:21:01 +0000675 }
Chris Lattner393ff042008-04-21 18:56:49 +0000676 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner393ff042008-04-21 18:56:49 +0000677 getARMDefines(Defines);
678 }
679 virtual void getTargetBuiltins(const Builtin::Info *&Records,
680 unsigned &NumRecords) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000681 // FIXME: Implement.
682 Records = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000683 NumRecords = 0;
684 }
685 virtual const char *getVAListDeclaration() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000686 return "typedef char* __builtin_va_list;";
Chris Lattner393ff042008-04-21 18:56:49 +0000687 }
688 virtual const char *getTargetPrefix() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000689 return "arm";
Chris Lattner393ff042008-04-21 18:56:49 +0000690 }
Chris Lattner393ff042008-04-21 18:56:49 +0000691 virtual void getGCCRegNames(const char * const *&Names,
692 unsigned &NumNames) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000693 // FIXME: Implement.
694 Names = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000695 NumNames = 0;
696 }
697 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
698 unsigned &NumAliases) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000699 // FIXME: Implement.
700 Aliases = 0;
Chris Lattner393ff042008-04-21 18:56:49 +0000701 NumAliases = 0;
702 }
703 virtual bool validateAsmConstraint(char c,
Nate Begemanad487f42008-04-22 05:03:19 +0000704 TargetInfo::ConstraintInfo &info) const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000705 // FIXME: Check if this is complete
Nate Begemanad487f42008-04-22 05:03:19 +0000706 switch (c) {
Eli Friedmana9f54962008-08-20 07:44:10 +0000707 default:
Nate Begemanad487f42008-04-22 05:03:19 +0000708 case 'l': // r0-r7
709 case 'h': // r8-r15
710 case 'w': // VFP Floating point register single precision
711 case 'P': // VFP Floating point register double precision
712 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
713 return true;
714 }
Chris Lattner393ff042008-04-21 18:56:49 +0000715 return false;
716 }
717 virtual const char *getClobbers() const {
Eli Friedmana9f54962008-08-20 07:44:10 +0000718 // FIXME: Is this really right?
Chris Lattner393ff042008-04-21 18:56:49 +0000719 return "";
720 }
721};
722} // end anonymous namespace.
723
Eli Friedmana9f54962008-08-20 07:44:10 +0000724
725namespace {
726class DarwinARMTargetInfo : public ARMTargetInfo {
727public:
728 DarwinARMTargetInfo(const std::string& triple) : ARMTargetInfo(triple) {}
729
730 virtual void getTargetDefines(std::vector<char> &Defines) const {
731 ARMTargetInfo::getTargetDefines(Defines);
Chris Lattner8b30c412008-09-30 01:00:25 +0000732 getDarwinDefines(Defines, getTargetTriple());
Eli Friedmana9f54962008-08-20 07:44:10 +0000733 }
734};
735} // end anonymous namespace.
736
Reid Spencer5f016e22007-07-11 17:01:13 +0000737namespace {
Eli Friedman01b86682008-08-20 07:28:14 +0000738class SparcV8TargetInfo : public TargetInfo {
Gabor Greif26658672008-02-21 16:29:08 +0000739public:
Eli Friedman01b86682008-08-20 07:28:14 +0000740 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) {
741 // FIXME: Support Sparc quad-precision long double?
Eli Friedmaned855cb2008-08-21 00:13:15 +0000742 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
743 "i64:64:64-f32:32:32-f64:64:64-v64:64:64";
Eli Friedman01b86682008-08-20 07:28:14 +0000744 }
Gabor Greif26658672008-02-21 16:29:08 +0000745 virtual void getTargetDefines(std::vector<char> &Defines) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000746 // FIXME: This is missing a lot of important defines; some of the
747 // missing stuff is likely to break system headers.
Gabor Greif26658672008-02-21 16:29:08 +0000748 Define(Defines, "__sparc");
Eli Friedmanbf0c9bd2008-05-25 05:26:09 +0000749 Define(Defines, "__sparc__");
Gabor Greif26658672008-02-21 16:29:08 +0000750 Define(Defines, "__sparcv8");
751 }
752 virtual void getTargetBuiltins(const Builtin::Info *&Records,
753 unsigned &NumRecords) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000754 // FIXME: Implement!
Gabor Greif26658672008-02-21 16:29:08 +0000755 }
756 virtual const char *getVAListDeclaration() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000757 return "typedef void* __builtin_va_list;";
Gabor Greif26658672008-02-21 16:29:08 +0000758 }
759 virtual const char *getTargetPrefix() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000760 return "sparc";
Gabor Greif26658672008-02-21 16:29:08 +0000761 }
762 virtual void getGCCRegNames(const char * const *&Names,
763 unsigned &NumNames) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000764 // FIXME: Implement!
765 Names = 0;
766 NumNames = 0;
Gabor Greif26658672008-02-21 16:29:08 +0000767 }
768 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
769 unsigned &NumAliases) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000770 // FIXME: Implement!
771 Aliases = 0;
772 NumAliases = 0;
Gabor Greif26658672008-02-21 16:29:08 +0000773 }
774 virtual bool validateAsmConstraint(char c,
775 TargetInfo::ConstraintInfo &info) const {
Eli Friedman01b86682008-08-20 07:28:14 +0000776 // FIXME: Implement!
777 return false;
Gabor Greif26658672008-02-21 16:29:08 +0000778 }
779 virtual const char *getClobbers() const {
Eli Friedman01b86682008-08-20 07:28:14 +0000780 // FIXME: Implement!
781 return "";
Gabor Greif26658672008-02-21 16:29:08 +0000782 }
783};
784
785} // end anonymous namespace.
786
Eli Friedman01b86682008-08-20 07:28:14 +0000787namespace {
788class SolarisSparcV8TargetInfo : public SparcV8TargetInfo {
789public:
790 SolarisSparcV8TargetInfo(const std::string& triple) :
791 SparcV8TargetInfo(triple) {}
792
793 virtual void getTargetDefines(std::vector<char> &Defines) const {
794 SparcV8TargetInfo::getTargetDefines(Defines);
795 getSolarisDefines(Defines);
796 }
797};
798} // end anonymous namespace.
Reid Spencer5f016e22007-07-11 17:01:13 +0000799
Chris Lattner2621fd12008-05-08 05:58:21 +0000800namespace {
801 class PIC16TargetInfo : public TargetInfo{
802 public:
803 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) {
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +0000804 IntWidth = 16;
805 LongWidth = LongLongWidth = 32;
806 PointerWidth = 16;
807 IntAlign = 8;
808 LongAlign = LongLongAlign = 8;
Eli Friedman61538a72008-05-20 14:21:01 +0000809 PointerAlign = 8;
Sanjiv Gupta31fc07d2008-10-31 09:52:39 +0000810 SizeType = UnsignedInt;
811 IntMaxType = SignedLong;
812 UIntMaxType = UnsignedLong;
813 PtrDiffType = SignedShort;
814 WCharType = UnsignedInt;
Sanjiv Gupta364af812008-08-18 10:05:22 +0000815 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8";
Chris Lattner2621fd12008-05-08 05:58:21 +0000816 }
Chris Lattner927686f2008-05-09 06:08:39 +0000817 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; }
818 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; }
Chris Lattner2621fd12008-05-08 05:58:21 +0000819 virtual void getTargetDefines(std::vector<char> &Defines) const {
820 Define(Defines, "__pic16");
821 }
822 virtual void getTargetBuiltins(const Builtin::Info *&Records,
823 unsigned &NumRecords) const {}
824 virtual const char *getVAListDeclaration() const { return "";}
825 virtual const char *getClobbers() const {return "";}
826 virtual const char *getTargetPrefix() const {return "";}
827 virtual void getGCCRegNames(const char * const *&Names,
828 unsigned &NumNames) const {}
829 virtual bool validateAsmConstraint(char c,
830 TargetInfo::ConstraintInfo &info) const {
831 return true;
832 }
833 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
834 unsigned &NumAliases) const {}
835 virtual bool useGlobalsForAutomaticVariables() const {return true;}
836 };
837}
838
Reid Spencer5f016e22007-07-11 17:01:13 +0000839//===----------------------------------------------------------------------===//
840// Driver code
841//===----------------------------------------------------------------------===//
842
Ted Kremenek8448d382007-12-04 17:07:35 +0000843static inline bool IsX86(const std::string& TT) {
Ted Kremenekae360762007-12-03 22:06:55 +0000844 return (TT.size() >= 5 && TT[0] == 'i' && TT[2] == '8' && TT[3] == '6' &&
845 TT[4] == '-' && TT[1] - '3' < 6);
846}
847
Chris Lattner42e67372008-03-05 01:18:20 +0000848/// CreateTargetInfo - Return the target info object for the specified target
849/// triple.
850TargetInfo* TargetInfo::CreateTargetInfo(const std::string &T) {
Eli Friedmaned855cb2008-08-21 00:13:15 +0000851 // OS detection; this isn't really anywhere near complete.
852 // Additions and corrections are welcome.
853 bool isDarwin = T.find("-darwin") != std::string::npos;
Chris Lattnereac7aee2008-08-23 18:23:14 +0000854 bool isDragonFly = T.find("-dragonfly") != std::string::npos;
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000855 bool isFreeBSD = T.find("-freebsd") != std::string::npos;
Eli Friedmaned855cb2008-08-21 00:13:15 +0000856 bool isSolaris = T.find("-solaris") != std::string::npos;
857 bool isLinux = T.find("-linux") != std::string::npos;
858 bool isWindows = T.find("-windows") != std::string::npos ||
859 T.find("-win32") != std::string::npos ||
860 T.find("-mingw") != std::string::npos;
Eli Friedman61538a72008-05-20 14:21:01 +0000861
Eli Friedmaned855cb2008-08-21 00:13:15 +0000862 if (T.find("ppc-") == 0 || T.find("powerpc-") == 0) {
863 if (isDarwin)
864 return new DarwinPPCTargetInfo(T);
865 return new PPC32TargetInfo(T);
866 }
Eli Friedman61538a72008-05-20 14:21:01 +0000867
Eli Friedmaned855cb2008-08-21 00:13:15 +0000868 if (T.find("ppc64-") == 0 || T.find("powerpc64-") == 0) {
869 if (isDarwin)
870 return new DarwinPPC64TargetInfo(T);
871 return new PPC64TargetInfo(T);
872 }
Chris Lattner393ff042008-04-21 18:56:49 +0000873
Eli Friedmaned855cb2008-08-21 00:13:15 +0000874 if (T.find("armv6-") == 0 || T.find("arm-") == 0) {
875 if (isDarwin)
876 return new DarwinARMTargetInfo(T);
877 return new ARMTargetInfo(T);
878 }
Eli Friedman61538a72008-05-20 14:21:01 +0000879
Eli Friedmaned855cb2008-08-21 00:13:15 +0000880 if (T.find("sparc-") == 0) {
881 if (isSolaris)
882 return new SolarisSparcV8TargetInfo(T);
883 return new SparcV8TargetInfo(T);
884 }
885
886 if (T.find("x86_64-") == 0) {
887 if (isDarwin)
888 return new DarwinX86_64TargetInfo(T);
Daniel Dunbarb55a42b2008-09-23 17:37:57 +0000889 if (isLinux)
890 return new LinuxX86_64TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000891 if (isFreeBSD)
892 return new FreeBSDX86_64TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +0000893 return new X86_64TargetInfo(T);
894 }
Eli Friedman61538a72008-05-20 14:21:01 +0000895
Chris Lattner2621fd12008-05-08 05:58:21 +0000896 if (T.find("pic16-") == 0)
897 return new PIC16TargetInfo(T);
898
Eli Friedmaned855cb2008-08-21 00:13:15 +0000899 if (IsX86(T)) {
900 if (isDarwin)
901 return new DarwinI386TargetInfo(T);
Eli Friedman0d4047b2008-08-21 00:24:02 +0000902 if (isLinux)
903 return new LinuxX86_32TargetInfo(T);
Chris Lattnereac7aee2008-08-23 18:23:14 +0000904 if (isDragonFly)
905 return new DragonFlyX86_32TargetInfo(T);
Chris Lattnerfd0269d2008-10-16 17:04:31 +0000906 if (isFreeBSD)
907 return new FreeBSDX86_32TargetInfo(T);
Eli Friedman29a30502008-08-21 01:40:19 +0000908 if (isWindows)
909 return new WindowsX86_32TargetInfo(T);
Eli Friedmaned855cb2008-08-21 00:13:15 +0000910 return new X86_32TargetInfo(T);
911 }
Eli Friedman61538a72008-05-20 14:21:01 +0000912
Chris Lattner42e67372008-03-05 01:18:20 +0000913 return NULL;
Reid Spencer5f016e22007-07-11 17:01:13 +0000914}
Ted Kremenekfb79f7c2008-03-04 17:47:18 +0000915