blob: 8dbc1b3050c068c57a1a638bf535fbb201cfa0c1 [file] [log] [blame]
Chris Lattner4b009652007-07-25 00:24:17 +00001//===--- Targets.cpp - Implement -arch option and targets -----------------===//
2//
3// The LLVM Compiler Infrastructure
4//
Chris Lattner959e5be2007-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 Lattner4b009652007-07-25 00:24:17 +00007//
8//===----------------------------------------------------------------------===//
9//
Anton Korobeynikove7772382009-05-03 13:42:53 +000010// This file implements construction of a TargetInfo object from a
Ted Kremenek38591a22007-12-12 18:05:32 +000011// target triple.
Chris Lattner4b009652007-07-25 00:24:17 +000012//
13//===----------------------------------------------------------------------===//
14
Chris Lattner4b009652007-07-25 00:24:17 +000015#include "clang/Basic/TargetInfo.h"
Daniel Dunbarca3e9912009-11-15 06:48:46 +000016#include "clang/Basic/Builtins.h"
17#include "clang/Basic/Diagnostic.h"
Chris Lattnerddae7102008-12-04 22:54:33 +000018#include "clang/Basic/LangOptions.h"
Chandler Carrutha088d5b2010-01-20 06:13:02 +000019#include "clang/Basic/MacroBuilder.h"
Daniel Dunbarca3e9912009-11-15 06:48:46 +000020#include "clang/Basic/TargetBuiltins.h"
21#include "clang/Basic/TargetOptions.h"
Eli Friedmand4011892008-05-20 14:27:34 +000022#include "llvm/ADT/APFloat.h"
Daniel Dunbarca3e9912009-11-15 06:48:46 +000023#include "llvm/ADT/OwningPtr.h"
Daniel Dunbar8dd8f262009-11-11 09:38:56 +000024#include "llvm/ADT/STLExtras.h"
Daniel Dunbar0433a022009-08-19 20:04:03 +000025#include "llvm/ADT/StringRef.h"
Daniel Dunbar8dd8f262009-11-11 09:38:56 +000026#include "llvm/ADT/StringSwitch.h"
Chris Lattnerf54f2212009-08-12 06:24:27 +000027#include "llvm/ADT/Triple.h"
Chris Lattner43954312009-08-10 19:03:04 +000028#include "llvm/MC/MCSectionMachO.h"
Benjamin Kramerf8a85782010-01-09 18:20:57 +000029#include <algorithm>
Chris Lattner4b009652007-07-25 00:24:17 +000030using namespace clang;
31
Chris Lattner4b009652007-07-25 00:24:17 +000032//===----------------------------------------------------------------------===//
33// Common code shared among targets.
34//===----------------------------------------------------------------------===//
35
Chris Lattnerc345a802009-03-20 16:06:38 +000036/// DefineStd - Define a macro name and standard variants. For example if
37/// MacroName is "unix", then this will define "__unix", "__unix__", and "unix"
38/// when in GNU mode.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000039static void DefineStd(MacroBuilder &Builder, llvm::StringRef MacroName,
Chris Lattnerc345a802009-03-20 16:06:38 +000040 const LangOptions &Opts) {
41 assert(MacroName[0] != '_' && "Identifier should be in the user's namespace");
Anton Korobeynikove7772382009-05-03 13:42:53 +000042
Chris Lattnerc345a802009-03-20 16:06:38 +000043 // If in GNU mode (e.g. -std=gnu99 but not -std=c99) define the raw identifier
44 // in the user's namespace.
45 if (Opts.GNUMode)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000046 Builder.defineMacro(MacroName);
Anton Korobeynikove7772382009-05-03 13:42:53 +000047
Chris Lattnerc345a802009-03-20 16:06:38 +000048 // Define __unix.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000049 Builder.defineMacro("__" + MacroName);
Anton Korobeynikove7772382009-05-03 13:42:53 +000050
Chris Lattnerc345a802009-03-20 16:06:38 +000051 // Define __unix__.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000052 Builder.defineMacro("__" + MacroName + "__");
Chris Lattnerc345a802009-03-20 16:06:38 +000053}
54
Chris Lattnerbd00eb82008-10-05 21:50:58 +000055//===----------------------------------------------------------------------===//
56// Defines specific to certain operating systems.
57//===----------------------------------------------------------------------===//
Chris Lattner43954312009-08-10 19:03:04 +000058
Edwin Török36565e52009-06-30 17:10:35 +000059namespace {
Douglas Gregor937331f2009-07-01 15:12:53 +000060template<typename TgtInfo>
61class OSTargetInfo : public TgtInfo {
Edwin Török36565e52009-06-30 17:10:35 +000062protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +000063 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000064 MacroBuilder &Builder) const=0;
Edwin Török36565e52009-06-30 17:10:35 +000065public:
Douglas Gregor937331f2009-07-01 15:12:53 +000066 OSTargetInfo(const std::string& triple) : TgtInfo(triple) {}
Edwin Török36565e52009-06-30 17:10:35 +000067 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000068 MacroBuilder &Builder) const {
69 TgtInfo::getTargetDefines(Opts, Builder);
70 getOSDefines(Opts, TgtInfo::getTriple(), Builder);
Edwin Török2d98f9f2009-06-30 17:00:25 +000071 }
Edwin Török36565e52009-06-30 17:10:35 +000072
73};
Chris Lattnerf54f2212009-08-12 06:24:27 +000074} // end anonymous namespace
Edwin Török2d98f9f2009-06-30 17:00:25 +000075
Chris Lattner43954312009-08-10 19:03:04 +000076
Daniel Dunbareab96a22010-01-26 01:44:04 +000077static void getDarwinDefines(MacroBuilder &Builder, const LangOptions &Opts,
78 const llvm::Triple &Triple) {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000079 Builder.defineMacro("__APPLE_CC__", "5621");
80 Builder.defineMacro("__APPLE__");
81 Builder.defineMacro("__MACH__");
82 Builder.defineMacro("OBJC_NEW_PROPERTIES");
Anton Korobeynikove7772382009-05-03 13:42:53 +000083
Chris Lattner8181e622009-04-07 16:50:40 +000084 // __weak is always defined, for use in blocks and with objc pointers.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000085 Builder.defineMacro("__weak", "__attribute__((objc_gc(weak)))");
Anton Korobeynikove7772382009-05-03 13:42:53 +000086
Chris Lattner8181e622009-04-07 16:50:40 +000087 // Darwin defines __strong even in C mode (just to nothing).
88 if (!Opts.ObjC1 || Opts.getGCMode() == LangOptions::NonGC)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000089 Builder.defineMacro("__strong", "");
Chris Lattner8181e622009-04-07 16:50:40 +000090 else
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000091 Builder.defineMacro("__strong", "__attribute__((objc_gc(strong)))");
Eli Friedmaneff0a422009-06-04 23:00:29 +000092
93 if (Opts.Static)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000094 Builder.defineMacro("__STATIC__");
Eli Friedmaneff0a422009-06-04 23:00:29 +000095 else
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000096 Builder.defineMacro("__DYNAMIC__");
Daniel Dunbar62a7cbc2009-09-03 04:54:28 +000097
98 if (Opts.POSIXThreads)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +000099 Builder.defineMacro("_REENTRANT");
Daniel Dunbar93f64532009-04-10 19:52:24 +0000100
Daniel Dunbareab96a22010-01-26 01:44:04 +0000101 // Get the OS version number from the triple.
Daniel Dunbar93f64532009-04-10 19:52:24 +0000102 unsigned Maj, Min, Rev;
Mike Stump25cf7602009-09-09 15:08:12 +0000103
Daniel Dunbareab96a22010-01-26 01:44:04 +0000104 // If no version was given, default to to 10.4.0, for simplifying tests.
105 if (Triple.getOSName() == "darwin") {
106 Min = Rev = 0;
107 Maj = 8;
108 } else
109 Triple.getDarwinNumber(Maj, Min, Rev);
110
111 // Set the appropriate OS version define.
112 if (Triple.getEnvironmentName() == "iphoneos") {
113 assert(Maj < 10 && Min < 99 && Rev < 99 && "Invalid version!");
114 char Str[6];
115 Str[0] = '0' + Maj;
116 Str[1] = '0' + (Min / 10);
117 Str[2] = '0' + (Min % 10);
118 Str[3] = '0' + (Rev / 10);
119 Str[4] = '0' + (Rev % 10);
120 Str[5] = '\0';
121 Builder.defineMacro("__ENVIRONMENT_IPHONE_OS_VERSION_MIN_REQUIRED__", Str);
122 } else {
123 // For historical reasons that make little sense, the version passed here is
124 // the "darwin" version, which drops the 10 and offsets by 4.
125 Rev = Min;
126 Min = Maj - 4;
127 Maj = 10;
128
129 assert(Triple.getEnvironmentName().empty() && "Invalid environment!");
130 assert(Maj < 99 && Min < 10 && Rev < 10 && "Invalid version!");
131 char Str[5];
132 Str[0] = '0' + (Maj / 10);
133 Str[1] = '0' + (Maj % 10);
134 Str[2] = '0' + Min;
135 Str[3] = '0' + Rev;
136 Str[4] = '\0';
137 Builder.defineMacro("__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__", Str);
Daniel Dunbar93f64532009-04-10 19:52:24 +0000138 }
Eli Friedman872996c2008-08-20 02:34:37 +0000139}
Chris Lattner4b009652007-07-25 00:24:17 +0000140
Chris Lattner43954312009-08-10 19:03:04 +0000141namespace {
Edwin Török36565e52009-06-30 17:10:35 +0000142template<typename Target>
143class DarwinTargetInfo : public OSTargetInfo<Target> {
144protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000145 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000146 MacroBuilder &Builder) const {
Daniel Dunbareab96a22010-01-26 01:44:04 +0000147 getDarwinDefines(Builder, Opts, Triple);
Edwin Török36565e52009-06-30 17:10:35 +0000148 }
Mike Stump25cf7602009-09-09 15:08:12 +0000149
Edwin Török36565e52009-06-30 17:10:35 +0000150public:
151 DarwinTargetInfo(const std::string& triple) :
152 OSTargetInfo<Target>(triple) {
153 this->TLSSupported = false;
154 }
155
Edwin Török36565e52009-06-30 17:10:35 +0000156 virtual const char *getUnicodeStringSection() const {
157 return "__TEXT,__ustring";
158 }
Mike Stump25cf7602009-09-09 15:08:12 +0000159
Anders Carlsson41f80b52010-01-30 18:33:31 +0000160 virtual std::string isValidSectionSpecifier(llvm::StringRef SR) const {
Chris Lattner43954312009-08-10 19:03:04 +0000161 // Let MCSectionMachO validate this.
162 llvm::StringRef Segment, Section;
163 unsigned TAA, StubSize;
164 return llvm::MCSectionMachO::ParseSectionSpecifier(SR, Segment, Section,
165 TAA, StubSize);
166 }
Edwin Török36565e52009-06-30 17:10:35 +0000167};
168
Chris Lattner43954312009-08-10 19:03:04 +0000169
Edwin Török36565e52009-06-30 17:10:35 +0000170// DragonFlyBSD Target
171template<typename Target>
172class DragonFlyBSDTargetInfo : public OSTargetInfo<Target> {
173protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000174 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000175 MacroBuilder &Builder) const {
Edwin Török36565e52009-06-30 17:10:35 +0000176 // DragonFly defines; list based off of gcc output
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000177 Builder.defineMacro("__DragonFly__");
178 Builder.defineMacro("__DragonFly_cc_version", "100001");
179 Builder.defineMacro("__ELF__");
180 Builder.defineMacro("__KPRINTF_ATTRIBUTE__");
181 Builder.defineMacro("__tune_i386__");
182 DefineStd(Builder, "unix", Opts);
Edwin Török36565e52009-06-30 17:10:35 +0000183 }
184public:
Mike Stump25cf7602009-09-09 15:08:12 +0000185 DragonFlyBSDTargetInfo(const std::string &triple)
Edwin Török36565e52009-06-30 17:10:35 +0000186 : OSTargetInfo<Target>(triple) {}
187};
188
189// FreeBSD Target
190template<typename Target>
191class FreeBSDTargetInfo : public OSTargetInfo<Target> {
192protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000193 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000194 MacroBuilder &Builder) const {
Edwin Török36565e52009-06-30 17:10:35 +0000195 // FreeBSD defines; list based off of gcc output
196
Daniel Dunbar608b3882009-08-24 09:10:05 +0000197 // FIXME: Move version number handling to llvm::Triple.
Benjamin Kramereaa3c702010-01-30 19:55:01 +0000198 llvm::StringRef Release = Triple.getOSName().substr(strlen("freebsd"), 1);
Edwin Török36565e52009-06-30 17:10:35 +0000199
Benjamin Kramereaa3c702010-01-30 19:55:01 +0000200 Builder.defineMacro("__FreeBSD__", Release);
201 Builder.defineMacro("__FreeBSD_cc_version", Release + "00001");
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000202 Builder.defineMacro("__KPRINTF_ATTRIBUTE__");
203 DefineStd(Builder, "unix", Opts);
204 Builder.defineMacro("__ELF__");
Edwin Török36565e52009-06-30 17:10:35 +0000205 }
206public:
Mike Stump25cf7602009-09-09 15:08:12 +0000207 FreeBSDTargetInfo(const std::string &triple)
Duncan Sandscd2cb662009-07-08 13:55:08 +0000208 : OSTargetInfo<Target>(triple) {
209 this->UserLabelPrefix = "";
210 }
Edwin Török36565e52009-06-30 17:10:35 +0000211};
212
213// Linux target
214template<typename Target>
215class LinuxTargetInfo : public OSTargetInfo<Target> {
216protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000217 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000218 MacroBuilder &Builder) const {
Edwin Török36565e52009-06-30 17:10:35 +0000219 // Linux defines; list based off of gcc output
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000220 DefineStd(Builder, "unix", Opts);
221 DefineStd(Builder, "linux", Opts);
222 Builder.defineMacro("__gnu_linux__");
223 Builder.defineMacro("__ELF__");
Daniel Dunbar62a7cbc2009-09-03 04:54:28 +0000224 if (Opts.POSIXThreads)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000225 Builder.defineMacro("_REENTRANT");
Edwin Török36565e52009-06-30 17:10:35 +0000226 }
227public:
Mike Stump25cf7602009-09-09 15:08:12 +0000228 LinuxTargetInfo(const std::string& triple)
Edwin Török36565e52009-06-30 17:10:35 +0000229 : OSTargetInfo<Target>(triple) {
230 this->UserLabelPrefix = "";
231 }
232};
233
Chris Lattner25fff082009-07-13 20:29:08 +0000234// NetBSD Target
235template<typename Target>
236class NetBSDTargetInfo : public OSTargetInfo<Target> {
237protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000238 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000239 MacroBuilder &Builder) const {
Chris Lattner25fff082009-07-13 20:29:08 +0000240 // NetBSD defines; list based off of gcc output
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000241 Builder.defineMacro("__NetBSD__");
242 Builder.defineMacro("__unix__");
243 Builder.defineMacro("__ELF__");
Daniel Dunbar62a7cbc2009-09-03 04:54:28 +0000244 if (Opts.POSIXThreads)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000245 Builder.defineMacro("_POSIX_THREADS");
Chris Lattner25fff082009-07-13 20:29:08 +0000246 }
247public:
Mike Stump25cf7602009-09-09 15:08:12 +0000248 NetBSDTargetInfo(const std::string &triple)
Chris Lattner25fff082009-07-13 20:29:08 +0000249 : OSTargetInfo<Target>(triple) {
250 this->UserLabelPrefix = "";
251 }
252};
253
Edwin Török36565e52009-06-30 17:10:35 +0000254// OpenBSD Target
255template<typename Target>
256class OpenBSDTargetInfo : public OSTargetInfo<Target> {
257protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000258 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000259 MacroBuilder &Builder) const {
Edwin Török36565e52009-06-30 17:10:35 +0000260 // OpenBSD defines; list based off of gcc output
261
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000262 Builder.defineMacro("__OpenBSD__");
263 DefineStd(Builder, "unix", Opts);
264 Builder.defineMacro("__ELF__");
Daniel Dunbar62a7cbc2009-09-03 04:54:28 +0000265 if (Opts.POSIXThreads)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000266 Builder.defineMacro("_POSIX_THREADS");
Edwin Török36565e52009-06-30 17:10:35 +0000267 }
268public:
Mike Stump25cf7602009-09-09 15:08:12 +0000269 OpenBSDTargetInfo(const std::string &triple)
Edwin Török36565e52009-06-30 17:10:35 +0000270 : OSTargetInfo<Target>(triple) {}
271};
272
Edward O'Callaghan097309f2009-11-15 10:22:07 +0000273// PSP Target
274template<typename Target>
275class PSPTargetInfo : public OSTargetInfo<Target> {
276protected:
277 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000278 MacroBuilder &Builder) const {
Edward O'Callaghan097309f2009-11-15 10:22:07 +0000279 // PSP defines; list based on the output of the pspdev gcc toolchain.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000280 Builder.defineMacro("PSP");
281 Builder.defineMacro("_PSP");
282 Builder.defineMacro("__psp__");
283 Builder.defineMacro("__ELF__");
Edward O'Callaghan097309f2009-11-15 10:22:07 +0000284 }
285public:
286 PSPTargetInfo(const std::string& triple)
287 : OSTargetInfo<Target>(triple) {
288 this->UserLabelPrefix = "";
289 }
290};
291
John Thompsoned7bdbc2009-11-19 17:18:50 +0000292// PS3 PPU Target
293template<typename Target>
294class PS3PPUTargetInfo : public OSTargetInfo<Target> {
295protected:
296 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000297 MacroBuilder &Builder) const {
John Thompsoned7bdbc2009-11-19 17:18:50 +0000298 // PS3 PPU defines.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000299 Builder.defineMacro("__PPU__");
300 Builder.defineMacro("__CELLOS_LV2__");
301 Builder.defineMacro("__ELF__");
302 Builder.defineMacro("__LP32__");
John Thompsoned7bdbc2009-11-19 17:18:50 +0000303 }
304public:
305 PS3PPUTargetInfo(const std::string& triple)
306 : OSTargetInfo<Target>(triple) {
307 this->UserLabelPrefix = "";
John Thompson4c3bd3f2009-12-18 14:21:08 +0000308 this->LongWidth = this->LongAlign = this->PointerWidth = this->PointerAlign = 32;
309 this->SizeType = TargetInfo::UnsignedInt;
John Thompsoned7bdbc2009-11-19 17:18:50 +0000310 }
311};
312
313// FIXME: Need a real SPU target.
314// PS3 SPU Target
315template<typename Target>
316class PS3SPUTargetInfo : public OSTargetInfo<Target> {
317protected:
318 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000319 MacroBuilder &Builder) const {
John Thompsoned7bdbc2009-11-19 17:18:50 +0000320 // PS3 PPU defines.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000321 Builder.defineMacro("__SPU__");
322 Builder.defineMacro("__ELF__");
John Thompsoned7bdbc2009-11-19 17:18:50 +0000323 }
324public:
325 PS3SPUTargetInfo(const std::string& triple)
326 : OSTargetInfo<Target>(triple) {
327 this->UserLabelPrefix = "";
328 }
329};
330
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +0000331// AuroraUX target
332template<typename Target>
333class AuroraUXTargetInfo : public OSTargetInfo<Target> {
334protected:
335 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000336 MacroBuilder &Builder) const {
337 DefineStd(Builder, "sun", Opts);
338 DefineStd(Builder, "unix", Opts);
339 Builder.defineMacro("__ELF__");
340 Builder.defineMacro("__svr4__");
341 Builder.defineMacro("__SVR4");
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +0000342 }
343public:
344 AuroraUXTargetInfo(const std::string& triple)
345 : OSTargetInfo<Target>(triple) {
346 this->UserLabelPrefix = "";
347 this->WCharType = this->SignedLong;
348 // FIXME: WIntType should be SignedLong
349 }
350};
351
Edwin Török36565e52009-06-30 17:10:35 +0000352// Solaris target
353template<typename Target>
354class SolarisTargetInfo : public OSTargetInfo<Target> {
355protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +0000356 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000357 MacroBuilder &Builder) const {
358 DefineStd(Builder, "sun", Opts);
359 DefineStd(Builder, "unix", Opts);
360 Builder.defineMacro("__ELF__");
361 Builder.defineMacro("__svr4__");
362 Builder.defineMacro("__SVR4");
Edwin Török36565e52009-06-30 17:10:35 +0000363 }
364public:
Mike Stump25cf7602009-09-09 15:08:12 +0000365 SolarisTargetInfo(const std::string& triple)
Edwin Török36565e52009-06-30 17:10:35 +0000366 : OSTargetInfo<Target>(triple) {
367 this->UserLabelPrefix = "";
368 this->WCharType = this->SignedLong;
369 // FIXME: WIntType should be SignedLong
370 }
371};
Mike Stump25cf7602009-09-09 15:08:12 +0000372} // end anonymous namespace.
Edwin Török36565e52009-06-30 17:10:35 +0000373
Chris Lattnerbd00eb82008-10-05 21:50:58 +0000374//===----------------------------------------------------------------------===//
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000375// Specific target implementations.
376//===----------------------------------------------------------------------===//
Anders Carlsson8b58e8a2007-10-13 00:45:48 +0000377
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000378namespace {
379// PPC abstract base class
380class PPCTargetInfo : public TargetInfo {
381 static const Builtin::Info BuiltinInfo[];
382 static const char * const GCCRegNames[];
383 static const TargetInfo::GCCRegAlias GCCRegAliases[];
384
385public:
Eli Friedmand9389be2009-06-05 07:05:05 +0000386 PPCTargetInfo(const std::string& triple) : TargetInfo(triple) {}
387
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000388 virtual void getTargetBuiltins(const Builtin::Info *&Records,
389 unsigned &NumRecords) const {
Chris Lattner4b009652007-07-25 00:24:17 +0000390 Records = BuiltinInfo;
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000391 NumRecords = clang::PPC::LastTSBuiltin-Builtin::FirstTSBuiltin;
Chris Lattner4b009652007-07-25 00:24:17 +0000392 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000393
Chris Lattner79682402009-03-20 15:52:06 +0000394 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000395 MacroBuilder &Builder) const;
Anton Korobeynikove7772382009-05-03 13:42:53 +0000396
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000397 virtual const char *getVAListDeclaration() const {
Chris Lattnera07708f2008-10-27 01:11:29 +0000398 return "typedef char* __builtin_va_list;";
399 // This is the right definition for ABI/V4: System V.4/eabi.
400 /*return "typedef struct __va_list_tag {"
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000401 " unsigned char gpr;"
402 " unsigned char fpr;"
403 " unsigned short reserved;"
404 " void* overflow_arg_area;"
405 " void* reg_save_area;"
Chris Lattnera07708f2008-10-27 01:11:29 +0000406 "} __builtin_va_list[1];";*/
Anders Carlsson7dd1c952007-11-24 23:38:12 +0000407 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000408 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000409 unsigned &NumNames) const;
Anton Korobeynikove7772382009-05-03 13:42:53 +0000410 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000411 unsigned &NumAliases) const;
Anders Carlsson36834a72009-02-28 17:11:49 +0000412 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattnerc49cc1a2009-04-26 07:16:29 +0000413 TargetInfo::ConstraintInfo &Info) const {
Anders Carlsson36834a72009-02-28 17:11:49 +0000414 switch (*Name) {
Anders Carlsson4ce42302007-11-27 04:11:28 +0000415 default: return false;
416 case 'O': // Zero
417 return true;
418 case 'b': // Base register
419 case 'f': // Floating point register
Chris Lattnerc49cc1a2009-04-26 07:16:29 +0000420 Info.setAllowsRegister();
Anders Carlsson4ce42302007-11-27 04:11:28 +0000421 return true;
422 }
423 }
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000424 virtual const char *getClobbers() const {
425 return "";
Anders Carlsson4ce42302007-11-27 04:11:28 +0000426 }
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000427};
Anders Carlsson4ce42302007-11-27 04:11:28 +0000428
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000429const Builtin::Info PPCTargetInfo::BuiltinInfo[] = {
Douglas Gregor2e8a7aa2009-02-16 21:58:21 +0000430#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false },
431#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false },
Chris Lattner99ca9d62009-06-14 01:05:48 +0000432#include "clang/Basic/BuiltinsPPC.def"
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000433};
Anton Korobeynikove7772382009-05-03 13:42:53 +0000434
435
Chris Lattnerbef1d722009-03-02 22:27:17 +0000436/// PPCTargetInfo::getTargetDefines - Return a set of the PowerPC-specific
437/// #defines that are not tied to a specific subtarget.
Chris Lattner79682402009-03-20 15:52:06 +0000438void PPCTargetInfo::getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000439 MacroBuilder &Builder) const {
Chris Lattnerbef1d722009-03-02 22:27:17 +0000440 // Target identification.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000441 Builder.defineMacro("__ppc__");
442 Builder.defineMacro("_ARCH_PPC");
443 Builder.defineMacro("__POWERPC__");
Chris Lattnerbef1d722009-03-02 22:27:17 +0000444 if (PointerWidth == 64) {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000445 Builder.defineMacro("_ARCH_PPC64");
446 Builder.defineMacro("_LP64");
447 Builder.defineMacro("__LP64__");
448 Builder.defineMacro("__ppc64__");
Chris Lattnerbef1d722009-03-02 22:27:17 +0000449 } else {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000450 Builder.defineMacro("__ppc__");
Chris Lattnerbef1d722009-03-02 22:27:17 +0000451 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000452
Chris Lattnerbef1d722009-03-02 22:27:17 +0000453 // Target properties.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000454 Builder.defineMacro("_BIG_ENDIAN");
455 Builder.defineMacro("__BIG_ENDIAN__");
Anton Korobeynikove7772382009-05-03 13:42:53 +0000456
Chris Lattnerbef1d722009-03-02 22:27:17 +0000457 // Subtarget options.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000458 Builder.defineMacro("__NATURAL_ALIGNMENT__");
459 Builder.defineMacro("__REGISTER_PREFIX__", "");
Anton Korobeynikove7772382009-05-03 13:42:53 +0000460
Chris Lattnerbef1d722009-03-02 22:27:17 +0000461 // FIXME: Should be controlled by command line option.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000462 Builder.defineMacro("__LONG_DOUBLE_128__");
John Thompsoned7bdbc2009-11-19 17:18:50 +0000463
464 if (Opts.AltiVec) {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000465 Builder.defineMacro("__VEC__", "10206");
466 Builder.defineMacro("__ALTIVEC__");
John Thompsoned7bdbc2009-11-19 17:18:50 +0000467 }
Chris Lattnerbef1d722009-03-02 22:27:17 +0000468}
469
Chris Lattner9fd73612008-04-21 18:56:49 +0000470
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000471const char * const PPCTargetInfo::GCCRegNames[] = {
Chris Lattner14d2bb72009-09-16 05:05:27 +0000472 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
473 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
474 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
475 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31",
476 "f0", "f1", "f2", "f3", "f4", "f5", "f6", "f7",
477 "f8", "f9", "f10", "f11", "f12", "f13", "f14", "f15",
478 "f16", "f17", "f18", "f19", "f20", "f21", "f22", "f23",
479 "f24", "f25", "f26", "f27", "f28", "f29", "f30", "f31",
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000480 "mq", "lr", "ctr", "ap",
Chris Lattner14d2bb72009-09-16 05:05:27 +0000481 "cr0", "cr1", "cr2", "cr3", "cr4", "cr5", "cr6", "cr7",
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000482 "xer",
Chris Lattner14d2bb72009-09-16 05:05:27 +0000483 "v0", "v1", "v2", "v3", "v4", "v5", "v6", "v7",
484 "v8", "v9", "v10", "v11", "v12", "v13", "v14", "v15",
485 "v16", "v17", "v18", "v19", "v20", "v21", "v22", "v23",
486 "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31",
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000487 "vrsave", "vscr",
488 "spe_acc", "spefscr",
489 "sfp"
490};
Chris Lattner4b009652007-07-25 00:24:17 +0000491
Anton Korobeynikove7772382009-05-03 13:42:53 +0000492void PPCTargetInfo::getGCCRegNames(const char * const *&Names,
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000493 unsigned &NumNames) const {
494 Names = GCCRegNames;
495 NumNames = llvm::array_lengthof(GCCRegNames);
496}
Chris Lattner4b009652007-07-25 00:24:17 +0000497
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000498const TargetInfo::GCCRegAlias PPCTargetInfo::GCCRegAliases[] = {
499 // While some of these aliases do map to different registers
500 // they still share the same register name.
Daniel Dunbar40b774e2009-09-17 07:03:19 +0000501 { { "0" }, "r0" },
502 { { "1"}, "r1" },
503 { { "2" }, "r2" },
504 { { "3" }, "r3" },
505 { { "4" }, "r4" },
506 { { "5" }, "r5" },
507 { { "6" }, "r6" },
508 { { "7" }, "r7" },
509 { { "8" }, "r8" },
510 { { "9" }, "r9" },
511 { { "10" }, "r10" },
512 { { "11" }, "r11" },
513 { { "12" }, "r12" },
514 { { "13" }, "r13" },
515 { { "14" }, "r14" },
516 { { "15" }, "r15" },
517 { { "16" }, "r16" },
518 { { "17" }, "r17" },
519 { { "18" }, "r18" },
520 { { "19" }, "r19" },
521 { { "20" }, "r20" },
522 { { "21" }, "r21" },
523 { { "22" }, "r22" },
524 { { "23" }, "r23" },
525 { { "24" }, "r24" },
526 { { "25" }, "r25" },
527 { { "26" }, "r26" },
528 { { "27" }, "r27" },
529 { { "28" }, "r28" },
530 { { "29" }, "r29" },
531 { { "30" }, "r30" },
532 { { "31" }, "r31" },
533 { { "fr0" }, "f0" },
534 { { "fr1" }, "f1" },
535 { { "fr2" }, "f2" },
536 { { "fr3" }, "f3" },
537 { { "fr4" }, "f4" },
538 { { "fr5" }, "f5" },
539 { { "fr6" }, "f6" },
540 { { "fr7" }, "f7" },
541 { { "fr8" }, "f8" },
542 { { "fr9" }, "f9" },
Mike Stump369c21c2009-09-17 21:15:00 +0000543 { { "fr10" }, "f10" },
Daniel Dunbar40b774e2009-09-17 07:03:19 +0000544 { { "fr11" }, "f11" },
545 { { "fr12" }, "f12" },
546 { { "fr13" }, "f13" },
547 { { "fr14" }, "f14" },
548 { { "fr15" }, "f15" },
549 { { "fr16" }, "f16" },
550 { { "fr17" }, "f17" },
551 { { "fr18" }, "f18" },
552 { { "fr19" }, "f19" },
553 { { "fr20" }, "f20" },
554 { { "fr21" }, "f21" },
555 { { "fr22" }, "f22" },
556 { { "fr23" }, "f23" },
557 { { "fr24" }, "f24" },
558 { { "fr25" }, "f25" },
559 { { "fr26" }, "f26" },
560 { { "fr27" }, "f27" },
561 { { "fr28" }, "f28" },
562 { { "fr29" }, "f29" },
563 { { "fr30" }, "f30" },
564 { { "fr31" }, "f31" },
565 { { "cc" }, "cr0" },
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000566};
567
Anton Korobeynikove7772382009-05-03 13:42:53 +0000568void PPCTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000569 unsigned &NumAliases) const {
570 Aliases = GCCRegAliases;
571 NumAliases = llvm::array_lengthof(GCCRegAliases);
572}
573} // end anonymous namespace.
Chris Lattner4b009652007-07-25 00:24:17 +0000574
575namespace {
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000576class PPC32TargetInfo : public PPCTargetInfo {
Chris Lattner4b009652007-07-25 00:24:17 +0000577public:
Eli Friedman2b161652008-08-21 00:13:15 +0000578 PPC32TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
579 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
Chris Lattner2e17d912009-11-07 18:59:41 +0000580 "i64:64:64-f32:32:32-f64:64:64-v128:128:128-n32";
Eli Friedman2b161652008-08-21 00:13:15 +0000581 }
Chris Lattner4b009652007-07-25 00:24:17 +0000582};
583} // end anonymous namespace.
584
585namespace {
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000586class PPC64TargetInfo : public PPCTargetInfo {
Chris Lattner4b009652007-07-25 00:24:17 +0000587public:
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000588 PPC64TargetInfo(const std::string& triple) : PPCTargetInfo(triple) {
Chris Lattnere5fde952008-05-09 06:17:04 +0000589 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedman38e31802009-07-01 03:36:11 +0000590 IntMaxType = SignedLong;
591 UIntMaxType = UnsignedLong;
592 Int64Type = SignedLong;
Eli Friedman2b161652008-08-21 00:13:15 +0000593 DescriptionString = "E-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
Chris Lattner2e17d912009-11-07 18:59:41 +0000594 "i64:64:64-f32:32:32-f64:64:64-v128:128:128-n32:64";
Chris Lattnere5fde952008-05-09 06:17:04 +0000595 }
Eli Friedmanfd5a4122008-08-20 23:11:40 +0000596};
597} // end anonymous namespace.
598
Chris Lattner4b009652007-07-25 00:24:17 +0000599namespace {
Eli Friedman872996c2008-08-20 02:34:37 +0000600// Namespace for x86 abstract base class
601const Builtin::Info BuiltinInfo[] = {
Douglas Gregor2e8a7aa2009-02-16 21:58:21 +0000602#define BUILTIN(ID, TYPE, ATTRS) { #ID, TYPE, ATTRS, 0, false },
603#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER) { #ID, TYPE, ATTRS, HEADER, false },
Chris Lattner99ca9d62009-06-14 01:05:48 +0000604#include "clang/Basic/BuiltinsX86.def"
Eli Friedman872996c2008-08-20 02:34:37 +0000605};
Eli Friedman0b7b1cb2008-05-20 14:21:01 +0000606
Nuno Lopesad1010d2009-12-23 17:49:57 +0000607static const char* const GCCRegNames[] = {
Eli Friedman872996c2008-08-20 02:34:37 +0000608 "ax", "dx", "cx", "bx", "si", "di", "bp", "sp",
609 "st", "st(1)", "st(2)", "st(3)", "st(4)", "st(5)", "st(6)", "st(7)",
610 "argp", "flags", "fspr", "dirflag", "frame",
611 "xmm0", "xmm1", "xmm2", "xmm3", "xmm4", "xmm5", "xmm6", "xmm7",
612 "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7",
613 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
614 "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"
615};
616
617const TargetInfo::GCCRegAlias GCCRegAliases[] = {
618 { { "al", "ah", "eax", "rax" }, "ax" },
619 { { "bl", "bh", "ebx", "rbx" }, "bx" },
620 { { "cl", "ch", "ecx", "rcx" }, "cx" },
621 { { "dl", "dh", "edx", "rdx" }, "dx" },
622 { { "esi", "rsi" }, "si" },
623 { { "edi", "rdi" }, "di" },
624 { { "esp", "rsp" }, "sp" },
625 { { "ebp", "rbp" }, "bp" },
626};
627
628// X86 target abstract base class; x86-32 and x86-64 are very close, so
629// most of the implementation can be shared.
630class X86TargetInfo : public TargetInfo {
Chris Lattner715fe4c2009-03-02 22:40:39 +0000631 enum X86SSEEnum {
632 NoMMXSSE, MMX, SSE1, SSE2, SSE3, SSSE3, SSE41, SSE42
633 } SSELevel;
Anders Carlssone5e222f2010-01-27 03:47:49 +0000634 enum AMD3DNowEnum {
635 NoAMD3DNow, AMD3DNow, AMD3DNowAthlon
636 } AMD3DNowLevel;
637
Eli Friedman872996c2008-08-20 02:34:37 +0000638public:
Anton Korobeynikove7772382009-05-03 13:42:53 +0000639 X86TargetInfo(const std::string& triple)
Anders Carlssone5e222f2010-01-27 03:47:49 +0000640 : TargetInfo(triple), SSELevel(NoMMXSSE), AMD3DNowLevel(NoAMD3DNow) {
Eli Friedman872996c2008-08-20 02:34:37 +0000641 LongDoubleFormat = &llvm::APFloat::x87DoubleExtended;
Chris Lattner4b009652007-07-25 00:24:17 +0000642 }
643 virtual void getTargetBuiltins(const Builtin::Info *&Records,
644 unsigned &NumRecords) const {
Eli Friedman872996c2008-08-20 02:34:37 +0000645 Records = BuiltinInfo;
646 NumRecords = clang::X86::LastTSBuiltin-Builtin::FirstTSBuiltin;
Chris Lattner4b009652007-07-25 00:24:17 +0000647 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000648 virtual void getGCCRegNames(const char * const *&Names,
Eli Friedman872996c2008-08-20 02:34:37 +0000649 unsigned &NumNames) const {
650 Names = GCCRegNames;
651 NumNames = llvm::array_lengthof(GCCRegNames);
Anders Carlsson7dd1c952007-11-24 23:38:12 +0000652 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000653 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Anders Carlsson7dd1c952007-11-24 23:38:12 +0000654 unsigned &NumAliases) const {
Eli Friedman872996c2008-08-20 02:34:37 +0000655 Aliases = GCCRegAliases;
656 NumAliases = llvm::array_lengthof(GCCRegAliases);
Anders Carlsson8b58e8a2007-10-13 00:45:48 +0000657 }
Anders Carlsson36834a72009-02-28 17:11:49 +0000658 virtual bool validateAsmConstraint(const char *&Name,
Eli Friedman872996c2008-08-20 02:34:37 +0000659 TargetInfo::ConstraintInfo &info) const;
660 virtual std::string convertConstraint(const char Constraint) const;
Anders Carlsson4ce42302007-11-27 04:11:28 +0000661 virtual const char *getClobbers() const {
Eli Friedman872996c2008-08-20 02:34:37 +0000662 return "~{dirflag},~{fpsr},~{flags}";
663 }
Chris Lattner79682402009-03-20 15:52:06 +0000664 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000665 MacroBuilder &Builder) const;
Daniel Dunbar0838f962009-05-06 21:07:50 +0000666 virtual bool setFeatureEnabled(llvm::StringMap<bool> &Features,
667 const std::string &Name,
668 bool Enabled) const;
Mike Stump25cf7602009-09-09 15:08:12 +0000669 virtual void getDefaultFeatures(const std::string &CPU,
Daniel Dunbar0838f962009-05-06 21:07:50 +0000670 llvm::StringMap<bool> &Features) const;
Daniel Dunbar4f7cd962009-12-19 03:30:57 +0000671 virtual void HandleTargetFeatures(std::vector<std::string> &Features);
Chris Lattner4b009652007-07-25 00:24:17 +0000672};
Chris Lattner7d6220c2009-03-02 22:20:04 +0000673
Mike Stump25cf7602009-09-09 15:08:12 +0000674void X86TargetInfo::getDefaultFeatures(const std::string &CPU,
Daniel Dunbar0838f962009-05-06 21:07:50 +0000675 llvm::StringMap<bool> &Features) const {
Daniel Dunbar07181d72009-05-06 03:16:41 +0000676 // FIXME: This should not be here.
677 Features["3dnow"] = false;
678 Features["3dnowa"] = false;
679 Features["mmx"] = false;
680 Features["sse"] = false;
681 Features["sse2"] = false;
682 Features["sse3"] = false;
683 Features["ssse3"] = false;
684 Features["sse41"] = false;
685 Features["sse42"] = false;
Anton Korobeynikove7772382009-05-03 13:42:53 +0000686
Daniel Dunbar07181d72009-05-06 03:16:41 +0000687 // LLVM does not currently recognize this.
688 // Features["sse4a"] = false;
Anton Korobeynikove7772382009-05-03 13:42:53 +0000689
Daniel Dunbar07181d72009-05-06 03:16:41 +0000690 // FIXME: This *really* should not be here.
691
692 // X86_64 always has SSE2.
693 if (PointerWidth == 64)
694 Features["sse2"] = Features["sse"] = Features["mmx"] = true;
695
Daniel Dunbarc2e55de2009-05-06 21:56:32 +0000696 if (CPU == "generic" || CPU == "i386" || CPU == "i486" || CPU == "i586" ||
697 CPU == "pentium" || CPU == "i686" || CPU == "pentiumpro")
698 ;
699 else if (CPU == "pentium-mmx" || CPU == "pentium2")
700 setFeatureEnabled(Features, "mmx", true);
701 else if (CPU == "pentium3")
702 setFeatureEnabled(Features, "sse", true);
703 else if (CPU == "pentium-m" || CPU == "pentium4" || CPU == "x86-64")
704 setFeatureEnabled(Features, "sse2", true);
705 else if (CPU == "yonah" || CPU == "prescott" || CPU == "nocona")
706 setFeatureEnabled(Features, "sse3", true);
707 else if (CPU == "core2")
708 setFeatureEnabled(Features, "ssse3", true);
709 else if (CPU == "penryn") {
710 setFeatureEnabled(Features, "sse4", true);
711 Features["sse42"] = false;
712 } else if (CPU == "atom")
713 setFeatureEnabled(Features, "sse3", true);
714 else if (CPU == "corei7")
715 setFeatureEnabled(Features, "sse4", true);
716 else if (CPU == "k6" || CPU == "winchip-c6")
717 setFeatureEnabled(Features, "mmx", true);
Mike Stump25cf7602009-09-09 15:08:12 +0000718 else if (CPU == "k6-2" || CPU == "k6-3" || CPU == "athlon" ||
Daniel Dunbarc2e55de2009-05-06 21:56:32 +0000719 CPU == "athlon-tbird" || CPU == "winchip2" || CPU == "c3") {
720 setFeatureEnabled(Features, "mmx", true);
721 setFeatureEnabled(Features, "3dnow", true);
722 } else if (CPU == "athlon-4" || CPU == "athlon-xp" || CPU == "athlon-mp") {
723 setFeatureEnabled(Features, "sse", true);
724 setFeatureEnabled(Features, "3dnowa", true);
725 } else if (CPU == "k8" || CPU == "opteron" || CPU == "athlon64" ||
726 CPU == "athlon-fx") {
Mike Stump25cf7602009-09-09 15:08:12 +0000727 setFeatureEnabled(Features, "sse2", true);
Daniel Dunbarc2e55de2009-05-06 21:56:32 +0000728 setFeatureEnabled(Features, "3dnowa", true);
729 } else if (CPU == "c3-2")
730 setFeatureEnabled(Features, "sse", true);
Daniel Dunbar07181d72009-05-06 03:16:41 +0000731}
732
Daniel Dunbar0838f962009-05-06 21:07:50 +0000733bool X86TargetInfo::setFeatureEnabled(llvm::StringMap<bool> &Features,
Mike Stump25cf7602009-09-09 15:08:12 +0000734 const std::string &Name,
Daniel Dunbar0838f962009-05-06 21:07:50 +0000735 bool Enabled) const {
736 // FIXME: This *really* should not be here.
737 if (!Features.count(Name) && Name != "sse4")
738 return false;
739
740 if (Enabled) {
741 if (Name == "mmx")
742 Features["mmx"] = true;
743 else if (Name == "sse")
744 Features["mmx"] = Features["sse"] = true;
745 else if (Name == "sse2")
746 Features["mmx"] = Features["sse"] = Features["sse2"] = true;
747 else if (Name == "sse3")
Mike Stump25cf7602009-09-09 15:08:12 +0000748 Features["mmx"] = Features["sse"] = Features["sse2"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000749 Features["sse3"] = true;
750 else if (Name == "ssse3")
Mike Stump25cf7602009-09-09 15:08:12 +0000751 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000752 Features["ssse3"] = true;
753 else if (Name == "sse4")
Mike Stump25cf7602009-09-09 15:08:12 +0000754 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000755 Features["ssse3"] = Features["sse41"] = Features["sse42"] = true;
756 else if (Name == "3dnow")
757 Features["3dnowa"] = true;
758 else if (Name == "3dnowa")
759 Features["3dnow"] = Features["3dnowa"] = true;
760 } else {
761 if (Name == "mmx")
Mike Stump25cf7602009-09-09 15:08:12 +0000762 Features["mmx"] = Features["sse"] = Features["sse2"] = Features["sse3"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000763 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
764 else if (Name == "sse")
Mike Stump25cf7602009-09-09 15:08:12 +0000765 Features["sse"] = Features["sse2"] = Features["sse3"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000766 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
767 else if (Name == "sse2")
Mike Stump25cf7602009-09-09 15:08:12 +0000768 Features["sse2"] = Features["sse3"] = Features["ssse3"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000769 Features["sse41"] = Features["sse42"] = false;
770 else if (Name == "sse3")
Mike Stump25cf7602009-09-09 15:08:12 +0000771 Features["sse3"] = Features["ssse3"] = Features["sse41"] =
Daniel Dunbar0838f962009-05-06 21:07:50 +0000772 Features["sse42"] = false;
773 else if (Name == "ssse3")
774 Features["ssse3"] = Features["sse41"] = Features["sse42"] = false;
775 else if (Name == "sse4")
776 Features["sse41"] = Features["sse42"] = false;
777 else if (Name == "3dnow")
778 Features["3dnow"] = Features["3dnowa"] = false;
779 else if (Name == "3dnowa")
780 Features["3dnowa"] = false;
781 }
782
783 return true;
784}
785
Daniel Dunbar07181d72009-05-06 03:16:41 +0000786/// HandleTargetOptions - Perform initialization based on the user
787/// configured set of features.
Daniel Dunbar4f7cd962009-12-19 03:30:57 +0000788void X86TargetInfo::HandleTargetFeatures(std::vector<std::string> &Features) {
Daniel Dunbar8dd8f262009-11-11 09:38:56 +0000789 // Remember the maximum enabled sselevel.
790 for (unsigned i = 0, e = Features.size(); i !=e; ++i) {
791 // Ignore disabled features.
792 if (Features[i][0] == '-')
793 continue;
794
795 assert(Features[i][0] == '+' && "Invalid target feature!");
796 X86SSEEnum Level = llvm::StringSwitch<X86SSEEnum>(Features[i].substr(1))
797 .Case("sse42", SSE42)
798 .Case("sse41", SSE41)
799 .Case("ssse3", SSSE3)
800 .Case("sse2", SSE2)
801 .Case("sse", SSE1)
802 .Case("mmx", MMX)
803 .Default(NoMMXSSE);
804 SSELevel = std::max(SSELevel, Level);
Anders Carlssone5e222f2010-01-27 03:47:49 +0000805
806 AMD3DNowEnum ThreeDNowLevel =
807 llvm::StringSwitch<AMD3DNowEnum>(Features[i].substr(1))
808 .Case("3dnowa", AMD3DNowAthlon)
809 .Case("3dnow", AMD3DNow)
810 .Default(NoAMD3DNow);
811
812 AMD3DNowLevel = std::max(AMD3DNowLevel, ThreeDNowLevel);
Daniel Dunbar8dd8f262009-11-11 09:38:56 +0000813 }
Chris Lattner7d6220c2009-03-02 22:20:04 +0000814}
Chris Lattnerbef1d722009-03-02 22:27:17 +0000815
816/// X86TargetInfo::getTargetDefines - Return a set of the X86-specific #defines
817/// that are not tied to a specific subtarget.
Chris Lattner79682402009-03-20 15:52:06 +0000818void X86TargetInfo::getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000819 MacroBuilder &Builder) const {
Chris Lattnerbef1d722009-03-02 22:27:17 +0000820 // Target identification.
821 if (PointerWidth == 64) {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000822 Builder.defineMacro("_LP64");
823 Builder.defineMacro("__LP64__");
824 Builder.defineMacro("__amd64__");
825 Builder.defineMacro("__amd64");
826 Builder.defineMacro("__x86_64");
827 Builder.defineMacro("__x86_64__");
Chris Lattnerbef1d722009-03-02 22:27:17 +0000828 } else {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000829 DefineStd(Builder, "i386", Opts);
Chris Lattnerbef1d722009-03-02 22:27:17 +0000830 }
Anton Korobeynikove7772382009-05-03 13:42:53 +0000831
Chris Lattnerbef1d722009-03-02 22:27:17 +0000832 // Target properties.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000833 Builder.defineMacro("__LITTLE_ENDIAN__");
Anton Korobeynikove7772382009-05-03 13:42:53 +0000834
Chris Lattnerbef1d722009-03-02 22:27:17 +0000835 // Subtarget options.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000836 Builder.defineMacro("__nocona");
837 Builder.defineMacro("__nocona__");
838 Builder.defineMacro("__tune_nocona__");
839 Builder.defineMacro("__REGISTER_PREFIX__", "");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000840
Chris Lattner25ac1c12009-04-19 17:32:33 +0000841 // Define __NO_MATH_INLINES on linux/x86 so that we don't get inline
842 // functions in glibc header files that use FP Stack inline asm which the
843 // backend can't deal with (PR879).
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000844 Builder.defineMacro("__NO_MATH_INLINES");
Anton Korobeynikove7772382009-05-03 13:42:53 +0000845
Chris Lattner715fe4c2009-03-02 22:40:39 +0000846 // Each case falls through to the previous one here.
847 switch (SSELevel) {
848 case SSE42:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000849 Builder.defineMacro("__SSE4_2__");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000850 case SSE41:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000851 Builder.defineMacro("__SSE4_1__");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000852 case SSSE3:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000853 Builder.defineMacro("__SSSE3__");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000854 case SSE3:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000855 Builder.defineMacro("__SSE3__");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000856 case SSE2:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000857 Builder.defineMacro("__SSE2__");
858 Builder.defineMacro("__SSE2_MATH__"); // -mfp-math=sse always implied.
Chris Lattner715fe4c2009-03-02 22:40:39 +0000859 case SSE1:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000860 Builder.defineMacro("__SSE__");
861 Builder.defineMacro("__SSE_MATH__"); // -mfp-math=sse always implied.
Chris Lattner715fe4c2009-03-02 22:40:39 +0000862 case MMX:
Benjamin Kramer9ffb10432010-01-09 17:55:51 +0000863 Builder.defineMacro("__MMX__");
Chris Lattner715fe4c2009-03-02 22:40:39 +0000864 case NoMMXSSE:
865 break;
866 }
Anders Carlssone5e222f2010-01-27 03:47:49 +0000867
868 // Each case falls through to the previous one here.
869 switch (AMD3DNowLevel) {
870 case AMD3DNowAthlon:
871 Builder.defineMacro("__3dNOW_A__");
872 case AMD3DNow:
873 Builder.defineMacro("__3dNOW__");
874 case NoAMD3DNow:
875 break;
876 }
Chris Lattnerbef1d722009-03-02 22:27:17 +0000877}
Anton Korobeynikove7772382009-05-03 13:42:53 +0000878
879
Eli Friedman872996c2008-08-20 02:34:37 +0000880bool
Anders Carlsson36834a72009-02-28 17:11:49 +0000881X86TargetInfo::validateAsmConstraint(const char *&Name,
Chris Lattnerc49cc1a2009-04-26 07:16:29 +0000882 TargetInfo::ConstraintInfo &Info) const {
Anders Carlsson36834a72009-02-28 17:11:49 +0000883 switch (*Name) {
Eli Friedman872996c2008-08-20 02:34:37 +0000884 default: return false;
885 case 'a': // eax.
886 case 'b': // ebx.
887 case 'c': // ecx.
888 case 'd': // edx.
889 case 'S': // esi.
890 case 'D': // edi.
891 case 'A': // edx:eax.
892 case 't': // top of floating point stack.
893 case 'u': // second from top of floating point stack.
894 case 'q': // Any register accessible as [r]l: a, b, c, and d.
Anders Carlsson2285e622008-10-06 00:41:45 +0000895 case 'y': // Any MMX register.
Anders Carlssond2459f92008-10-06 19:17:39 +0000896 case 'x': // Any SSE register.
Eli Friedman872996c2008-08-20 02:34:37 +0000897 case 'Q': // Any register accessible as [r]h: a, b, c, and d.
Anton Korobeynikove7772382009-05-03 13:42:53 +0000898 case 'e': // 32-bit signed integer constant for use with zero-extending
Anders Carlssonff235da2009-01-24 18:03:09 +0000899 // x86_64 instructions.
Anton Korobeynikove7772382009-05-03 13:42:53 +0000900 case 'Z': // 32-bit unsigned integer constant for use with zero-extending
Anders Carlssonff235da2009-01-24 18:03:09 +0000901 // x86_64 instructions.
Eli Friedman872996c2008-08-20 02:34:37 +0000902 case 'N': // unsigned 8-bit integer constant for use with in and out
903 // instructions.
Eli Friedman7e17aed2009-06-08 20:45:44 +0000904 case 'R': // "legacy" registers: ax, bx, cx, dx, di, si, sp, bp.
Chris Lattnerc49cc1a2009-04-26 07:16:29 +0000905 Info.setAllowsRegister();
Eli Friedman872996c2008-08-20 02:34:37 +0000906 return true;
907 }
908}
909
910std::string
911X86TargetInfo::convertConstraint(const char Constraint) const {
912 switch (Constraint) {
913 case 'a': return std::string("{ax}");
914 case 'b': return std::string("{bx}");
915 case 'c': return std::string("{cx}");
916 case 'd': return std::string("{dx}");
917 case 'S': return std::string("{si}");
918 case 'D': return std::string("{di}");
919 case 't': // top of floating point stack.
920 return std::string("{st}");
921 case 'u': // second from top of floating point stack.
922 return std::string("{st(1)}"); // second from top of floating point stack.
923 default:
924 return std::string(1, Constraint);
925 }
926}
Eli Friedman872996c2008-08-20 02:34:37 +0000927} // end anonymous namespace
Chris Lattner4b009652007-07-25 00:24:17 +0000928
929namespace {
Eli Friedman872996c2008-08-20 02:34:37 +0000930// X86-32 generic target
931class X86_32TargetInfo : public X86TargetInfo {
Chris Lattner4b009652007-07-25 00:24:17 +0000932public:
Eli Friedman872996c2008-08-20 02:34:37 +0000933 X86_32TargetInfo(const std::string& triple) : X86TargetInfo(triple) {
934 DoubleAlign = LongLongAlign = 32;
935 LongDoubleWidth = 96;
936 LongDoubleAlign = 32;
Eli Friedman2b161652008-08-21 00:13:15 +0000937 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
938 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
Chris Lattner2e17d912009-11-07 18:59:41 +0000939 "a0:0:64-f80:32:32-n8:16:32";
Eli Friedman04ede302009-03-29 20:31:09 +0000940 SizeType = UnsignedInt;
941 PtrDiffType = SignedInt;
942 IntPtrType = SignedInt;
Anton Korobeynikov8fcffeb2009-04-03 23:38:25 +0000943 RegParmMax = 3;
Eli Friedman872996c2008-08-20 02:34:37 +0000944 }
945 virtual const char *getVAListDeclaration() const {
Eli Friedmanff158dd2008-08-20 07:28:14 +0000946 return "typedef char* __builtin_va_list;";
Eli Friedman872996c2008-08-20 02:34:37 +0000947 }
Chris Lattneraa339182009-09-23 06:06:36 +0000948
949 int getEHDataRegisterNumber(unsigned RegNo) const {
950 if (RegNo == 0) return 0;
951 if (RegNo == 1) return 2;
952 return -1;
953 }
Eli Friedman872996c2008-08-20 02:34:37 +0000954};
955} // end anonymous namespace
956
957namespace {
Eli Friedman1c79f4b2009-07-05 18:47:56 +0000958class OpenBSDI386TargetInfo : public OpenBSDTargetInfo<X86_32TargetInfo> {
959public:
960 OpenBSDI386TargetInfo(const std::string& triple) :
961 OpenBSDTargetInfo<X86_32TargetInfo>(triple) {
962 SizeType = UnsignedLong;
963 IntPtrType = SignedLong;
Eli Friedman96ada022009-07-05 22:31:18 +0000964 PtrDiffType = SignedLong;
Eli Friedman1c79f4b2009-07-05 18:47:56 +0000965 }
966};
967} // end anonymous namespace
968
969namespace {
Edwin Török36565e52009-06-30 17:10:35 +0000970class DarwinI386TargetInfo : public DarwinTargetInfo<X86_32TargetInfo> {
Eli Friedman872996c2008-08-20 02:34:37 +0000971public:
Edwin Török36565e52009-06-30 17:10:35 +0000972 DarwinI386TargetInfo(const std::string& triple) :
973 DarwinTargetInfo<X86_32TargetInfo>(triple) {
Eli Friedman872996c2008-08-20 02:34:37 +0000974 LongDoubleWidth = 128;
975 LongDoubleAlign = 128;
Eli Friedman04ede302009-03-29 20:31:09 +0000976 SizeType = UnsignedLong;
977 IntPtrType = SignedLong;
Eli Friedman2b161652008-08-21 00:13:15 +0000978 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
979 "i64:32:64-f32:32:32-f64:32:64-v64:64:64-v128:128:128-"
Chris Lattner2e17d912009-11-07 18:59:41 +0000980 "a0:0:64-f80:128:128-n8:16:32";
Edwin Török2d98f9f2009-06-30 17:00:25 +0000981 }
982
Eli Friedman872996c2008-08-20 02:34:37 +0000983};
Daniel Dunbar64c77a12009-06-29 20:52:51 +0000984} // end anonymous namespace
985
986namespace {
Eli Friedman23cb7912008-08-21 01:40:19 +0000987// x86-32 Windows target
988class WindowsX86_32TargetInfo : public X86_32TargetInfo {
989public:
990 WindowsX86_32TargetInfo(const std::string& triple)
991 : X86_32TargetInfo(triple) {
Eli Friedman8f575172009-04-19 21:38:35 +0000992 TLSSupported = false;
Chris Lattnera8a69e12009-06-24 17:12:15 +0000993 WCharType = UnsignedShort;
Eli Friedmanb28055e2009-06-08 21:16:17 +0000994 DoubleAlign = LongLongAlign = 64;
995 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
Anton Korobeynikov186e7d32009-12-19 02:05:07 +0000996 "i64:64:64-f32:32:32-f64:64:64-f80:128:128-v64:64:64-"
997 "v128:128:128-a0:0:64-f80:32:32-n8:16:32";
Eli Friedman23cb7912008-08-21 01:40:19 +0000998 }
Chris Lattner79682402009-03-20 15:52:06 +0000999 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001000 MacroBuilder &Builder) const {
1001 X86_32TargetInfo::getTargetDefines(Opts, Builder);
Eli Friedman23cb7912008-08-21 01:40:19 +00001002 // This list is based off of the the list of things MingW defines
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001003 Builder.defineMacro("_WIN32");
1004 DefineStd(Builder, "WIN32", Opts);
1005 DefineStd(Builder, "WINNT", Opts);
1006 Builder.defineMacro("_X86_");
Eli Friedman23cb7912008-08-21 01:40:19 +00001007 }
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001008};
1009} // end anonymous namespace
Eli Friedman6b6ca942009-06-08 06:11:14 +00001010
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001011namespace {
1012
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001013// x86-32 Windows Visual Studio target
1014class VisualStudioWindowsX86_32TargetInfo : public WindowsX86_32TargetInfo {
1015public:
1016 VisualStudioWindowsX86_32TargetInfo(const std::string& triple)
1017 : WindowsX86_32TargetInfo(triple) {
1018 }
1019 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001020 MacroBuilder &Builder) const {
1021 WindowsX86_32TargetInfo::getTargetDefines(Opts, Builder);
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001022 // The value of the following reflects processor type.
1023 // 300=386, 400=486, 500=Pentium, 600=Blend (default)
1024 // We lost the original triple, so we use the default.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001025 Builder.defineMacro("_M_IX86", "600");
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001026 }
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001027};
1028} // end anonymous namespace
1029
1030namespace {
1031// x86-32 MinGW target
1032class MinGWX86_32TargetInfo : public WindowsX86_32TargetInfo {
1033public:
1034 MinGWX86_32TargetInfo(const std::string& triple)
1035 : WindowsX86_32TargetInfo(triple) {
1036 }
1037 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001038 MacroBuilder &Builder) const {
1039 WindowsX86_32TargetInfo::getTargetDefines(Opts, Builder);
1040 Builder.defineMacro("__MSVCRT__");
1041 Builder.defineMacro("__MINGW32__");
1042 Builder.defineMacro("__declspec", "__declspec");
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001043 }
1044};
1045} // end anonymous namespace
1046
1047namespace {
1048// x86-32 Cygwin target
1049class CygwinX86_32TargetInfo : public X86_32TargetInfo {
1050public:
1051 CygwinX86_32TargetInfo(const std::string& triple)
1052 : X86_32TargetInfo(triple) {
1053 TLSSupported = false;
1054 WCharType = UnsignedShort;
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001055 DoubleAlign = LongLongAlign = 64;
1056 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1057 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001058 "a0:0:64-f80:32:32-n8:16:32";
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001059 }
1060 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001061 MacroBuilder &Builder) const {
1062 X86_32TargetInfo::getTargetDefines(Opts, Builder);
1063 Builder.defineMacro("__CYGWIN__");
1064 Builder.defineMacro("__CYGWIN32__");
1065 DefineStd(Builder, "unix", Opts);
Eli Friedman6b6ca942009-06-08 06:11:14 +00001066 }
Eli Friedman23cb7912008-08-21 01:40:19 +00001067};
1068} // end anonymous namespace
1069
1070namespace {
Eli Friedman872996c2008-08-20 02:34:37 +00001071// x86-64 generic target
1072class X86_64TargetInfo : public X86TargetInfo {
1073public:
Chris Lattner79682402009-03-20 15:52:06 +00001074 X86_64TargetInfo(const std::string &triple) : X86TargetInfo(triple) {
Chris Lattnere5fde952008-05-09 06:17:04 +00001075 LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00001076 LongDoubleWidth = 128;
1077 LongDoubleAlign = 128;
Chris Lattnerbfbfbaf2009-02-05 07:32:46 +00001078 IntMaxType = SignedLong;
1079 UIntMaxType = UnsignedLong;
Eli Friedman38e31802009-07-01 03:36:11 +00001080 Int64Type = SignedLong;
Anton Korobeynikov8fcffeb2009-04-03 23:38:25 +00001081 RegParmMax = 6;
Chris Lattnerbfbfbaf2009-02-05 07:32:46 +00001082
Eli Friedman2b161652008-08-21 00:13:15 +00001083 DescriptionString = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1084 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001085 "a0:0:64-s0:64:64-f80:128:128-n8:16:32:64";
Chris Lattner4b009652007-07-25 00:24:17 +00001086 }
Anders Carlsson8b58e8a2007-10-13 00:45:48 +00001087 virtual const char *getVAListDeclaration() const {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001088 return "typedef struct __va_list_tag {"
1089 " unsigned gp_offset;"
1090 " unsigned fp_offset;"
1091 " void* overflow_arg_area;"
1092 " void* reg_save_area;"
Eli Friedman3c79eee2009-07-03 00:45:06 +00001093 "} __va_list_tag;"
1094 "typedef __va_list_tag __builtin_va_list[1];";
Anders Carlsson7dd1c952007-11-24 23:38:12 +00001095 }
Chris Lattneraa339182009-09-23 06:06:36 +00001096
1097 int getEHDataRegisterNumber(unsigned RegNo) const {
1098 if (RegNo == 0) return 0;
1099 if (RegNo == 1) return 1;
1100 return -1;
1101 }
Eli Friedman872996c2008-08-20 02:34:37 +00001102};
1103} // end anonymous namespace
1104
1105namespace {
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001106// x86-64 Windows target
1107class WindowsX86_64TargetInfo : public X86_64TargetInfo {
1108public:
1109 WindowsX86_64TargetInfo(const std::string& triple)
1110 : X86_64TargetInfo(triple) {
1111 TLSSupported = false;
1112 WCharType = UnsignedShort;
Mike Stump4da7a162009-10-08 23:00:00 +00001113 LongWidth = LongAlign = 32;
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001114 DoubleAlign = LongLongAlign = 64;
1115 }
1116 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001117 MacroBuilder &Builder) const {
1118 X86_64TargetInfo::getTargetDefines(Opts, Builder);
1119 Builder.defineMacro("_WIN64");
1120 DefineStd(Builder, "WIN64", Opts);
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001121 }
1122};
1123} // end anonymous namespace
1124
1125namespace {
1126// x86-64 Windows Visual Studio target
1127class VisualStudioWindowsX86_64TargetInfo : public WindowsX86_64TargetInfo {
1128public:
1129 VisualStudioWindowsX86_64TargetInfo(const std::string& triple)
1130 : WindowsX86_64TargetInfo(triple) {
1131 }
1132 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001133 MacroBuilder &Builder) const {
1134 WindowsX86_64TargetInfo::getTargetDefines(Opts, Builder);
1135 Builder.defineMacro("_M_X64");
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001136 }
1137 virtual const char *getVAListDeclaration() const {
1138 return "typedef char* va_list;";
1139 }
1140};
1141} // end anonymous namespace
1142
1143namespace {
1144// x86-64 MinGW target
1145class MinGWX86_64TargetInfo : public WindowsX86_64TargetInfo {
1146public:
1147 MinGWX86_64TargetInfo(const std::string& triple)
1148 : WindowsX86_64TargetInfo(triple) {
1149 }
1150 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001151 MacroBuilder &Builder) const {
1152 WindowsX86_64TargetInfo::getTargetDefines(Opts, Builder);
1153 Builder.defineMacro("__MSVCRT__");
1154 Builder.defineMacro("__MINGW64__");
1155 Builder.defineMacro("__declspec");
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00001156 }
1157};
1158} // end anonymous namespace
1159
1160namespace {
Eli Friedman38e31802009-07-01 03:36:11 +00001161class DarwinX86_64TargetInfo : public DarwinTargetInfo<X86_64TargetInfo> {
1162public:
Mike Stump25cf7602009-09-09 15:08:12 +00001163 DarwinX86_64TargetInfo(const std::string& triple)
Eli Friedman38e31802009-07-01 03:36:11 +00001164 : DarwinTargetInfo<X86_64TargetInfo>(triple) {
1165 Int64Type = SignedLongLong;
1166 }
1167};
1168} // end anonymous namespace
1169
1170namespace {
Eli Friedman96ada022009-07-05 22:31:18 +00001171class OpenBSDX86_64TargetInfo : public OpenBSDTargetInfo<X86_64TargetInfo> {
1172public:
Mike Stump25cf7602009-09-09 15:08:12 +00001173 OpenBSDX86_64TargetInfo(const std::string& triple)
Eli Friedman96ada022009-07-05 22:31:18 +00001174 : OpenBSDTargetInfo<X86_64TargetInfo>(triple) {
1175 IntMaxType = SignedLongLong;
1176 UIntMaxType = UnsignedLongLong;
1177 Int64Type = SignedLongLong;
1178 }
1179};
1180} // end anonymous namespace
1181
1182namespace {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001183class ARMTargetInfo : public TargetInfo {
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001184 // Possible FPU choices.
1185 enum FPUMode {
1186 NoFPU,
1187 VFP2FPU,
1188 VFP3FPU,
1189 NeonFPU
1190 };
1191
1192 static bool FPUModeIsVFP(FPUMode Mode) {
1193 return Mode >= VFP2FPU && Mode <= NeonFPU;
1194 }
1195
1196 static const TargetInfo::GCCRegAlias GCCRegAliases[];
1197 static const char * const GCCRegNames[];
Daniel Dunbar40b774e2009-09-17 07:03:19 +00001198
Daniel Dunbar33b40752009-12-18 18:42:37 +00001199 std::string ABI, CPU;
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001200
1201 unsigned FPU : 3;
1202
Daniel Dunbar48075d82009-12-19 04:15:38 +00001203 unsigned IsThumb : 1;
1204
1205 // Initialized via features.
1206 unsigned SoftFloat : 1;
1207 unsigned SoftFloatABI : 1;
Daniel Dunbar0d83d512009-09-14 00:35:03 +00001208
Chris Lattner9fd73612008-04-21 18:56:49 +00001209public:
Daniel Dunbarf0156562009-09-17 16:21:10 +00001210 ARMTargetInfo(const std::string &TripleStr)
Daniel Dunbar33b40752009-12-18 18:42:37 +00001211 : TargetInfo(TripleStr), ABI("aapcs-linux"), CPU("arm1136j-s")
Daniel Dunbar0d83d512009-09-14 00:35:03 +00001212 {
Daniel Dunbarb9531632009-09-14 00:02:24 +00001213 SizeType = UnsignedInt;
1214 PtrDiffType = SignedInt;
Daniel Dunbarf0156562009-09-17 16:21:10 +00001215
Daniel Dunbar33b40752009-12-18 18:42:37 +00001216 // FIXME: Should we just treat this as a feature?
Daniel Dunbar0a542ca2009-12-18 19:57:13 +00001217 IsThumb = getTriple().getArchName().startswith("thumb");
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001218 if (IsThumb) {
1219 DescriptionString = ("e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-"
1220 "i64:64:64-f32:32:32-f64:64:64-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001221 "v64:64:64-v128:128:128-a0:0:32-n32");
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001222 } else {
1223 DescriptionString = ("e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1224 "i64:64:64-f32:32:32-f64:64:64-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001225 "v64:64:64-v128:128:128-a0:0:64-n32");
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001226 }
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00001227 }
Daniel Dunbar0d83d512009-09-14 00:35:03 +00001228 virtual const char *getABI() const { return ABI.c_str(); }
Daniel Dunbarb9531632009-09-14 00:02:24 +00001229 virtual bool setABI(const std::string &Name) {
Daniel Dunbar0d83d512009-09-14 00:35:03 +00001230 ABI = Name;
1231
Daniel Dunbarb9531632009-09-14 00:02:24 +00001232 // The defaults (above) are for AAPCS, check if we need to change them.
1233 //
1234 // FIXME: We need support for -meabi... we could just mangle it into the
1235 // name.
1236 if (Name == "apcs-gnu") {
Daniel Dunbarda94a772010-01-27 20:23:08 +00001237 DoubleAlign = LongLongAlign = LongDoubleAlign = 32;
Daniel Dunbarb9531632009-09-14 00:02:24 +00001238 SizeType = UnsignedLong;
1239
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001240 if (IsThumb) {
1241 DescriptionString = ("e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-"
1242 "i64:32:32-f32:32:32-f64:32:32-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001243 "v64:64:64-v128:128:128-a0:0:32-n32");
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001244 } else {
1245 DescriptionString = ("e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
1246 "i64:32:32-f32:32:32-f64:32:32-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001247 "v64:64:64-v128:128:128-a0:0:64-n32");
Daniel Dunbar54f62dc2009-09-22 21:44:58 +00001248 }
1249
Daniel Dunbarb9531632009-09-14 00:02:24 +00001250 // FIXME: Override "preferred align" for double and long long.
1251 } else if (Name == "aapcs") {
1252 // FIXME: Enumerated types are variable width in straight AAPCS.
1253 } else if (Name == "aapcs-linux") {
1254 ;
1255 } else
1256 return false;
1257
1258 return true;
1259 }
Daniel Dunbar48075d82009-12-19 04:15:38 +00001260
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001261 void getDefaultFeatures(const std::string &CPU,
1262 llvm::StringMap<bool> &Features) const {
1263 // FIXME: This should not be here.
1264 Features["vfp2"] = false;
1265 Features["vfp3"] = false;
1266 Features["neon"] = false;
1267
1268 if (CPU == "arm1136jf-s" || CPU == "arm1176jzf-s" || CPU == "mpcore")
1269 Features["vfp2"] = true;
1270 else if (CPU == "cortex-a8" || CPU == "cortex-a9")
1271 Features["neon"] = true;
1272 }
1273
Daniel Dunbar48075d82009-12-19 04:15:38 +00001274 virtual bool setFeatureEnabled(llvm::StringMap<bool> &Features,
1275 const std::string &Name,
1276 bool Enabled) const {
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001277 if (Name == "soft-float" || Name == "soft-float-abi") {
1278 Features[Name] = Enabled;
1279 } else if (Name == "vfp2" || Name == "vfp3" || Name == "neon") {
1280 // These effectively are a single option, reset them when any is enabled.
1281 if (Enabled)
1282 Features["vfp2"] = Features["vfp3"] = Features["neon"] = false;
1283 Features[Name] = Enabled;
1284 } else
Daniel Dunbar48075d82009-12-19 04:15:38 +00001285 return false;
1286
Daniel Dunbar48075d82009-12-19 04:15:38 +00001287 return true;
1288 }
1289
1290 virtual void HandleTargetFeatures(std::vector<std::string> &Features) {
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001291 FPU = NoFPU;
Daniel Dunbar48075d82009-12-19 04:15:38 +00001292 SoftFloat = SoftFloatABI = false;
1293 for (unsigned i = 0, e = Features.size(); i != e; ++i) {
1294 if (Features[i] == "+soft-float")
1295 SoftFloat = true;
1296 else if (Features[i] == "+soft-float-abi")
1297 SoftFloatABI = true;
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001298 else if (Features[i] == "+vfp2")
1299 FPU = VFP2FPU;
1300 else if (Features[i] == "+vfp3")
1301 FPU = VFP3FPU;
1302 else if (Features[i] == "+neon")
1303 FPU = NeonFPU;
Daniel Dunbar48075d82009-12-19 04:15:38 +00001304 }
1305
1306 // Remove front-end specific options which the backend handles differently.
1307 std::vector<std::string>::iterator it;
1308 it = std::find(Features.begin(), Features.end(), "+soft-float");
1309 if (it != Features.end())
1310 Features.erase(it);
1311 it = std::find(Features.begin(), Features.end(), "+soft-float-abi");
1312 if (it != Features.end())
1313 Features.erase(it);
1314 }
1315
Daniel Dunbar33b40752009-12-18 18:42:37 +00001316 static const char *getCPUDefineSuffix(llvm::StringRef Name) {
1317 return llvm::StringSwitch<const char*>(Name)
1318 .Cases("arm8", "arm810", "4")
1319 .Cases("strongarm", "strongarm110", "strongarm1100", "strongarm1110", "4")
1320 .Cases("arm7tdmi", "arm7tdmi-s", "arm710t", "arm720t", "arm9", "4T")
1321 .Cases("arm9tdmi", "arm920", "arm920t", "arm922t", "arm940t", "4T")
1322 .Case("ep9312", "4T")
1323 .Cases("arm10tdmi", "arm1020t", "5T")
1324 .Cases("arm9e", "arm946e-s", "arm966e-s", "arm968e-s", "5TE")
1325 .Case("arm926ej-s", "5TEJ")
1326 .Cases("arm10e", "arm1020e", "arm1022e", "5TE")
1327 .Cases("xscale", "iwmmxt", "5TE")
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001328 .Case("arm1136j-s", "6J")
Daniel Dunbar33b40752009-12-18 18:42:37 +00001329 .Cases("arm1176jz-s", "arm1176jzf-s", "6ZK")
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001330 .Cases("arm1136jf-s", "mpcorenovfp", "mpcore", "6K")
Daniel Dunbar33b40752009-12-18 18:42:37 +00001331 .Cases("arm1156t2-s", "arm1156t2f-s", "6T2")
1332 .Cases("cortex-a8", "cortex-a9", "7A")
1333 .Default(0);
1334 }
1335 virtual bool setCPU(const std::string &Name) {
1336 if (!getCPUDefineSuffix(Name))
1337 return false;
1338
1339 CPU = Name;
1340 return true;
1341 }
Chris Lattner79682402009-03-20 15:52:06 +00001342 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001343 MacroBuilder &Builder) const {
Chris Lattnerbef1d722009-03-02 22:27:17 +00001344 // Target identification.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001345 Builder.defineMacro("__arm");
1346 Builder.defineMacro("__arm__");
Anton Korobeynikove7772382009-05-03 13:42:53 +00001347
Chris Lattnerbef1d722009-03-02 22:27:17 +00001348 // Target properties.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001349 Builder.defineMacro("__ARMEL__");
1350 Builder.defineMacro("__LITTLE_ENDIAN__");
1351 Builder.defineMacro("__REGISTER_PREFIX__", "");
Daniel Dunbar33b40752009-12-18 18:42:37 +00001352
1353 llvm::StringRef CPUArch = getCPUDefineSuffix(CPU);
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001354 Builder.defineMacro("__ARM_ARCH_" + CPUArch + "__");
Anton Korobeynikove7772382009-05-03 13:42:53 +00001355
Mike Stumpf90a29f2009-04-08 02:07:04 +00001356 // Subtarget options.
Daniel Dunbarf0156562009-09-17 16:21:10 +00001357
Daniel Dunbar33b40752009-12-18 18:42:37 +00001358 // FIXME: It's more complicated than this and we don't really support
1359 // interworking.
1360 if ('5' <= CPUArch[0] && CPUArch[0] <= '7')
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001361 Builder.defineMacro("__THUMB_INTERWORK__");
Daniel Dunbar33b40752009-12-18 18:42:37 +00001362
Daniel Dunbar33b40752009-12-18 18:42:37 +00001363 if (ABI == "aapcs" || ABI == "aapcs-linux")
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001364 Builder.defineMacro("__ARM_EABI__");
Daniel Dunbar33b40752009-12-18 18:42:37 +00001365
Daniel Dunbar48075d82009-12-19 04:15:38 +00001366 if (SoftFloat)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001367 Builder.defineMacro("__SOFTFP__");
Daniel Dunbar33b40752009-12-18 18:42:37 +00001368
1369 if (CPU == "xscale")
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001370 Builder.defineMacro("__XSCALE__");
Daniel Dunbarf0156562009-09-17 16:21:10 +00001371
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001372 bool IsThumb2 = IsThumb && (CPUArch == "6T2" || CPUArch.startswith("7"));
Daniel Dunbarf0156562009-09-17 16:21:10 +00001373 if (IsThumb) {
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001374 Builder.defineMacro("__THUMBEL__");
1375 Builder.defineMacro("__thumb__");
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001376 if (IsThumb2)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001377 Builder.defineMacro("__thumb2__");
Daniel Dunbarf0156562009-09-17 16:21:10 +00001378 }
1379
1380 // Note, this is always on in gcc, even though it doesn't make sense.
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001381 Builder.defineMacro("__APCS_32__");
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001382
1383 if (FPUModeIsVFP((FPUMode) FPU))
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001384 Builder.defineMacro("__VFP_FP__");
Daniel Dunbar96be2a42009-12-21 23:28:17 +00001385
1386 // This only gets set when Neon instructions are actually available, unlike
1387 // the VFP define, hence the soft float and arch check. This is subtly
1388 // different from gcc, we follow the intent which was that it should be set
1389 // when Neon instructions are actually available.
1390 if (FPU == NeonFPU && !SoftFloat && IsThumb2)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001391 Builder.defineMacro("__ARM_NEON__");
Daniel Dunbarf0156562009-09-17 16:21:10 +00001392
Daniel Dunbar0a542ca2009-12-18 19:57:13 +00001393 if (getTriple().getOS() == llvm::Triple::Darwin)
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001394 Builder.defineMacro("__USING_SJLJ_EXCEPTIONS__");
Chris Lattner9fd73612008-04-21 18:56:49 +00001395 }
1396 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1397 unsigned &NumRecords) const {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001398 // FIXME: Implement.
1399 Records = 0;
Chris Lattner9fd73612008-04-21 18:56:49 +00001400 NumRecords = 0;
1401 }
1402 virtual const char *getVAListDeclaration() const {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001403 return "typedef char* __builtin_va_list;";
Chris Lattner9fd73612008-04-21 18:56:49 +00001404 }
Anton Korobeynikove7772382009-05-03 13:42:53 +00001405 virtual void getGCCRegNames(const char * const *&Names,
Daniel Dunbar40b774e2009-09-17 07:03:19 +00001406 unsigned &NumNames) const;
Anton Korobeynikove7772382009-05-03 13:42:53 +00001407 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Daniel Dunbar40b774e2009-09-17 07:03:19 +00001408 unsigned &NumAliases) const;
Anders Carlsson36834a72009-02-28 17:11:49 +00001409 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattnerc49cc1a2009-04-26 07:16:29 +00001410 TargetInfo::ConstraintInfo &Info) const {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001411 // FIXME: Check if this is complete
Anders Carlsson36834a72009-02-28 17:11:49 +00001412 switch (*Name) {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001413 default:
Nate Begeman222823a2008-04-22 05:03:19 +00001414 case 'l': // r0-r7
1415 case 'h': // r8-r15
1416 case 'w': // VFP Floating point register single precision
1417 case 'P': // VFP Floating point register double precision
Chris Lattnerc49cc1a2009-04-26 07:16:29 +00001418 Info.setAllowsRegister();
Nate Begeman222823a2008-04-22 05:03:19 +00001419 return true;
1420 }
Chris Lattner9fd73612008-04-21 18:56:49 +00001421 return false;
1422 }
1423 virtual const char *getClobbers() const {
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001424 // FIXME: Is this really right?
Chris Lattner9fd73612008-04-21 18:56:49 +00001425 return "";
1426 }
1427};
Daniel Dunbar40b774e2009-09-17 07:03:19 +00001428
1429const char * const ARMTargetInfo::GCCRegNames[] = {
1430 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1431 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
1432};
1433
1434void ARMTargetInfo::getGCCRegNames(const char * const *&Names,
1435 unsigned &NumNames) const {
1436 Names = GCCRegNames;
1437 NumNames = llvm::array_lengthof(GCCRegNames);
1438}
1439
1440const TargetInfo::GCCRegAlias ARMTargetInfo::GCCRegAliases[] = {
1441
1442 { { "a1" }, "r0" },
1443 { { "a2" }, "r1" },
1444 { { "a3" }, "r2" },
1445 { { "a4" }, "r3" },
1446 { { "v1" }, "r4" },
1447 { { "v2" }, "r5" },
1448 { { "v3" }, "r6" },
1449 { { "v4" }, "r7" },
1450 { { "v5" }, "r8" },
1451 { { "v6", "rfp" }, "r9" },
1452 { { "sl" }, "r10" },
1453 { { "fp" }, "r11" },
1454 { { "ip" }, "r12" },
1455 { { "sp" }, "r13" },
1456 { { "lr" }, "r14" },
1457 { { "pc" }, "r15" },
1458};
1459
1460void ARMTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
1461 unsigned &NumAliases) const {
1462 Aliases = GCCRegAliases;
1463 NumAliases = llvm::array_lengthof(GCCRegAliases);
1464}
Chris Lattner9fd73612008-04-21 18:56:49 +00001465} // end anonymous namespace.
1466
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001467
1468namespace {
Mike Stump25cf7602009-09-09 15:08:12 +00001469class DarwinARMTargetInfo :
Edwin Török36565e52009-06-30 17:10:35 +00001470 public DarwinTargetInfo<ARMTargetInfo> {
1471protected:
Daniel Dunbar608b3882009-08-24 09:10:05 +00001472 virtual void getOSDefines(const LangOptions &Opts, const llvm::Triple &Triple,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001473 MacroBuilder &Builder) const {
Daniel Dunbareab96a22010-01-26 01:44:04 +00001474 getDarwinDefines(Builder, Opts, Triple);
Eli Friedman8f575172009-04-19 21:38:35 +00001475 }
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001476
Edwin Török36565e52009-06-30 17:10:35 +00001477public:
Mike Stump25cf7602009-09-09 15:08:12 +00001478 DarwinARMTargetInfo(const std::string& triple)
Edwin Török36565e52009-06-30 17:10:35 +00001479 : DarwinTargetInfo<ARMTargetInfo>(triple) {}
Eli Friedmanbe727fe2008-08-20 07:44:10 +00001480};
1481} // end anonymous namespace.
1482
Chris Lattner4b009652007-07-25 00:24:17 +00001483namespace {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001484class SparcV8TargetInfo : public TargetInfo {
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001485 static const TargetInfo::GCCRegAlias GCCRegAliases[];
1486 static const char * const GCCRegNames[];
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001487public:
Eli Friedmanff158dd2008-08-20 07:28:14 +00001488 SparcV8TargetInfo(const std::string& triple) : TargetInfo(triple) {
1489 // FIXME: Support Sparc quad-precision long double?
Eli Friedman2b161652008-08-21 00:13:15 +00001490 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-"
Chris Lattner2e17d912009-11-07 18:59:41 +00001491 "i64:64:64-f32:32:32-f64:64:64-v64:64:64-n32";
Eli Friedmanff158dd2008-08-20 07:28:14 +00001492 }
Chris Lattner79682402009-03-20 15:52:06 +00001493 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001494 MacroBuilder &Builder) const {
1495 DefineStd(Builder, "sparc", Opts);
1496 Builder.defineMacro("__sparcv8");
1497 Builder.defineMacro("__REGISTER_PREFIX__", "");
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001498 }
1499 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1500 unsigned &NumRecords) const {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001501 // FIXME: Implement!
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001502 }
1503 virtual const char *getVAListDeclaration() const {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001504 return "typedef void* __builtin_va_list;";
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001505 }
Anton Korobeynikove7772382009-05-03 13:42:53 +00001506 virtual void getGCCRegNames(const char * const *&Names,
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001507 unsigned &NumNames) const;
Anton Korobeynikove7772382009-05-03 13:42:53 +00001508 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001509 unsigned &NumAliases) const;
Anders Carlsson36834a72009-02-28 17:11:49 +00001510 virtual bool validateAsmConstraint(const char *&Name,
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001511 TargetInfo::ConstraintInfo &info) const {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001512 // FIXME: Implement!
1513 return false;
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001514 }
1515 virtual const char *getClobbers() const {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001516 // FIXME: Implement!
1517 return "";
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001518 }
1519};
1520
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001521const char * const SparcV8TargetInfo::GCCRegNames[] = {
1522 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1523 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15",
1524 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23",
1525 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31"
1526};
1527
Anton Korobeynikove7772382009-05-03 13:42:53 +00001528void SparcV8TargetInfo::getGCCRegNames(const char * const *&Names,
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001529 unsigned &NumNames) const {
1530 Names = GCCRegNames;
1531 NumNames = llvm::array_lengthof(GCCRegNames);
1532}
1533
1534const TargetInfo::GCCRegAlias SparcV8TargetInfo::GCCRegAliases[] = {
Anton Korobeynikove7772382009-05-03 13:42:53 +00001535 { { "g0" }, "r0" },
1536 { { "g1" }, "r1" },
1537 { { "g2" }, "r2" },
1538 { { "g3" }, "r3" },
1539 { { "g4" }, "r4" },
1540 { { "g5" }, "r5" },
1541 { { "g6" }, "r6" },
1542 { { "g7" }, "r7" },
1543 { { "o0" }, "r8" },
1544 { { "o1" }, "r9" },
1545 { { "o2" }, "r10" },
1546 { { "o3" }, "r11" },
1547 { { "o4" }, "r12" },
1548 { { "o5" }, "r13" },
1549 { { "o6", "sp" }, "r14" },
1550 { { "o7" }, "r15" },
1551 { { "l0" }, "r16" },
1552 { { "l1" }, "r17" },
1553 { { "l2" }, "r18" },
1554 { { "l3" }, "r19" },
1555 { { "l4" }, "r20" },
1556 { { "l5" }, "r21" },
1557 { { "l6" }, "r22" },
1558 { { "l7" }, "r23" },
1559 { { "i0" }, "r24" },
1560 { { "i1" }, "r25" },
1561 { { "i2" }, "r26" },
1562 { { "i3" }, "r27" },
1563 { { "i4" }, "r28" },
1564 { { "i5" }, "r29" },
1565 { { "i6", "fp" }, "r30" },
1566 { { "i7" }, "r31" },
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001567};
1568
Anton Korobeynikove7772382009-05-03 13:42:53 +00001569void SparcV8TargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattnerff7c53d2009-01-27 01:58:38 +00001570 unsigned &NumAliases) const {
1571 Aliases = GCCRegAliases;
1572 NumAliases = llvm::array_lengthof(GCCRegAliases);
1573}
Gabor Greif8a3ff0d2008-02-21 16:29:08 +00001574} // end anonymous namespace.
1575
Eli Friedmanff158dd2008-08-20 07:28:14 +00001576namespace {
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +00001577class AuroraUXSparcV8TargetInfo : public AuroraUXTargetInfo<SparcV8TargetInfo> {
1578public:
1579 AuroraUXSparcV8TargetInfo(const std::string& triple) :
1580 AuroraUXTargetInfo<SparcV8TargetInfo>(triple) {
1581 SizeType = UnsignedInt;
1582 PtrDiffType = SignedInt;
1583 }
1584};
Edwin Török36565e52009-06-30 17:10:35 +00001585class SolarisSparcV8TargetInfo : public SolarisTargetInfo<SparcV8TargetInfo> {
Eli Friedmanff158dd2008-08-20 07:28:14 +00001586public:
1587 SolarisSparcV8TargetInfo(const std::string& triple) :
Edwin Török36565e52009-06-30 17:10:35 +00001588 SolarisTargetInfo<SparcV8TargetInfo>(triple) {
Eli Friedman7cca0982008-11-02 02:43:55 +00001589 SizeType = UnsignedInt;
1590 PtrDiffType = SignedInt;
Eli Friedmanff158dd2008-08-20 07:28:14 +00001591 }
1592};
1593} // end anonymous namespace.
Chris Lattner4b009652007-07-25 00:24:17 +00001594
Chris Lattner85970f32008-05-08 05:58:21 +00001595namespace {
1596 class PIC16TargetInfo : public TargetInfo{
1597 public:
1598 PIC16TargetInfo(const std::string& triple) : TargetInfo(triple) {
Eli Friedman8f575172009-04-19 21:38:35 +00001599 TLSSupported = false;
Sanjiv Guptafa451432008-10-31 09:52:39 +00001600 IntWidth = 16;
1601 LongWidth = LongLongWidth = 32;
1602 PointerWidth = 16;
1603 IntAlign = 8;
1604 LongAlign = LongLongAlign = 8;
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00001605 PointerAlign = 8;
Sanjiv Guptafa451432008-10-31 09:52:39 +00001606 SizeType = UnsignedInt;
1607 IntMaxType = SignedLong;
1608 UIntMaxType = UnsignedLong;
Chris Lattnerd9ef7242009-02-13 22:28:55 +00001609 IntPtrType = SignedShort;
Eli Friedman7cca0982008-11-02 02:43:55 +00001610 PtrDiffType = SignedInt;
Edward O'Callaghan14a70a32009-11-21 00:49:54 +00001611 SigAtomicType = SignedLong;
Sanjiv Guptaae8f1e82009-06-02 04:43:46 +00001612 FloatWidth = 32;
1613 FloatAlign = 32;
1614 DoubleWidth = 32;
1615 DoubleAlign = 32;
1616 LongDoubleWidth = 32;
1617 LongDoubleAlign = 32;
1618 FloatFormat = &llvm::APFloat::IEEEsingle;
1619 DoubleFormat = &llvm::APFloat::IEEEsingle;
1620 LongDoubleFormat = &llvm::APFloat::IEEEsingle;
Chris Lattner2e17d912009-11-07 18:59:41 +00001621 DescriptionString = "e-p:16:8:8-i8:8:8-i16:8:8-i32:8:8-f32:32:32-n8";
Sanjiv Guptaae8f1e82009-06-02 04:43:46 +00001622
Chris Lattner85970f32008-05-08 05:58:21 +00001623 }
Chris Lattner727b3c42008-05-09 06:08:39 +00001624 virtual uint64_t getPointerWidthV(unsigned AddrSpace) const { return 16; }
1625 virtual uint64_t getPointerAlignV(unsigned AddrSpace) const { return 8; }
Chris Lattner79682402009-03-20 15:52:06 +00001626 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001627 MacroBuilder &Builder) const {
1628 Builder.defineMacro("__pic16");
1629 Builder.defineMacro("rom", "__attribute__((address_space(1)))");
1630 Builder.defineMacro("ram", "__attribute__((address_space(0)))");
1631 Builder.defineMacro("_section(SectName)",
Sanjiv Gupta9e2b9e02009-08-20 17:48:52 +00001632 "__attribute__((section(SectName)))");
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001633 Builder.defineMacro("near",
Sanjiv Gupta09e95f02009-10-24 18:08:20 +00001634 "__attribute__((section(\"Address=NEAR\")))");
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001635 Builder.defineMacro("_address(Addr)",
Sanjiv Gupta9e2b9e02009-08-20 17:48:52 +00001636 "__attribute__((section(\"Address=\"#Addr)))");
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001637 Builder.defineMacro("_CONFIG(conf)", "asm(\"CONFIG \"#conf)");
1638 Builder.defineMacro("_interrupt",
Sanjiv Gupta9e2b9e02009-08-20 17:48:52 +00001639 "__attribute__((section(\"interrupt=0x4\"))) \
1640 __attribute__((used))");
Chris Lattner85970f32008-05-08 05:58:21 +00001641 }
1642 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1643 unsigned &NumRecords) const {}
Mike Stump25cf7602009-09-09 15:08:12 +00001644 virtual const char *getVAListDeclaration() const {
Daniel Dunbar2e967de2009-08-24 09:54:37 +00001645 return "";
1646 }
1647 virtual const char *getClobbers() const {
1648 return "";
1649 }
Anton Korobeynikove7772382009-05-03 13:42:53 +00001650 virtual void getGCCRegNames(const char * const *&Names,
1651 unsigned &NumNames) const {}
1652 virtual bool validateAsmConstraint(const char *&Name,
Chris Lattner85970f32008-05-08 05:58:21 +00001653 TargetInfo::ConstraintInfo &info) const {
1654 return true;
1655 }
Anton Korobeynikove7772382009-05-03 13:42:53 +00001656 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
Chris Lattner85970f32008-05-08 05:58:21 +00001657 unsigned &NumAliases) const {}
1658 virtual bool useGlobalsForAutomaticVariables() const {return true;}
1659 };
1660}
1661
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001662namespace {
1663 class MSP430TargetInfo : public TargetInfo {
1664 static const char * const GCCRegNames[];
1665 public:
1666 MSP430TargetInfo(const std::string& triple) : TargetInfo(triple) {
1667 TLSSupported = false;
Anton Korobeynikov2a6630a2010-01-30 12:55:11 +00001668 IntWidth = 16; IntAlign = 16;
1669 LongWidth = 32; LongLongWidth = 64;
1670 LongAlign = LongLongAlign = 16;
1671 PointerWidth = 16; PointerAlign = 16;
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001672 SizeType = UnsignedInt;
1673 IntMaxType = SignedLong;
1674 UIntMaxType = UnsignedLong;
1675 IntPtrType = SignedShort;
1676 PtrDiffType = SignedInt;
Edward O'Callaghan14a70a32009-11-21 00:49:54 +00001677 SigAtomicType = SignedLong;
Anton Korobeynikov314713f2009-12-19 01:32:37 +00001678 DescriptionString = "e-p:16:16:16-i8:8:8-i16:16:16-i32:16:32-n8:16";
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001679 }
1680 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001681 MacroBuilder &Builder) const {
1682 Builder.defineMacro("MSP430");
1683 Builder.defineMacro("__MSP430__");
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001684 // FIXME: defines for different 'flavours' of MCU
1685 }
1686 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1687 unsigned &NumRecords) const {
1688 // FIXME: Implement.
1689 Records = 0;
1690 NumRecords = 0;
1691 }
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001692 virtual void getGCCRegNames(const char * const *&Names,
1693 unsigned &NumNames) const;
1694 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1695 unsigned &NumAliases) const {
1696 // No aliases.
1697 Aliases = 0;
1698 NumAliases = 0;
1699 }
1700 virtual bool validateAsmConstraint(const char *&Name,
1701 TargetInfo::ConstraintInfo &info) const {
Anton Korobeynikov174219b2009-10-15 23:17:13 +00001702 // No target constraints for now.
1703 return false;
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001704 }
1705 virtual const char *getClobbers() const {
1706 // FIXME: Is this really right?
1707 return "";
1708 }
1709 virtual const char *getVAListDeclaration() const {
1710 // FIXME: implement
Anton Korobeynikovf5955592009-05-08 18:24:57 +00001711 return "typedef char* __builtin_va_list;";
Anton Korobeynikov954bd3f2009-05-03 13:43:08 +00001712 }
1713 };
1714
1715 const char * const MSP430TargetInfo::GCCRegNames[] = {
1716 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1717 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
1718 };
1719
1720 void MSP430TargetInfo::getGCCRegNames(const char * const *&Names,
1721 unsigned &NumNames) const {
1722 Names = GCCRegNames;
1723 NumNames = llvm::array_lengthof(GCCRegNames);
1724 }
1725}
1726
1727
Anton Korobeynikov57f236f2009-07-16 20:09:57 +00001728namespace {
1729 class SystemZTargetInfo : public TargetInfo {
1730 static const char * const GCCRegNames[];
1731 public:
1732 SystemZTargetInfo(const std::string& triple) : TargetInfo(triple) {
1733 TLSSupported = false;
1734 IntWidth = IntAlign = 32;
1735 LongWidth = LongLongWidth = LongAlign = LongLongAlign = 64;
1736 PointerWidth = PointerAlign = 64;
Chris Lattner2e17d912009-11-07 18:59:41 +00001737 DescriptionString = "E-p:64:64:64-i8:8:16-i16:16:16-i32:32:32-"
1738 "i64:64:64-f32:32:32-f64:64:64-f128:128:128-a0:16:16-n32:64";
Anton Korobeynikov57f236f2009-07-16 20:09:57 +00001739 }
1740 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001741 MacroBuilder &Builder) const {
1742 Builder.defineMacro("__s390__");
1743 Builder.defineMacro("__s390x__");
Anton Korobeynikov57f236f2009-07-16 20:09:57 +00001744 }
1745 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1746 unsigned &NumRecords) const {
1747 // FIXME: Implement.
1748 Records = 0;
1749 NumRecords = 0;
1750 }
Anton Korobeynikov57f236f2009-07-16 20:09:57 +00001751
Anton Korobeynikov57f236f2009-07-16 20:09:57 +00001752 virtual void getGCCRegNames(const char * const *&Names,
1753 unsigned &NumNames) const;
1754 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1755 unsigned &NumAliases) const {
1756 // No aliases.
1757 Aliases = 0;
1758 NumAliases = 0;
1759 }
1760 virtual bool validateAsmConstraint(const char *&Name,
1761 TargetInfo::ConstraintInfo &info) const {
1762 // FIXME: implement
1763 return true;
1764 }
1765 virtual const char *getClobbers() const {
1766 // FIXME: Is this really right?
1767 return "";
1768 }
1769 virtual const char *getVAListDeclaration() const {
1770 // FIXME: implement
1771 return "typedef char* __builtin_va_list;";
1772 }
1773 };
1774
1775 const char * const SystemZTargetInfo::GCCRegNames[] = {
1776 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1777 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15"
1778 };
1779
1780 void SystemZTargetInfo::getGCCRegNames(const char * const *&Names,
1781 unsigned &NumNames) const {
1782 Names = GCCRegNames;
1783 NumNames = llvm::array_lengthof(GCCRegNames);
1784 }
1785}
1786
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00001787namespace {
1788 class BlackfinTargetInfo : public TargetInfo {
1789 static const char * const GCCRegNames[];
1790 public:
1791 BlackfinTargetInfo(const std::string& triple) : TargetInfo(triple) {
1792 TLSSupported = false;
1793 DoubleAlign = 32;
1794 LongLongAlign = 32;
1795 LongDoubleAlign = 32;
Chris Lattner2e17d912009-11-07 18:59:41 +00001796 DescriptionString = "e-p:32:32-i64:32-f64:32-n32";
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00001797 }
1798
1799 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001800 MacroBuilder &Builder) const {
1801 DefineStd(Builder, "bfin", Opts);
1802 DefineStd(Builder, "BFIN", Opts);
1803 Builder.defineMacro("__ADSPBLACKFIN__");
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00001804 // FIXME: This one is really dependent on -mcpu
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001805 Builder.defineMacro("__ADSPLPBLACKFIN__");
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00001806 // FIXME: Add cpu-dependent defines and __SILICON_REVISION__
1807 }
1808
1809 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1810 unsigned &NumRecords) const {
1811 // FIXME: Implement.
1812 Records = 0;
1813 NumRecords = 0;
1814 }
1815
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00001816 virtual void getGCCRegNames(const char * const *&Names,
1817 unsigned &NumNames) const;
1818
1819 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1820 unsigned &NumAliases) const {
1821 // No aliases.
1822 Aliases = 0;
1823 NumAliases = 0;
1824 }
1825
1826 virtual bool validateAsmConstraint(const char *&Name,
1827 TargetInfo::ConstraintInfo &Info) const {
1828 if (strchr("adzDWeABbvfcCtukxywZY", Name[0])) {
1829 Info.setAllowsRegister();
1830 return true;
1831 }
1832 return false;
1833 }
1834
1835 virtual const char *getClobbers() const {
1836 return "";
1837 }
1838
1839 virtual const char *getVAListDeclaration() const {
1840 return "typedef char* __builtin_va_list;";
1841 }
1842 };
1843
1844 const char * const BlackfinTargetInfo::GCCRegNames[] = {
1845 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
1846 "p0", "p1", "p2", "p3", "p4", "p5", "sp", "fp",
1847 "i0", "i1", "i2", "i3", "b0", "b1", "b2", "b3",
1848 "l0", "l1", "l2", "l3", "m0", "m1", "m2", "m3",
1849 "a0", "a1", "cc",
1850 "rets", "reti", "retx", "retn", "rete", "astat", "seqstat", "usp",
1851 "argp", "lt0", "lt1", "lc0", "lc1", "lb0", "lb1"
1852 };
1853
1854 void BlackfinTargetInfo::getGCCRegNames(const char * const *&Names,
1855 unsigned &NumNames) const {
1856 Names = GCCRegNames;
1857 NumNames = llvm::array_lengthof(GCCRegNames);
1858 }
1859}
1860
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001861namespace {
1862
Mike Stump25cf7602009-09-09 15:08:12 +00001863 // LLVM and Clang cannot be used directly to output native binaries for
1864 // target, but is used to compile C code to llvm bitcode with correct
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001865 // type and alignment information.
Mike Stump25cf7602009-09-09 15:08:12 +00001866 //
1867 // TCE uses the llvm bitcode as input and uses it for generating customized
1868 // target processor and program binary. TCE co-design environment is
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001869 // publicly available in http://tce.cs.tut.fi
1870
1871 class TCETargetInfo : public TargetInfo{
1872 public:
1873 TCETargetInfo(const std::string& triple) : TargetInfo(triple) {
1874 TLSSupported = false;
1875 IntWidth = 32;
1876 LongWidth = LongLongWidth = 32;
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001877 PointerWidth = 32;
1878 IntAlign = 32;
1879 LongAlign = LongLongAlign = 32;
1880 PointerAlign = 32;
1881 SizeType = UnsignedInt;
1882 IntMaxType = SignedLong;
1883 UIntMaxType = UnsignedLong;
1884 IntPtrType = SignedInt;
1885 PtrDiffType = SignedInt;
1886 FloatWidth = 32;
1887 FloatAlign = 32;
1888 DoubleWidth = 32;
1889 DoubleAlign = 32;
1890 LongDoubleWidth = 32;
1891 LongDoubleAlign = 32;
1892 FloatFormat = &llvm::APFloat::IEEEsingle;
1893 DoubleFormat = &llvm::APFloat::IEEEsingle;
1894 LongDoubleFormat = &llvm::APFloat::IEEEsingle;
1895 DescriptionString = "E-p:32:32:32-a0:32:32"
1896 "-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64"
Chris Lattner2e17d912009-11-07 18:59:41 +00001897 "-f32:32:32-f64:32:64-n32";
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001898 }
1899
1900 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001901 MacroBuilder &Builder) const {
1902 DefineStd(Builder, "tce", Opts);
1903 Builder.defineMacro("__TCE__");
1904 Builder.defineMacro("__TCE_V1__");
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001905 }
1906 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1907 unsigned &NumRecords) const {}
Daniel Dunbar2e967de2009-08-24 09:54:37 +00001908 virtual const char *getClobbers() const {
1909 return "";
1910 }
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001911 virtual const char *getVAListDeclaration() const {
1912 return "typedef void* __builtin_va_list;";
1913 }
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00001914 virtual void getGCCRegNames(const char * const *&Names,
1915 unsigned &NumNames) const {}
1916 virtual bool validateAsmConstraint(const char *&Name,
1917 TargetInfo::ConstraintInfo &info) const {
1918 return true;
1919 }
1920 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1921 unsigned &NumAliases) const {}
1922 };
1923}
1924
Edward O'Callaghan097309f2009-11-15 10:22:07 +00001925namespace {
1926class MipsTargetInfo : public TargetInfo {
1927 static const TargetInfo::GCCRegAlias GCCRegAliases[];
1928 static const char * const GCCRegNames[];
1929public:
1930 MipsTargetInfo(const std::string& triple) : TargetInfo(triple) {
1931 DescriptionString = "E-p:32:32:32-i1:8:8-i8:8:32-i16:16:32-i32:32:32-"
1932 "i64:32:64-f32:32:32-f64:64:64-v64:64:64-n32";
1933 }
1934 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00001935 MacroBuilder &Builder) const {
1936 DefineStd(Builder, "mips", Opts);
1937 Builder.defineMacro("_mips");
1938 DefineStd(Builder, "MIPSEB", Opts);
1939 Builder.defineMacro("_MIPSEB");
1940 Builder.defineMacro("__REGISTER_PREFIX__", "");
Edward O'Callaghan097309f2009-11-15 10:22:07 +00001941 }
1942 virtual void getTargetBuiltins(const Builtin::Info *&Records,
1943 unsigned &NumRecords) const {
1944 // FIXME: Implement!
1945 }
1946 virtual const char *getVAListDeclaration() const {
1947 return "typedef void* __builtin_va_list;";
1948 }
1949 virtual void getGCCRegNames(const char * const *&Names,
1950 unsigned &NumNames) const;
1951 virtual void getGCCRegAliases(const GCCRegAlias *&Aliases,
1952 unsigned &NumAliases) const;
1953 virtual bool validateAsmConstraint(const char *&Name,
1954 TargetInfo::ConstraintInfo &Info) const {
1955 switch (*Name) {
1956 default:
1957 case 'r': // CPU registers.
1958 case 'd': // Equivalent to "r" unless generating MIPS16 code.
1959 case 'y': // Equivalent to "r", backwards compatibility only.
1960 case 'f': // floating-point registers.
1961 Info.setAllowsRegister();
1962 return true;
1963 }
1964 return false;
1965 }
1966
1967 virtual const char *getClobbers() const {
1968 // FIXME: Implement!
1969 return "";
1970 }
1971};
1972
1973const char * const MipsTargetInfo::GCCRegNames[] = {
1974 "$0", "$1", "$2", "$3", "$4", "$5", "$6", "$7",
1975 "$8", "$9", "$10", "$11", "$12", "$13", "$14", "$15",
1976 "$16", "$17", "$18", "$19", "$20", "$21", "$22", "$23",
1977 "$24", "$25", "$26", "$27", "$28", "$sp", "$fp", "$31",
1978 "$f0", "$f1", "$f2", "$f3", "$f4", "$f5", "$f6", "$f7",
1979 "$f8", "$f9", "$f10", "$f11", "$f12", "$f13", "$f14", "$f15",
1980 "$f16", "$f17", "$f18", "$f19", "$f20", "$f21", "$f22", "$f23",
1981 "$f24", "$f25", "$f26", "$f27", "$f28", "$f29", "$f30", "$f31",
1982 "hi", "lo", "", "$fcc0","$fcc1","$fcc2","$fcc3","$fcc4",
1983 "$fcc5","$fcc6","$fcc7"
1984};
1985
1986void MipsTargetInfo::getGCCRegNames(const char * const *&Names,
1987 unsigned &NumNames) const {
1988 Names = GCCRegNames;
1989 NumNames = llvm::array_lengthof(GCCRegNames);
1990}
1991
1992const TargetInfo::GCCRegAlias MipsTargetInfo::GCCRegAliases[] = {
1993 { { "at" }, "$1" },
1994 { { "v0" }, "$2" },
1995 { { "v1" }, "$3" },
1996 { { "a0" }, "$4" },
1997 { { "a1" }, "$5" },
1998 { { "a2" }, "$6" },
1999 { { "a3" }, "$7" },
2000 { { "t0" }, "$8" },
2001 { { "t1" }, "$9" },
2002 { { "t2" }, "$10" },
2003 { { "t3" }, "$11" },
2004 { { "t4" }, "$12" },
2005 { { "t5" }, "$13" },
2006 { { "t6" }, "$14" },
2007 { { "t7" }, "$15" },
2008 { { "s0" }, "$16" },
2009 { { "s1" }, "$17" },
2010 { { "s2" }, "$18" },
2011 { { "s3" }, "$19" },
2012 { { "s4" }, "$20" },
2013 { { "s5" }, "$21" },
2014 { { "s6" }, "$22" },
2015 { { "s7" }, "$23" },
2016 { { "t8" }, "$24" },
2017 { { "t9" }, "$25" },
2018 { { "k0" }, "$26" },
2019 { { "k1" }, "$27" },
2020 { { "gp" }, "$28" },
2021 { { "sp" }, "$29" },
2022 { { "fp" }, "$30" },
2023 { { "ra" }, "$31" }
2024};
2025
2026void MipsTargetInfo::getGCCRegAliases(const GCCRegAlias *&Aliases,
2027 unsigned &NumAliases) const {
2028 Aliases = GCCRegAliases;
2029 NumAliases = llvm::array_lengthof(GCCRegAliases);
2030}
2031} // end anonymous namespace.
2032
2033namespace {
2034class MipselTargetInfo : public MipsTargetInfo {
2035public:
2036 MipselTargetInfo(const std::string& triple) : MipsTargetInfo(triple) {
2037 DescriptionString = "e-p:32:32:32-i1:8:8-i8:8:32-i16:16:32-i32:32:32-"
2038 "i64:32:64-f32:32:32-f64:64:64-v64:64:64-n32";
2039 }
2040
2041 virtual void getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00002042 MacroBuilder &Builder) const;
Edward O'Callaghan097309f2009-11-15 10:22:07 +00002043};
2044
2045void MipselTargetInfo::getTargetDefines(const LangOptions &Opts,
Benjamin Kramer9ffb10432010-01-09 17:55:51 +00002046 MacroBuilder &Builder) const {
2047 DefineStd(Builder, "mips", Opts);
2048 Builder.defineMacro("_mips");
2049 DefineStd(Builder, "MIPSEL", Opts);
2050 Builder.defineMacro("_MIPSEL");
2051 Builder.defineMacro("__REGISTER_PREFIX__", "");
Edward O'Callaghan097309f2009-11-15 10:22:07 +00002052}
2053} // end anonymous namespace.
2054
Chris Lattner4b009652007-07-25 00:24:17 +00002055//===----------------------------------------------------------------------===//
2056// Driver code
2057//===----------------------------------------------------------------------===//
2058
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002059static TargetInfo *AllocateTarget(const std::string &T) {
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002060 llvm::Triple Triple(T);
2061 llvm::Triple::OSType os = Triple.getOS();
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00002062
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002063 switch (Triple.getArch()) {
2064 default:
2065 return NULL;
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00002066
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002067 case llvm::Triple::arm:
Daniel Dunbar3f361b52009-09-11 01:14:50 +00002068 case llvm::Triple::thumb:
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002069 switch (os) {
2070 case llvm::Triple::Darwin:
Eli Friedman2b161652008-08-21 00:13:15 +00002071 return new DarwinARMTargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002072 case llvm::Triple::FreeBSD:
Edwin Török36565e52009-06-30 17:10:35 +00002073 return new FreeBSDTargetInfo<ARMTargetInfo>(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002074 default:
2075 return new ARMTargetInfo(T);
2076 }
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00002077
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002078 case llvm::Triple::bfin:
Jakob Stoklund Olesen61774372009-08-17 20:08:44 +00002079 return new BlackfinTargetInfo(T);
2080
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002081 case llvm::Triple::msp430:
2082 return new MSP430TargetInfo(T);
Eli Friedman0b7b1cb2008-05-20 14:21:01 +00002083
Edward O'Callaghan097309f2009-11-15 10:22:07 +00002084 case llvm::Triple::mips:
2085 if (os == llvm::Triple::Psp)
2086 return new PSPTargetInfo<MipsTargetInfo>(T);
2087 if (os == llvm::Triple::Linux)
2088 return new LinuxTargetInfo<MipsTargetInfo>(T);
2089 return new MipsTargetInfo(T);
2090
2091 case llvm::Triple::mipsel:
2092 if (os == llvm::Triple::Psp)
2093 return new PSPTargetInfo<MipselTargetInfo>(T);
2094 if (os == llvm::Triple::Linux)
2095 return new LinuxTargetInfo<MipselTargetInfo>(T);
2096 return new MipselTargetInfo(T);
2097
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002098 case llvm::Triple::pic16:
2099 return new PIC16TargetInfo(T);
2100
2101 case llvm::Triple::ppc:
2102 if (os == llvm::Triple::Darwin)
2103 return new DarwinTargetInfo<PPCTargetInfo>(T);
2104 return new PPC32TargetInfo(T);
2105
2106 case llvm::Triple::ppc64:
2107 if (os == llvm::Triple::Darwin)
2108 return new DarwinTargetInfo<PPC64TargetInfo>(T);
John Thompsoned7bdbc2009-11-19 17:18:50 +00002109 else if (os == llvm::Triple::Lv2)
2110 return new PS3PPUTargetInfo<PPC64TargetInfo>(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002111 return new PPC64TargetInfo(T);
2112
2113 case llvm::Triple::sparc:
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +00002114 if (os == llvm::Triple::AuroraUX)
2115 return new AuroraUXSparcV8TargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002116 if (os == llvm::Triple::Solaris)
2117 return new SolarisSparcV8TargetInfo(T);
2118 return new SparcV8TargetInfo(T);
2119
John Thompsoned7bdbc2009-11-19 17:18:50 +00002120 // FIXME: Need a real SPU target.
2121 case llvm::Triple::cellspu:
2122 return new PS3SPUTargetInfo<PPC64TargetInfo>(T);
2123
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002124 case llvm::Triple::systemz:
2125 return new SystemZTargetInfo(T);
2126
Eli Friedmanf0ff32f2009-08-19 20:47:07 +00002127 case llvm::Triple::tce:
2128 return new TCETargetInfo(T);
2129
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002130 case llvm::Triple::x86:
2131 switch (os) {
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +00002132 case llvm::Triple::AuroraUX:
2133 return new AuroraUXTargetInfo<X86_32TargetInfo>(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002134 case llvm::Triple::Darwin:
2135 return new DarwinI386TargetInfo(T);
2136 case llvm::Triple::Linux:
2137 return new LinuxTargetInfo<X86_32TargetInfo>(T);
2138 case llvm::Triple::DragonFly:
2139 return new DragonFlyBSDTargetInfo<X86_32TargetInfo>(T);
2140 case llvm::Triple::NetBSD:
2141 return new NetBSDTargetInfo<X86_32TargetInfo>(T);
2142 case llvm::Triple::OpenBSD:
2143 return new OpenBSDI386TargetInfo(T);
2144 case llvm::Triple::FreeBSD:
2145 return new FreeBSDTargetInfo<X86_32TargetInfo>(T);
2146 case llvm::Triple::Solaris:
2147 return new SolarisTargetInfo<X86_32TargetInfo>(T);
2148 case llvm::Triple::Cygwin:
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00002149 return new CygwinX86_32TargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002150 case llvm::Triple::MinGW32:
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00002151 return new MinGWX86_32TargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002152 case llvm::Triple::Win32:
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00002153 return new VisualStudioWindowsX86_32TargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002154 default:
2155 return new X86_32TargetInfo(T);
2156 }
2157
2158 case llvm::Triple::x86_64:
2159 switch (os) {
Edward O'Callaghan0a7ef9a2009-10-18 13:33:59 +00002160 case llvm::Triple::AuroraUX:
2161 return new AuroraUXTargetInfo<X86_64TargetInfo>(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002162 case llvm::Triple::Darwin:
2163 return new DarwinX86_64TargetInfo(T);
2164 case llvm::Triple::Linux:
2165 return new LinuxTargetInfo<X86_64TargetInfo>(T);
Chris Lattner1eac0812010-01-09 05:41:14 +00002166 case llvm::Triple::DragonFly:
2167 return new DragonFlyBSDTargetInfo<X86_64TargetInfo>(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002168 case llvm::Triple::NetBSD:
2169 return new NetBSDTargetInfo<X86_64TargetInfo>(T);
2170 case llvm::Triple::OpenBSD:
2171 return new OpenBSDX86_64TargetInfo(T);
2172 case llvm::Triple::FreeBSD:
2173 return new FreeBSDTargetInfo<X86_64TargetInfo>(T);
2174 case llvm::Triple::Solaris:
2175 return new SolarisTargetInfo<X86_64TargetInfo>(T);
Daniel Dunbar8d8e9d62009-09-23 07:31:35 +00002176 case llvm::Triple::MinGW64:
2177 return new MinGWX86_64TargetInfo(T);
2178 case llvm::Triple::Win32: // This is what Triple.h supports now.
2179 return new VisualStudioWindowsX86_64TargetInfo(T);
Daniel Dunbar8ba3de02009-08-18 05:47:58 +00002180 default:
2181 return new X86_64TargetInfo(T);
2182 }
2183 }
Chris Lattner4b009652007-07-25 00:24:17 +00002184}
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002185
2186/// CreateTargetInfo - Return the target info object for the specified target
2187/// triple.
2188TargetInfo *TargetInfo::CreateTargetInfo(Diagnostic &Diags,
Daniel Dunbar4f7cd962009-12-19 03:30:57 +00002189 TargetOptions &Opts) {
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002190 llvm::Triple Triple(Opts.Triple);
2191
2192 // Construct the target
2193 llvm::OwningPtr<TargetInfo> Target(AllocateTarget(Triple.str()));
2194 if (!Target) {
2195 Diags.Report(diag::err_target_unknown_triple) << Triple.str();
2196 return 0;
2197 }
2198
Daniel Dunbar33b40752009-12-18 18:42:37 +00002199 // Set the target CPU if specified.
2200 if (!Opts.CPU.empty() && !Target->setCPU(Opts.CPU)) {
2201 Diags.Report(diag::err_target_unknown_cpu) << Opts.CPU;
2202 return 0;
2203 }
2204
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002205 // Set the target ABI if specified.
2206 if (!Opts.ABI.empty() && !Target->setABI(Opts.ABI)) {
2207 Diags.Report(diag::err_target_unknown_abi) << Opts.ABI;
2208 return 0;
2209 }
2210
2211 // Compute the default target features, we need the target to handle this
2212 // because features may have dependencies on one another.
2213 llvm::StringMap<bool> Features;
2214 Target->getDefaultFeatures(Opts.CPU, Features);
2215
2216 // Apply the user specified deltas.
2217 for (std::vector<std::string>::const_iterator it = Opts.Features.begin(),
2218 ie = Opts.Features.end(); it != ie; ++it) {
2219 const char *Name = it->c_str();
2220
2221 // Apply the feature via the target.
2222 if ((Name[0] != '-' && Name[0] != '+') ||
2223 !Target->setFeatureEnabled(Features, Name + 1, (Name[0] == '+'))) {
2224 Diags.Report(diag::err_target_invalid_feature) << Name;
2225 return 0;
2226 }
2227 }
2228
2229 // Add the features to the compile options.
2230 //
2231 // FIXME: If we are completely confident that we have the right set, we only
2232 // need to pass the minuses.
Daniel Dunbar4f7cd962009-12-19 03:30:57 +00002233 Opts.Features.clear();
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002234 for (llvm::StringMap<bool>::const_iterator it = Features.begin(),
2235 ie = Features.end(); it != ie; ++it)
Daniel Dunbar4f7cd962009-12-19 03:30:57 +00002236 Opts.Features.push_back(std::string(it->second ? "+" : "-") + it->first());
2237 Target->HandleTargetFeatures(Opts.Features);
Daniel Dunbarca3e9912009-11-15 06:48:46 +00002238
2239 return Target.take();
2240}