blob: fcd105a7aafb0ddd7cef32114ca7e064a893800a [file] [log] [blame]
Chris Lattner5ba61f02006-10-14 07:39:34 +00001//===--- Targets.cpp - Implement -arch option and targets -----------------===//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner5b12ab82007-12-29 19:59:25 +00005// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
Chris Lattner5ba61f02006-10-14 07:39:34 +00007//
8//===----------------------------------------------------------------------===//
9//
Ted Kremenek6f6ff372007-12-12 18:05:32 +000010// This file implements construction of a TargetInfo object from a
11// target triple.
Chris Lattner5ba61f02006-10-14 07:39:34 +000012//
13//===----------------------------------------------------------------------===//
14
Chris Lattner10a5b382007-01-29 05:24:35 +000015#include "clang/AST/Builtins.h"
Anders Carlsson895af082007-12-09 23:17:02 +000016#include "clang/AST/TargetBuiltins.h"
Chris Lattner5ba61f02006-10-14 07:39:34 +000017#include "clang/Basic/Diagnostic.h"
18#include "clang/Basic/TargetInfo.h"
Anders Carlsson5fa3f342007-11-24 23:38:12 +000019#include "llvm/ADT/STLExtras.h"
Ted Kremenekb0615542007-12-03 22:06:55 +000020
Chris Lattner5ba61f02006-10-14 07:39:34 +000021using namespace clang;
22
Chris Lattner5ba61f02006-10-14 07:39:34 +000023//===----------------------------------------------------------------------===//
Chris Lattner1f5ad112006-10-14 18:32:12 +000024// Common code shared among targets.
Chris Lattner5ba61f02006-10-14 07:39:34 +000025//===----------------------------------------------------------------------===//
26
Chris Lattnerb2d486a2007-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
37
Chris Lattner5ba61f02006-10-14 07:39:34 +000038namespace {
39class DarwinTargetInfo : public TargetInfoImpl {
40public:
Ted Kremenekb0615542007-12-03 22:06:55 +000041 DarwinTargetInfo(const std::string& triple) : TargetInfoImpl(triple) {}
42
Chris Lattnerb2d486a2007-10-06 06:57:34 +000043 virtual void getTargetDefines(std::vector<char> &Defs) const {
Chris Lattner253023b2007-10-17 06:04:46 +000044// FIXME: we need a real target configuration system. For now, only define
45// __APPLE__ if the host has it.
46#ifdef __APPLE__
Chris Lattnerb2d486a2007-10-06 06:57:34 +000047 Define(Defs, "__APPLE__");
48 Define(Defs, "__MACH__");
Chris Lattner253023b2007-10-17 06:04:46 +000049#endif
Chris Lattner9c837532006-10-15 01:05:46 +000050
51 if (1) {// -fobjc-gc controls this.
Chris Lattnerb2d486a2007-10-06 06:57:34 +000052 Define(Defs, "__weak", "");
53 Define(Defs, "__strong", "");
Chris Lattner9c837532006-10-15 01:05:46 +000054 } else {
Chris Lattnerb2d486a2007-10-06 06:57:34 +000055 Define(Defs, "__weak", "__attribute__((objc_gc(weak)))");
56 Define(Defs, "__strong", "__attribute__((objc_gc(strong)))");
57 Define(Defs, "__OBJC_GC__");
Chris Lattner9c837532006-10-15 01:05:46 +000058 }
59
60 // darwin_constant_cfstrings controls this.
Chris Lattnerb2d486a2007-10-06 06:57:34 +000061 Define(Defs, "__CONSTANT_CFSTRINGS__");
Chris Lattner9c837532006-10-15 01:05:46 +000062
63 if (0) // darwin_pascal_strings
Chris Lattnerb2d486a2007-10-06 06:57:34 +000064 Define(Defs, "__PASCAL_STRINGS__");
Chris Lattner1f5ad112006-10-14 18:32:12 +000065 }
66
Chris Lattner5ba61f02006-10-14 07:39:34 +000067};
68} // end anonymous namespace.
69
70
Chris Lattner1f5ad112006-10-14 18:32:12 +000071/// getPowerPCDefines - Return a set of the PowerPC-specific #defines that are
72/// not tied to a specific subtarget.
Chris Lattnerb2d486a2007-10-06 06:57:34 +000073static void getPowerPCDefines(std::vector<char> &Defs, bool is64Bit) {
Chris Lattner9c837532006-10-15 01:05:46 +000074 // Target identification.
Chris Lattnerb2d486a2007-10-06 06:57:34 +000075 Define(Defs, "__ppc__");
76 Define(Defs, "_ARCH_PPC");
77 Define(Defs, "__POWERPC__");
Chris Lattner9c837532006-10-15 01:05:46 +000078 if (is64Bit) {
Chris Lattnerb2d486a2007-10-06 06:57:34 +000079 Define(Defs, "_ARCH_PPC64");
80 Define(Defs, "_LP64");
81 Define(Defs, "__LP64__");
82 Define(Defs, "__ppc64__");
Chris Lattner9c837532006-10-15 01:05:46 +000083 } else {
Chris Lattnerb2d486a2007-10-06 06:57:34 +000084 Define(Defs, "__ppc__");
Chris Lattner9c837532006-10-15 01:05:46 +000085 }
Chris Lattner1f5ad112006-10-14 18:32:12 +000086
Chris Lattner9c837532006-10-15 01:05:46 +000087 // Target properties.
Chris Lattnerb2d486a2007-10-06 06:57:34 +000088 Define(Defs, "_BIG_ENDIAN");
89 Define(Defs, "__BIG_ENDIAN__");
Chris Lattner9c837532006-10-15 01:05:46 +000090
91 if (is64Bit) {
Chris Lattnerb2d486a2007-10-06 06:57:34 +000092 Define(Defs, "__INTMAX_MAX__", "9223372036854775807L");
93 Define(Defs, "__INTMAX_TYPE__", "long int");
94 Define(Defs, "__LONG_MAX__", "9223372036854775807L");
95 Define(Defs, "__PTRDIFF_TYPE__", "long int");
96 Define(Defs, "__UINTMAX_TYPE__", "long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +000097 } else {
Chris Lattnerb2d486a2007-10-06 06:57:34 +000098 Define(Defs, "__INTMAX_MAX__", "9223372036854775807LL");
99 Define(Defs, "__INTMAX_TYPE__", "long long int");
100 Define(Defs, "__LONG_MAX__", "2147483647L");
101 Define(Defs, "__PTRDIFF_TYPE__", "int");
102 Define(Defs, "__UINTMAX_TYPE__", "long long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +0000103 }
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000104 Define(Defs, "__INT_MAX__", "2147483647");
105 Define(Defs, "__LONG_LONG_MAX__", "9223372036854775807LL");
106 Define(Defs, "__CHAR_BIT__", "8");
107 Define(Defs, "__SCHAR_MAX__", "127");
108 Define(Defs, "__SHRT_MAX__", "32767");
109 Define(Defs, "__SIZE_TYPE__", "long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +0000110
111 // Subtarget options.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000112 Define(Defs, "__USER_LABEL_PREFIX__", "_");
113 Define(Defs, "__NATURAL_ALIGNMENT__");
114 Define(Defs, "__REGISTER_PREFIX__", "");
Chris Lattner9c837532006-10-15 01:05:46 +0000115
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000116 Define(Defs, "__WCHAR_MAX__", "2147483647");
117 Define(Defs, "__WCHAR_TYPE__", "int");
118 Define(Defs, "__WINT_TYPE__", "int");
Chris Lattner9c837532006-10-15 01:05:46 +0000119
120 // Float macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000121 Define(Defs, "__FLT_DENORM_MIN__", "1.40129846e-45F");
122 Define(Defs, "__FLT_DIG__", "6");
123 Define(Defs, "__FLT_EPSILON__", "1.19209290e-7F");
124 Define(Defs, "__FLT_EVAL_METHOD__", "0");
125 Define(Defs, "__FLT_HAS_INFINITY__");
126 Define(Defs, "__FLT_HAS_QUIET_NAN__");
127 Define(Defs, "__FLT_MANT_DIG__", "24");
128 Define(Defs, "__FLT_MAX_10_EXP__", "38");
129 Define(Defs, "__FLT_MAX_EXP__", "128");
130 Define(Defs, "__FLT_MAX__", "3.40282347e+38F");
131 Define(Defs, "__FLT_MIN_10_EXP__", "(-37)");
132 Define(Defs, "__FLT_MIN_EXP__", "(-125)");
133 Define(Defs, "__FLT_MIN__", "1.17549435e-38F");
134 Define(Defs, "__FLT_RADIX__", "2");
Chris Lattner9c837532006-10-15 01:05:46 +0000135
136 // double macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000137 Define(Defs, "__DBL_DENORM_MIN__", "4.9406564584124654e-324");
138 Define(Defs, "__DBL_DIG__", "15");
139 Define(Defs, "__DBL_EPSILON__", "2.2204460492503131e-16");
140 Define(Defs, "__DBL_HAS_INFINITY__");
141 Define(Defs, "__DBL_HAS_QUIET_NAN__");
142 Define(Defs, "__DBL_MANT_DIG__", "53");
143 Define(Defs, "__DBL_MAX_10_EXP__", "308");
144 Define(Defs, "__DBL_MAX_EXP__", "1024");
145 Define(Defs, "__DBL_MAX__", "1.7976931348623157e+308");
146 Define(Defs, "__DBL_MIN_10_EXP__", "(-307)");
147 Define(Defs, "__DBL_MIN_EXP__", "(-1021)");
148 Define(Defs, "__DBL_MIN__", "2.2250738585072014e-308");
149 Define(Defs, "__DECIMAL_DIG__", "33");
Chris Lattner9c837532006-10-15 01:05:46 +0000150
151 // 128-bit long double macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000152 Define(Defs, "__LDBL_DENORM_MIN__",
153 "4.94065645841246544176568792868221e-324L");
154 Define(Defs, "__LDBL_DIG__", "31");
155 Define(Defs, "__LDBL_EPSILON__",
156 "4.94065645841246544176568792868221e-324L");
157 Define(Defs, "__LDBL_HAS_INFINITY__");
158 Define(Defs, "__LDBL_HAS_QUIET_NAN__");
159 Define(Defs, "__LDBL_MANT_DIG__", "106");
160 Define(Defs, "__LDBL_MAX_10_EXP__", "308");
161 Define(Defs, "__LDBL_MAX_EXP__", "1024");
162 Define(Defs, "__LDBL_MAX__",
163 "1.79769313486231580793728971405301e+308L");
164 Define(Defs, "__LDBL_MIN_10_EXP__", "(-291)");
165 Define(Defs, "__LDBL_MIN_EXP__", "(-968)");
166 Define(Defs, "__LDBL_MIN__",
167 "2.00416836000897277799610805135016e-292L");
168 Define(Defs, "__LONG_DOUBLE_128__");
Chris Lattner1f5ad112006-10-14 18:32:12 +0000169}
170
171/// getX86Defines - Return a set of the X86-specific #defines that are
172/// not tied to a specific subtarget.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000173static void getX86Defines(std::vector<char> &Defs, bool is64Bit) {
Chris Lattner9c837532006-10-15 01:05:46 +0000174 // Target identification.
175 if (is64Bit) {
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000176 Define(Defs, "_LP64");
177 Define(Defs, "__LP64__");
178 Define(Defs, "__amd64__");
179 Define(Defs, "__amd64");
180 Define(Defs, "__x86_64");
181 Define(Defs, "__x86_64__");
Chris Lattner9c837532006-10-15 01:05:46 +0000182 } else {
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000183 Define(Defs, "__i386__");
184 Define(Defs, "__i386");
185 Define(Defs, "i386");
Chris Lattner9c837532006-10-15 01:05:46 +0000186 }
187
188 // Target properties.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000189 Define(Defs, "__LITTLE_ENDIAN__");
Chris Lattner9c837532006-10-15 01:05:46 +0000190
191 if (is64Bit) {
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000192 Define(Defs, "__INTMAX_MAX__", "9223372036854775807L");
193 Define(Defs, "__INTMAX_TYPE__", "long int");
194 Define(Defs, "__LONG_MAX__", "9223372036854775807L");
195 Define(Defs, "__PTRDIFF_TYPE__", "long int");
196 Define(Defs, "__UINTMAX_TYPE__", "long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +0000197 } else {
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000198 Define(Defs, "__INTMAX_MAX__", "9223372036854775807LL");
199 Define(Defs, "__INTMAX_TYPE__", "long long int");
200 Define(Defs, "__LONG_MAX__", "2147483647L");
201 Define(Defs, "__PTRDIFF_TYPE__", "int");
202 Define(Defs, "__UINTMAX_TYPE__", "long long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +0000203 }
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000204 Define(Defs, "__CHAR_BIT__", "8");
205 Define(Defs, "__INT_MAX__", "2147483647");
206 Define(Defs, "__LONG_LONG_MAX__", "9223372036854775807LL");
207 Define(Defs, "__SCHAR_MAX__", "127");
208 Define(Defs, "__SHRT_MAX__", "32767");
209 Define(Defs, "__SIZE_TYPE__", "long unsigned int");
Chris Lattner9c837532006-10-15 01:05:46 +0000210
211 // Subtarget options.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000212 Define(Defs, "__nocona");
213 Define(Defs, "__nocona__");
214 Define(Defs, "__tune_nocona__");
215 Define(Defs, "__SSE2_MATH__");
216 Define(Defs, "__SSE2__");
217 Define(Defs, "__SSE_MATH__");
218 Define(Defs, "__SSE__");
219 Define(Defs, "__MMX__");
220 Define(Defs, "__REGISTER_PREFIX__", "");
Chris Lattner9c837532006-10-15 01:05:46 +0000221
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000222 Define(Defs, "__WCHAR_MAX__", "2147483647");
223 Define(Defs, "__WCHAR_TYPE__", "int");
224 Define(Defs, "__WINT_TYPE__", "int");
Chris Lattner9c837532006-10-15 01:05:46 +0000225
226 // Float macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000227 Define(Defs, "__FLT_DENORM_MIN__", "1.40129846e-45F");
228 Define(Defs, "__FLT_DIG__", "6");
229 Define(Defs, "__FLT_EPSILON__", "1.19209290e-7F");
230 Define(Defs, "__FLT_EVAL_METHOD__", "0");
231 Define(Defs, "__FLT_HAS_INFINITY__");
232 Define(Defs, "__FLT_HAS_QUIET_NAN__");
233 Define(Defs, "__FLT_MANT_DIG__", "24");
234 Define(Defs, "__FLT_MAX_10_EXP__", "38");
235 Define(Defs, "__FLT_MAX_EXP__", "128");
236 Define(Defs, "__FLT_MAX__", "3.40282347e+38F");
237 Define(Defs, "__FLT_MIN_10_EXP__", "(-37)");
238 Define(Defs, "__FLT_MIN_EXP__", "(-125)");
239 Define(Defs, "__FLT_MIN__", "1.17549435e-38F");
240 Define(Defs, "__FLT_RADIX__", "2");
Chris Lattner9c837532006-10-15 01:05:46 +0000241
242 // Double macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000243 Define(Defs, "__DBL_DENORM_MIN__", "4.9406564584124654e-324");
244 Define(Defs, "__DBL_DIG__", "15");
245 Define(Defs, "__DBL_EPSILON__", "2.2204460492503131e-16");
246 Define(Defs, "__DBL_HAS_INFINITY__");
247 Define(Defs, "__DBL_HAS_QUIET_NAN__");
248 Define(Defs, "__DBL_MANT_DIG__", "53");
249 Define(Defs, "__DBL_MAX_10_EXP__", "308");
250 Define(Defs, "__DBL_MAX_EXP__", "1024");
251 Define(Defs, "__DBL_MAX__", "1.7976931348623157e+308");
252 Define(Defs, "__DBL_MIN_10_EXP__", "(-307)");
253 Define(Defs, "__DBL_MIN_EXP__", "(-1021)");
254 Define(Defs, "__DBL_MIN__", "2.2250738585072014e-308");
255 Define(Defs, "__DECIMAL_DIG__", "21");
Chris Lattner9c837532006-10-15 01:05:46 +0000256
257 // 80-bit Long double macros.
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000258 Define(Defs, "__LDBL_DENORM_MIN__", "3.64519953188247460253e-4951L");
259 Define(Defs, "__LDBL_DIG__", "18");
260 Define(Defs, "__LDBL_EPSILON__", "1.08420217248550443401e-19L");
261 Define(Defs, "__LDBL_HAS_INFINITY__");
262 Define(Defs, "__LDBL_HAS_QUIET_NAN__");
263 Define(Defs, "__LDBL_MANT_DIG__", "64");
264 Define(Defs, "__LDBL_MAX_10_EXP__", "4932");
265 Define(Defs, "__LDBL_MAX_EXP__", "16384");
266 Define(Defs, "__LDBL_MAX__", "1.18973149535723176502e+4932L");
267 Define(Defs, "__LDBL_MIN_10_EXP__", "(-4931)");
268 Define(Defs, "__LDBL_MIN_EXP__", "(-16381)");
269 Define(Defs, "__LDBL_MIN__", "3.36210314311209350626e-4932L");
Chris Lattner1f5ad112006-10-14 18:32:12 +0000270}
271
Anders Carlssona7408e72007-10-13 00:45:48 +0000272static const char* getI386VAListDeclaration() {
273 return "typedef char* __builtin_va_list;";
274}
275
276static const char* getX86_64VAListDeclaration() {
277 return
278 "typedef struct __va_list_tag {"
279 " unsigned gp_offset;"
280 " unsigned fp_offset;"
281 " void* overflow_arg_area;"
282 " void* reg_save_area;"
283 "} __builtin_va_list[1];";
284}
285
286static const char* getPPCVAListDeclaration() {
287 return
288 "typedef struct __va_list_tag {"
289 " unsigned char gpr;"
290 " unsigned char fpr;"
291 " unsigned short reserved;"
292 " void* overflow_arg_area;"
293 " void* reg_save_area;"
294 "} __builtin_va_list[1];";
295}
296
297
Chris Lattner10a5b382007-01-29 05:24:35 +0000298/// PPC builtin info.
Chris Lattner29a16af2007-12-11 04:36:28 +0000299namespace clang {
Chris Lattner10a5b382007-01-29 05:24:35 +0000300namespace PPC {
Chris Lattner10a5b382007-01-29 05:24:35 +0000301
302 static const Builtin::Info BuiltinInfo[] = {
303#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
Anders Carlsson895af082007-12-09 23:17:02 +0000304#include "clang/AST/PPCBuiltins.def"
Chris Lattner10a5b382007-01-29 05:24:35 +0000305 };
306
307 static void getBuiltins(const Builtin::Info *&Records, unsigned &NumRecords) {
308 Records = BuiltinInfo;
309 NumRecords = LastTSBuiltin-Builtin::FirstTSBuiltin;
310 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000311
312 static const char * const GCCRegNames[] = {
313 "0", "1", "2", "3", "4", "5", "6", "7",
314 "8", "9", "10", "11", "12", "13", "14", "15",
315 "16", "17", "18", "19", "20", "21", "22", "23",
316 "24", "25", "26", "27", "28", "29", "30", "31",
317 "0", "1", "2", "3", "4", "5", "6", "7",
318 "8", "9", "10", "11", "12", "13", "14", "15",
319 "16", "17", "18", "19", "20", "21", "22", "23",
320 "24", "25", "26", "27", "28", "29", "30", "31",
321 "mq", "lr", "ctr", "ap",
322 "0", "1", "2", "3", "4", "5", "6", "7",
323 "xer",
324 "0", "1", "2", "3", "4", "5", "6", "7",
325 "8", "9", "10", "11", "12", "13", "14", "15",
326 "16", "17", "18", "19", "20", "21", "22", "23",
327 "24", "25", "26", "27", "28", "29", "30", "31",
328 "vrsave", "vscr",
329 "spe_acc", "spefscr",
330 "sfp"
331 };
332
333 static void getGCCRegNames(const char * const *&Names,
334 unsigned &NumNames) {
335 Names = GCCRegNames;
336 NumNames = llvm::array_lengthof(GCCRegNames);
337 }
338
339 static const TargetInfoImpl::GCCRegAlias GCCRegAliases[] = {
340 // While some of these aliases do map to different registers
341 // they still share the same register name.
342 { { "cc", "cr0", "fr0", "r0", "v0"}, "0" },
343 { { "cr1", "fr1", "r1", "sp", "v1"}, "1" },
344 { { "cr2", "fr2", "r2", "toc", "v2"}, "2" },
345 { { "cr3", "fr3", "r3", "v3"}, "3" },
346 { { "cr4", "fr4", "r4", "v4"}, "4" },
347 { { "cr5", "fr5", "r5", "v5"}, "5" },
348 { { "cr6", "fr6", "r6", "v6"}, "6" },
349 { { "cr7", "fr7", "r7", "v7"}, "7" },
350 { { "fr8", "r8", "v8"}, "8" },
351 { { "fr9", "r9", "v9"}, "9" },
352 { { "fr10", "r10", "v10"}, "10" },
353 { { "fr11", "r11", "v11"}, "11" },
354 { { "fr12", "r12", "v12"}, "12" },
355 { { "fr13", "r13", "v13"}, "13" },
356 { { "fr14", "r14", "v14"}, "14" },
357 { { "fr15", "r15", "v15"}, "15" },
358 { { "fr16", "r16", "v16"}, "16" },
359 { { "fr17", "r17", "v17"}, "17" },
360 { { "fr18", "r18", "v18"}, "18" },
361 { { "fr19", "r19", "v19"}, "19" },
362 { { "fr20", "r20", "v20"}, "20" },
363 { { "fr21", "r21", "v21"}, "21" },
364 { { "fr22", "r22", "v22"}, "22" },
365 { { "fr23", "r23", "v23"}, "23" },
366 { { "fr24", "r24", "v24"}, "24" },
367 { { "fr25", "r25", "v25"}, "25" },
368 { { "fr26", "r26", "v26"}, "26" },
369 { { "fr27", "r27", "v27"}, "27" },
370 { { "fr28", "r28", "v28"}, "28" },
371 { { "fr29", "r29", "v29"}, "29" },
372 { { "fr30", "r30", "v30"}, "30" },
373 { { "fr31", "r31", "v31"}, "31" },
374 };
375
376 static void getGCCRegAliases(const TargetInfoImpl::GCCRegAlias *&Aliases,
377 unsigned &NumAliases) {
378 Aliases = GCCRegAliases;
379 NumAliases = llvm::array_lengthof(GCCRegAliases);
Anders Carlssonf511f642007-11-27 04:11:28 +0000380 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000381
Anders Carlssonf511f642007-11-27 04:11:28 +0000382 static bool validateAsmConstraint(char c,
383 TargetInfo::ConstraintInfo &info) {
384 switch (c) {
385 default: return false;
386 case 'O': // Zero
387 return true;
388 case 'b': // Base register
389 case 'f': // Floating point register
390 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
391 return true;
392 }
393 }
394
395 const char *getClobbers() {
396 return 0;
397 }
398
Anders Carlsson050f4942007-12-08 19:32:57 +0000399 const char *getTargetPrefix() {
400 return "ppc";
401 }
402
Chris Lattner10a5b382007-01-29 05:24:35 +0000403} // End namespace PPC
404
Chris Lattner10a5b382007-01-29 05:24:35 +0000405/// X86 builtin info.
406namespace X86 {
Chris Lattner10a5b382007-01-29 05:24:35 +0000407 static const Builtin::Info BuiltinInfo[] = {
408#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS },
Anders Carlsson895af082007-12-09 23:17:02 +0000409#include "clang/AST/X86Builtins.def"
Chris Lattner10a5b382007-01-29 05:24:35 +0000410 };
411
412 static void getBuiltins(const Builtin::Info *&Records, unsigned &NumRecords) {
413 Records = BuiltinInfo;
414 NumRecords = LastTSBuiltin-Builtin::FirstTSBuiltin;
415 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000416
417 static const char *GCCRegNames[] = {
418 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp",
419 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)",
Anders Carlssonc1636572007-11-25 00:23:10 +0000420 "argp", "flags", "fspr", "dirflag", "frame",
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000421 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7",
422 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7",
423 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
424 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
425 };
426
427 static void getGCCRegNames(const char * const *&Names,
428 unsigned &NumNames) {
429 Names = GCCRegNames;
430 NumNames = llvm::array_lengthof(GCCRegNames);
431 }
432
433 static const TargetInfoImpl::GCCRegAlias GCCRegAliases[] = {
434 { { "al", "ah", "eax", "rax" }, "ax" },
435 { { "bl", "bh", "ebx", "rbx" }, "bx" },
436 { { "cl", "ch", "ecx", "rcx" }, "cx" },
437 { { "dl", "dh", "edx", "rdx" }, "dx" },
438 { { "esi", "rsi" }, "si" },
439 { { "esp", "rsp" }, "sp" },
440 { { "ebp", "rbp" }, "bp" },
441 };
442
443 static void getGCCRegAliases(const TargetInfoImpl::GCCRegAlias *&Aliases,
444 unsigned &NumAliases) {
445 Aliases = GCCRegAliases;
446 NumAliases = llvm::array_lengthof(GCCRegAliases);
447 }
448
Anders Carlssonf511f642007-11-27 04:11:28 +0000449 static bool validateAsmConstraint(char c,
450 TargetInfo::ConstraintInfo &info) {
451 switch (c) {
452 default: return false;
453 case 'a': // eax.
454 case 'b': // ebx.
455 case 'c': // ecx.
456 case 'd': // edx.
457 case 'S': // esi.
458 case 'D': // edi.
459 case 'A': // edx:eax.
460 case 't': // top of floating point stack.
461 case 'u': // second from top of floating point stack.
462 case 'q': // a, b, c, d registers or any integer register in 64-bit.
463 info = (TargetInfo::ConstraintInfo)(info|TargetInfo::CI_AllowsRegister);
464 return true;
465 }
466 }
467
468 const char *getClobbers() {
469 return "~{dirflag},~{fpsr},~{flags}";
470 }
471
Anders Carlsson050f4942007-12-08 19:32:57 +0000472 const char *getTargetPrefix() {
473 return "x86";
474 }
475
Chris Lattner10a5b382007-01-29 05:24:35 +0000476} // End namespace X86
Chris Lattner29a16af2007-12-11 04:36:28 +0000477} // end namespace clang.
Chris Lattner10a5b382007-01-29 05:24:35 +0000478
Chris Lattner5ba61f02006-10-14 07:39:34 +0000479//===----------------------------------------------------------------------===//
480// Specific target implementations.
481//===----------------------------------------------------------------------===//
482
Chris Lattner02dffbd2006-10-14 07:50:21 +0000483
Chris Lattner5ba61f02006-10-14 07:39:34 +0000484namespace {
485class DarwinPPCTargetInfo : public DarwinTargetInfo {
486public:
Ted Kremenekb0615542007-12-03 22:06:55 +0000487 DarwinPPCTargetInfo(const std::string& triple) : DarwinTargetInfo(triple) {}
488
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000489 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner1f5ad112006-10-14 18:32:12 +0000490 DarwinTargetInfo::getTargetDefines(Defines);
491 getPowerPCDefines(Defines, false);
492 }
Chris Lattner10a5b382007-01-29 05:24:35 +0000493 virtual void getTargetBuiltins(const Builtin::Info *&Records,
494 unsigned &NumRecords) const {
495 PPC::getBuiltins(Records, NumRecords);
496 }
Anders Carlssona7408e72007-10-13 00:45:48 +0000497 virtual const char *getVAListDeclaration() const {
498 return getPPCVAListDeclaration();
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000499 }
Anders Carlsson050f4942007-12-08 19:32:57 +0000500 virtual const char *getTargetPrefix() const {
501 return PPC::getTargetPrefix();
502 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000503 virtual void getGCCRegNames(const char * const *&Names,
504 unsigned &NumNames) const {
505 PPC::getGCCRegNames(Names, NumNames);
506 }
507 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
508 unsigned &NumAliases) const {
509 PPC::getGCCRegAliases(Aliases, NumAliases);
510 }
Anders Carlssonf511f642007-11-27 04:11:28 +0000511 virtual bool validateAsmConstraint(char c,
512 TargetInfo::ConstraintInfo &info) const {
513 return PPC::validateAsmConstraint(c, info);
514 }
515 virtual const char *getClobbers() const {
516 return PPC::getClobbers();
517 }
Chris Lattner5ba61f02006-10-14 07:39:34 +0000518};
519} // end anonymous namespace.
520
521namespace {
522class DarwinPPC64TargetInfo : public DarwinTargetInfo {
523public:
Ted Kremenekb0615542007-12-03 22:06:55 +0000524 DarwinPPC64TargetInfo(const std::string& triple) : DarwinTargetInfo(triple) {}
525
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000526 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner1f5ad112006-10-14 18:32:12 +0000527 DarwinTargetInfo::getTargetDefines(Defines);
528 getPowerPCDefines(Defines, true);
529 }
Chris Lattner10a5b382007-01-29 05:24:35 +0000530 virtual void getTargetBuiltins(const Builtin::Info *&Records,
531 unsigned &NumRecords) const {
532 PPC::getBuiltins(Records, NumRecords);
533 }
Anders Carlssona7408e72007-10-13 00:45:48 +0000534 virtual const char *getVAListDeclaration() const {
535 return getPPCVAListDeclaration();
536 }
Anders Carlsson050f4942007-12-08 19:32:57 +0000537 virtual const char *getTargetPrefix() const {
538 return PPC::getTargetPrefix();
539 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000540 virtual void getGCCRegNames(const char * const *&Names,
541 unsigned &NumNames) const {
542 PPC::getGCCRegNames(Names, NumNames);
543 }
544 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
545 unsigned &NumAliases) const {
546 PPC::getGCCRegAliases(Aliases, NumAliases);
547 }
Anders Carlssonf511f642007-11-27 04:11:28 +0000548 virtual bool validateAsmConstraint(char c,
549 TargetInfo::ConstraintInfo &info) const {
550 return PPC::validateAsmConstraint(c, info);
551 }
552 virtual const char *getClobbers() const {
553 return PPC::getClobbers();
554 }
Chris Lattner5ba61f02006-10-14 07:39:34 +0000555};
556} // end anonymous namespace.
557
558namespace {
559class DarwinI386TargetInfo : public DarwinTargetInfo {
560public:
Ted Kremenekb0615542007-12-03 22:06:55 +0000561 DarwinI386TargetInfo(const std::string& triple) : DarwinTargetInfo(triple) {}
562
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000563 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner1f5ad112006-10-14 18:32:12 +0000564 DarwinTargetInfo::getTargetDefines(Defines);
565 getX86Defines(Defines, false);
566 }
Chris Lattner10a5b382007-01-29 05:24:35 +0000567 virtual void getTargetBuiltins(const Builtin::Info *&Records,
568 unsigned &NumRecords) const {
569 X86::getBuiltins(Records, NumRecords);
570 }
Anders Carlssona7408e72007-10-13 00:45:48 +0000571 virtual const char *getVAListDeclaration() const {
572 return getI386VAListDeclaration();
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000573 }
Anders Carlsson050f4942007-12-08 19:32:57 +0000574 virtual const char *getTargetPrefix() const {
575 return X86::getTargetPrefix();
576 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000577 virtual void getGCCRegNames(const char * const *&Names,
578 unsigned &NumNames) const {
579 X86::getGCCRegNames(Names, NumNames);
580 }
581 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
582 unsigned &NumAliases) const {
583 X86::getGCCRegAliases(Aliases, NumAliases);
Anders Carlssona7408e72007-10-13 00:45:48 +0000584 }
Anders Carlssonf511f642007-11-27 04:11:28 +0000585 virtual bool validateAsmConstraint(char c,
586 TargetInfo::ConstraintInfo &info) const {
587 return X86::validateAsmConstraint(c, info);
588 }
589 virtual const char *getClobbers() const {
590 return X86::getClobbers();
591 }
Chris Lattner5ba61f02006-10-14 07:39:34 +0000592};
593} // end anonymous namespace.
594
595namespace {
596class DarwinX86_64TargetInfo : public DarwinTargetInfo {
597public:
Ted Kremenekb0615542007-12-03 22:06:55 +0000598 DarwinX86_64TargetInfo(const std::string& triple) :DarwinTargetInfo(triple) {}
599
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000600 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner1f5ad112006-10-14 18:32:12 +0000601 DarwinTargetInfo::getTargetDefines(Defines);
602 getX86Defines(Defines, true);
603 }
Chris Lattner10a5b382007-01-29 05:24:35 +0000604 virtual void getTargetBuiltins(const Builtin::Info *&Records,
605 unsigned &NumRecords) const {
606 X86::getBuiltins(Records, NumRecords);
607 }
Anders Carlssona7408e72007-10-13 00:45:48 +0000608 virtual const char *getVAListDeclaration() const {
609 return getX86_64VAListDeclaration();
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000610 }
Anders Carlsson050f4942007-12-08 19:32:57 +0000611 virtual const char *getTargetPrefix() const {
612 return X86::getTargetPrefix();
613 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000614 virtual void getGCCRegNames(const char * const *&Names,
615 unsigned &NumNames) const {
616 X86::getGCCRegNames(Names, NumNames);
Anders Carlssona7408e72007-10-13 00:45:48 +0000617 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000618 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
619 unsigned &NumAliases) const {
620 X86::getGCCRegAliases(Aliases, NumAliases);
621 }
Anders Carlssonf511f642007-11-27 04:11:28 +0000622 virtual bool validateAsmConstraint(char c,
623 TargetInfo::ConstraintInfo &info) const {
624 return X86::validateAsmConstraint(c, info);
625 }
626 virtual const char *getClobbers() const {
627 return X86::getClobbers();
628 }
Chris Lattner5ba61f02006-10-14 07:39:34 +0000629};
630} // end anonymous namespace.
631
632namespace {
633class LinuxTargetInfo : public DarwinTargetInfo {
634public:
Ted Kremenekb0615542007-12-03 22:06:55 +0000635 LinuxTargetInfo(const std::string& triple) : DarwinTargetInfo(triple) {
Chris Lattner5ba61f02006-10-14 07:39:34 +0000636 // Note: I have no idea if this is right, just for testing.
Chris Lattnerd5a828b2007-04-05 06:57:57 +0000637 WCharWidth = 16;
Chris Lattner4481b422007-07-14 01:29:45 +0000638 WCharAlign = 16;
Chris Lattner5ba61f02006-10-14 07:39:34 +0000639 }
Chris Lattner1f5ad112006-10-14 18:32:12 +0000640
Chris Lattnerb2d486a2007-10-06 06:57:34 +0000641 virtual void getTargetDefines(std::vector<char> &Defines) const {
Chris Lattner1f5ad112006-10-14 18:32:12 +0000642 // TODO: linux-specific stuff.
643 getX86Defines(Defines, false);
644 }
Chris Lattner10a5b382007-01-29 05:24:35 +0000645 virtual void getTargetBuiltins(const Builtin::Info *&Records,
646 unsigned &NumRecords) const {
647 X86::getBuiltins(Records, NumRecords);
648 }
Anders Carlssona7408e72007-10-13 00:45:48 +0000649 virtual const char *getVAListDeclaration() const {
650 return getI386VAListDeclaration();
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000651 }
Anders Carlsson050f4942007-12-08 19:32:57 +0000652 virtual const char *getTargetPrefix() const {
653 return X86::getTargetPrefix();
654 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000655 virtual void getGCCRegNames(const char * const *&Names,
656 unsigned &NumNames) const {
657 X86::getGCCRegNames(Names, NumNames);
Anders Carlssona7408e72007-10-13 00:45:48 +0000658 }
Anders Carlsson5fa3f342007-11-24 23:38:12 +0000659 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
660 unsigned &NumAliases) const {
661 X86::getGCCRegAliases(Aliases, NumAliases);
662 }
Anders Carlssonf511f642007-11-27 04:11:28 +0000663 virtual bool validateAsmConstraint(char c,
664 TargetInfo::ConstraintInfo &info) const {
665 return X86::validateAsmConstraint(c, info);
666 }
667 virtual const char *getClobbers() const {
668 return X86::getClobbers();
669 }
Chris Lattner5ba61f02006-10-14 07:39:34 +0000670};
671} // end anonymous namespace.
672
673
674//===----------------------------------------------------------------------===//
675// Driver code
676//===----------------------------------------------------------------------===//
677
Ted Kremenek0c2bea22007-12-04 17:07:35 +0000678static inline bool IsX86(const std::string& TT) {
Ted Kremenekb0615542007-12-03 22:06:55 +0000679 return (TT.size() >= 5 && TT[0] == 'i' && TT[2] == '8' && TT[3] == '6' &&
680 TT[4] == '-' && TT[1] - '3' < 6);
681}
682
Chris Lattner5ba61f02006-10-14 07:39:34 +0000683/// CreateTarget - Create the TargetInfoImpl object for the specified target
684/// enum value.
Ted Kremenekb0615542007-12-03 22:06:55 +0000685static TargetInfoImpl *CreateTarget(const std::string& T) {
Chris Lattner36021a92007-12-05 18:41:05 +0000686 if (T.find("ppc-") == 0 || T.find("powerpc-") == 0)
Ted Kremenek0c2bea22007-12-04 17:07:35 +0000687 return new DarwinPPCTargetInfo(T);
Chris Lattner36021a92007-12-05 18:41:05 +0000688 else if (T.find("ppc64-") == 0 || T.find("powerpc64-") == 0)
Ted Kremenek0c2bea22007-12-04 17:07:35 +0000689 return new DarwinPPC64TargetInfo(T);
690 else if (T.find("x86_64-") == 0)
691 return new DarwinX86_64TargetInfo(T);
692 else if (IsX86(T))
693 return new DarwinI386TargetInfo(T);
694 else if (T.find("bogusW16W16-") == 0) // For testing portability.
695 return new LinuxTargetInfo(T);
696 else
697 return NULL;
Chris Lattner5ba61f02006-10-14 07:39:34 +0000698}
699
700/// CreateTargetInfo - Return the set of target info objects as specified by
701/// the -arch command line option.
Ted Kremenek1daa3cf2007-12-12 22:39:36 +0000702TargetInfo* TargetInfo::CreateTargetInfo(const std::string* TriplesStart,
Ted Kremenek6f6ff372007-12-12 18:05:32 +0000703 const std::string* TriplesEnd,
704 Diagnostic *Diags) {
Chris Lattner5ba61f02006-10-14 07:39:34 +0000705
706 // Create the primary target and target info.
Ted Kremenek6f6ff372007-12-12 18:05:32 +0000707 TargetInfoImpl* PrimaryTarget = CreateTarget(*TriplesStart);
Ted Kremenekeead4052007-12-03 23:23:21 +0000708
709 if (!PrimaryTarget)
710 return NULL;
711
Ted Kremenek1daa3cf2007-12-12 22:39:36 +0000712 TargetInfo *TI = new TargetInfo(PrimaryTarget, Diags);
Chris Lattner5ba61f02006-10-14 07:39:34 +0000713
714 // Add all secondary targets.
Ted Kremenek6f6ff372007-12-12 18:05:32 +0000715 for (const std::string* I=TriplesStart+1; I != TriplesEnd; ++I) {
716 TargetInfoImpl* SecondaryTarget = CreateTarget(*I);
Ted Kremenekeead4052007-12-03 23:23:21 +0000717
718 if (!SecondaryTarget) {
Ted Kremenek6f6ff372007-12-12 18:05:32 +0000719 fprintf (stderr,
720 "Warning: secondary target '%s' unrecognized.\n",
721 I->c_str());
722
Ted Kremenekeead4052007-12-03 23:23:21 +0000723 continue;
724 }
725
Ted Kremenek6f6ff372007-12-12 18:05:32 +0000726 TI->AddSecondaryTarget(SecondaryTarget);
Ted Kremenekeead4052007-12-03 23:23:21 +0000727 }
Ted Kremenekb0615542007-12-03 22:06:55 +0000728
Chris Lattner5ba61f02006-10-14 07:39:34 +0000729 return TI;
730}