diff options
author | Saleem Abdulrasool <compnerd@compnerd.org> | 2017-10-06 23:09:55 +0000 |
---|---|---|
committer | Saleem Abdulrasool <compnerd@compnerd.org> | 2017-10-06 23:09:55 +0000 |
commit | 729379a1e19cb82b212bc3a6ba7a12274720bc2a (patch) | |
tree | bec003a8acebe5300df0cef7583108d8b930ed2c /clang/lib | |
parent | d2f225fdef3120443b8f92382de5bacfc2985ba7 (diff) | |
download | bcm5719-llvm-729379a1e19cb82b212bc3a6ba7a12274720bc2a.tar.gz bcm5719-llvm-729379a1e19cb82b212bc3a6ba7a12274720bc2a.zip |
Driver: hoist the `wchar_t` handling to the driver
Move the logic for determining the `wchar_t` type information into the
driver. Rather than passing the single bit of information of
`-fshort-wchar` indicate to the frontend the desired type of `wchar_t`
through a new `-cc1` option of `-fwchar-type` and indicate the
signedness through `-f{,no-}signed-wchar`. This replicates the current
logic which was spread throughout Basic into the
`RenderCharacterOptions`.
Most of the changes to the tests are to ensure that the frontend uses
the correct type. Add a new test set under `test/Driver/wchar_t.c` to
ensure that we calculate the proper types for the various cases.
llvm-svn: 315126
Diffstat (limited to 'clang/lib')
-rw-r--r-- | clang/lib/Basic/TargetInfo.cpp | 12 | ||||
-rw-r--r-- | clang/lib/Basic/Targets/AArch64.cpp | 13 | ||||
-rw-r--r-- | clang/lib/Basic/Targets/ARM.cpp | 23 | ||||
-rw-r--r-- | clang/lib/Basic/Targets/AVR.h | 1 | ||||
-rw-r--r-- | clang/lib/Basic/Targets/OSTargets.h | 7 | ||||
-rw-r--r-- | clang/lib/Basic/Targets/X86.h | 6 | ||||
-rw-r--r-- | clang/lib/Driver/ToolChains/Clang.cpp | 49 | ||||
-rw-r--r-- | clang/lib/Frontend/CompilerInstance.cpp | 1 | ||||
-rw-r--r-- | clang/lib/Frontend/CompilerInvocation.cpp | 11 |
9 files changed, 71 insertions, 52 deletions
diff --git a/clang/lib/Basic/TargetInfo.cpp b/clang/lib/Basic/TargetInfo.cpp index de26a67eac3..9b736d113d6 100644 --- a/clang/lib/Basic/TargetInfo.cpp +++ b/clang/lib/Basic/TargetInfo.cpp @@ -19,6 +19,7 @@ #include "llvm/ADT/APFloat.h" #include "llvm/ADT/STLExtras.h" #include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/TargetParser.h" #include <cstdlib> using namespace clang; @@ -290,8 +291,15 @@ bool TargetInfo::isTypeSigned(IntType T) { void TargetInfo::adjust(LangOptions &Opts) { if (Opts.NoBitFieldTypeAlign) UseBitFieldTypeAlignment = false; - if (Opts.ShortWChar) - WCharType = UnsignedShort; + + switch (Opts.WCharSize) { + default: llvm_unreachable("invalid wchar_t width"); + case 0: break; + case 1: WCharType = Opts.WCharIsSigned ? SignedChar : UnsignedChar; break; + case 2: WCharType = Opts.WCharIsSigned ? SignedShort : UnsignedShort; break; + case 4: WCharType = Opts.WCharIsSigned ? SignedInt : UnsignedInt; break; + } + if (Opts.AlignDouble) { DoubleAlign = LongLongAlign = 64; LongDoubleAlign = 64; diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp index 2a85c89cbb3..e915d362b90 100644 --- a/clang/lib/Basic/Targets/AArch64.cpp +++ b/clang/lib/Basic/Targets/AArch64.cpp @@ -15,6 +15,7 @@ #include "clang/Basic/TargetBuiltins.h" #include "clang/Basic/TargetInfo.h" #include "llvm/ADT/ArrayRef.h" +#include "llvm/ADT/StringExtras.h" using namespace clang; using namespace clang::targets; @@ -34,18 +35,19 @@ AArch64TargetInfo::AArch64TargetInfo(const llvm::Triple &Triple, : TargetInfo(Triple), ABI("aapcs") { if (getTriple().getOS() == llvm::Triple::NetBSD || getTriple().getOS() == llvm::Triple::OpenBSD) { - WCharType = SignedInt; - // NetBSD apparently prefers consistency across ARM targets to // consistency across 64-bit targets. Int64Type = SignedLongLong; IntMaxType = SignedLongLong; } else { - WCharType = UnsignedInt; + if (!getTriple().isOSDarwin()) + WCharType = UnsignedInt; + Int64Type = SignedLong; IntMaxType = SignedLong; } + LongWidth = LongAlign = PointerWidth = PointerAlign = 64; MaxVectorAlign = 128; MaxAtomicInlineWidth = 128; @@ -154,7 +156,8 @@ void AArch64TargetInfo::getTargetDefines(const LangOptions &Opts, if (Opts.UnsafeFPMath) Builder.defineMacro("__ARM_FP_FAST", "1"); - Builder.defineMacro("__ARM_SIZEOF_WCHAR_T", Opts.ShortWChar ? "2" : "4"); + Builder.defineMacro("__ARM_SIZEOF_WCHAR_T", + llvm::utostr(Opts.WCharSize ? Opts.WCharSize : 4)); Builder.defineMacro("__ARM_SIZEOF_MINIMAL_ENUM", Opts.ShortEnums ? "1" : "4"); @@ -420,7 +423,6 @@ WindowsARM64TargetInfo::WindowsARM64TargetInfo(const llvm::Triple &Triple, // This is an LLP64 platform. // int:4, long:4, long long:8, long double:8. - WCharType = UnsignedShort; IntWidth = IntAlign = 32; LongWidth = LongAlign = 32; DoubleAlign = LongLongAlign = 64; @@ -502,7 +504,6 @@ DarwinAArch64TargetInfo::DarwinAArch64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : DarwinTargetInfo<AArch64leTargetInfo>(Triple, Opts) { Int64Type = SignedLongLong; - WCharType = SignedInt; UseSignedCharForObjCBool = false; LongDoubleWidth = LongDoubleAlign = SuitableAlign = 64; diff --git a/clang/lib/Basic/Targets/ARM.cpp b/clang/lib/Basic/Targets/ARM.cpp index b3e8007bcb1..92685fcd21c 100644 --- a/clang/lib/Basic/Targets/ARM.cpp +++ b/clang/lib/Basic/Targets/ARM.cpp @@ -36,20 +36,10 @@ void ARMTargetInfo::setABIAAPCS() { else SizeType = UnsignedInt; - switch (T.getOS()) { - case llvm::Triple::NetBSD: - case llvm::Triple::OpenBSD: - WCharType = SignedInt; - break; - case llvm::Triple::Win32: - WCharType = UnsignedShort; - break; - case llvm::Triple::Linux: - default: - // AAPCS 7.1.1, ARM-Linux ABI 2.4: type of wchar_t is unsigned int. + bool IsNetBSD = T.getOS() == llvm::Triple::NetBSD; + bool IsOpenBSD = T.getOS() == llvm::Triple::OpenBSD; + if (!T.isOSWindows() && !IsNetBSD && !IsOpenBSD) WCharType = UnsignedInt; - break; - } UseBitFieldTypeAlignment = true; @@ -99,7 +89,6 @@ void ARMTargetInfo::setABIAPCS(bool IsAAPCS16) { else SizeType = UnsignedLong; - // Revert to using SignedInt on apcs-gnu to comply with existing behaviour. WCharType = SignedInt; // Do not respect the alignment of bit-field types when laying out @@ -689,7 +678,8 @@ void ARMTargetInfo::getTargetDefines(const LangOptions &Opts, "0x" + llvm::utohexstr(HW_FP & ~HW_FP_DP)); } - Builder.defineMacro("__ARM_SIZEOF_WCHAR_T", Opts.ShortWChar ? "2" : "4"); + Builder.defineMacro("__ARM_SIZEOF_WCHAR_T", + llvm::utostr(Opts.WCharSize ? Opts.WCharSize : 4)); Builder.defineMacro("__ARM_SIZEOF_MINIMAL_ENUM", Opts.ShortEnums ? "1" : "4"); @@ -932,7 +922,6 @@ void ARMbeTargetInfo::getTargetDefines(const LangOptions &Opts, WindowsARMTargetInfo::WindowsARMTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : WindowsTargetInfo<ARMleTargetInfo>(Triple, Opts), Triple(Triple) { - WCharType = UnsignedShort; SizeType = UnsignedInt; } @@ -1023,8 +1012,8 @@ void MinGWARMTargetInfo::getTargetDefines(const LangOptions &Opts, CygwinARMTargetInfo::CygwinARMTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : ARMleTargetInfo(Triple, Opts) { + this->WCharType = TargetInfo::UnsignedShort; TLSSupported = false; - WCharType = UnsignedShort; DoubleAlign = LongLongAlign = 64; resetDataLayout("e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64"); } diff --git a/clang/lib/Basic/Targets/AVR.h b/clang/lib/Basic/Targets/AVR.h index 679e639e745..3dfb84f7566 100644 --- a/clang/lib/Basic/Targets/AVR.h +++ b/clang/lib/Basic/Targets/AVR.h @@ -52,7 +52,6 @@ public: PtrDiffType = SignedInt; IntPtrType = SignedInt; Char16Type = UnsignedInt; - WCharType = SignedInt; WIntType = SignedInt; Char32Type = UnsignedLong; SigAtomicType = SignedChar; diff --git a/clang/lib/Basic/Targets/OSTargets.h b/clang/lib/Basic/Targets/OSTargets.h index ca84a875de1..c775fe32ee5 100644 --- a/clang/lib/Basic/Targets/OSTargets.h +++ b/clang/lib/Basic/Targets/OSTargets.h @@ -477,7 +477,7 @@ protected: public: PS4OSTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : OSTargetInfo<Target>(Triple, Opts) { - this->WCharType = this->UnsignedShort; + this->WCharType = TargetInfo::UnsignedShort; // On PS4, TLS variable cannot be aligned to more than 32 bytes (256 bits). this->MaxTLSAlign = 256; @@ -561,7 +561,6 @@ protected: public: SolarisTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : OSTargetInfo<Target>(Triple, Opts) { - this->WCharType = this->SignedInt; // FIXME: WIntType should be SignedLong } }; @@ -628,7 +627,9 @@ protected: public: WindowsTargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) - : OSTargetInfo<Target>(Triple, Opts) {} + : OSTargetInfo<Target>(Triple, Opts) { + this->WCharType = TargetInfo::UnsignedShort; + } }; template <typename Target> diff --git a/clang/lib/Basic/Targets/X86.h b/clang/lib/Basic/Targets/X86.h index 24d535a7333..38fb0c66f65 100644 --- a/clang/lib/Basic/Targets/X86.h +++ b/clang/lib/Basic/Targets/X86.h @@ -639,7 +639,6 @@ class LLVM_LIBRARY_VISIBILITY WindowsX86_32TargetInfo public: WindowsX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : WindowsTargetInfo<X86_32TargetInfo>(Triple, Opts) { - WCharType = UnsignedShort; DoubleAlign = LongLongAlign = 64; bool IsWinCOFF = getTriple().isOSWindows() && getTriple().isOSBinFormatCOFF(); @@ -700,7 +699,7 @@ class LLVM_LIBRARY_VISIBILITY CygwinX86_32TargetInfo : public X86_32TargetInfo { public: CygwinX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : X86_32TargetInfo(Triple, Opts) { - WCharType = UnsignedShort; + this->WCharType = TargetInfo::UnsignedShort; DoubleAlign = LongLongAlign = 64; resetDataLayout("e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32"); } @@ -886,7 +885,6 @@ class LLVM_LIBRARY_VISIBILITY WindowsX86_64TargetInfo public: WindowsX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : WindowsTargetInfo<X86_64TargetInfo>(Triple, Opts) { - WCharType = UnsignedShort; LongWidth = LongAlign = 32; DoubleAlign = LongLongAlign = 64; IntMaxType = SignedLongLong; @@ -979,8 +977,8 @@ class LLVM_LIBRARY_VISIBILITY CygwinX86_64TargetInfo : public X86_64TargetInfo { public: CygwinX86_64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : X86_64TargetInfo(Triple, Opts) { + this->WCharType = TargetInfo::UnsignedShort; TLSSupported = false; - WCharType = UnsignedShort; } void getTargetDefines(const LangOptions &Opts, diff --git a/clang/lib/Driver/ToolChains/Clang.cpp b/clang/lib/Driver/ToolChains/Clang.cpp index 21937ef143d..6c285dec653 100644 --- a/clang/lib/Driver/ToolChains/Clang.cpp +++ b/clang/lib/Driver/ToolChains/Clang.cpp @@ -2601,6 +2601,33 @@ static void RenderModulesOptions(Compilation &C, const Driver &D, Args.AddLastArg(CmdArgs, options::OPT_fmodules_disable_diagnostic_validation); } +static void RenderCharacterOptions(const ArgList &Args, const llvm::Triple &T, + ArgStringList &CmdArgs) { + // -fsigned-char is default. + if (const Arg *A = Args.getLastArg(options::OPT_fsigned_char, + options::OPT_fno_signed_char, + options::OPT_funsigned_char, + options::OPT_fno_unsigned_char)) { + if (A->getOption().matches(options::OPT_funsigned_char) || + A->getOption().matches(options::OPT_fno_signed_char)) { + CmdArgs.push_back("-fno-signed-char"); + } + } else if (!isSignedCharDefault(T)) { + CmdArgs.push_back("-fno-signed-char"); + } + + if (const Arg *A = Args.getLastArg(options::OPT_fshort_wchar, + options::OPT_fno_short_wchar)) { + if (A->getOption().matches(options::OPT_fshort_wchar)) { + CmdArgs.push_back("-fwchar-type=short"); + CmdArgs.push_back("-fno-signed-wchar"); + } else { + CmdArgs.push_back("-fwchar-type=int"); + CmdArgs.push_back("-fsigned-wchar"); + } + } +} + static void RenderObjCOptions(const ToolChain &TC, const Driver &D, const llvm::Triple &T, const ArgList &Args, ObjCRuntime &Runtime, bool InferCovariantReturns, @@ -2991,6 +3018,9 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, Inputs.size() == 1) && "Unable to handle multiple inputs."); + const llvm::Triple *AuxTriple = + IsCuda ? getToolChain().getAuxTriple() : nullptr; + bool IsWindowsGNU = RawTriple.isWindowsGNUEnvironment(); bool IsWindowsCygnus = RawTriple.isWindowsCygwinEnvironment(); bool IsWindowsMSVC = RawTriple.isWindowsMSVCEnvironment(); @@ -3000,7 +3030,6 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, // mode (i.e., getToolchain().getTriple() is NVPTX, not Windows), we need to // pass Windows-specific flags to cc1. if (IsCuda) { - const llvm::Triple *AuxTriple = getToolChain().getAuxTriple(); IsWindowsMSVC |= AuxTriple && AuxTriple->isWindowsMSVCEnvironment(); IsWindowsGNU |= AuxTriple && AuxTriple->isWindowsGNUEnvironment(); IsWindowsCygnus |= AuxTriple && AuxTriple->isWindowsCygwinEnvironment(); @@ -4003,17 +4032,7 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, getToolChain().getArch() == llvm::Triple::hexagon)) CmdArgs.push_back("-fshort-enums"); - // -fsigned-char is default. - if (Arg *A = Args.getLastArg( - options::OPT_fsigned_char, options::OPT_fno_signed_char, - options::OPT_funsigned_char, options::OPT_fno_unsigned_char)) { - if (A->getOption().matches(options::OPT_funsigned_char) || - A->getOption().matches(options::OPT_fno_signed_char)) { - CmdArgs.push_back("-fno-signed-char"); - } - } else if (!isSignedCharDefault(RawTriple)) { - CmdArgs.push_back("-fno-signed-char"); - } + RenderCharacterOptions(Args, AuxTriple ? *AuxTriple : RawTriple, CmdArgs); // -fuse-cxa-atexit is default. if (!Args.hasFlag( @@ -4182,12 +4201,6 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, options::OPT_mno_constant_cfstrings)) CmdArgs.push_back("-fno-constant-cfstrings"); - // -fshort-wchar default varies depending on platform; only - // pass if specified. - if (Arg *A = Args.getLastArg(options::OPT_fshort_wchar, - options::OPT_fno_short_wchar)) - A->render(Args, CmdArgs); - // -fno-pascal-strings is default, only pass non-default. if (Args.hasFlag(options::OPT_fpascal_strings, options::OPT_fno_pascal_strings, false)) diff --git a/clang/lib/Frontend/CompilerInstance.cpp b/clang/lib/Frontend/CompilerInstance.cpp index d97ebb0a0e4..32f1232bbe2 100644 --- a/clang/lib/Frontend/CompilerInstance.cpp +++ b/clang/lib/Frontend/CompilerInstance.cpp @@ -386,6 +386,7 @@ void CompilerInstance::createPreprocessor(TranslationUnitKind TUKind) { Invocation->getPreprocessorOptsPtr(), getDiagnostics(), getLangOpts(), getSourceManager(), getPCMCache(), *HeaderInfo, *this, PTHMgr, /*OwnsHeaderSearch=*/true, TUKind); + getTarget().adjust(getLangOpts()); PP->Initialize(getTarget(), getAuxTarget()); // Note that this is different then passing PTHMgr to Preprocessor's ctor. diff --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp index 37ba39dfd07..7114e654dab 100644 --- a/clang/lib/Frontend/CompilerInvocation.cpp +++ b/clang/lib/Frontend/CompilerInvocation.cpp @@ -2154,7 +2154,16 @@ static void ParseLangArgs(LangOptions &Opts, ArgList &Args, InputKind IK, Opts.ImplicitModules = !Args.hasArg(OPT_fno_implicit_modules); Opts.CharIsSigned = Opts.OpenCL || !Args.hasArg(OPT_fno_signed_char); Opts.WChar = Opts.CPlusPlus && !Args.hasArg(OPT_fno_wchar); - Opts.ShortWChar = Args.hasFlag(OPT_fshort_wchar, OPT_fno_short_wchar, false); + if (const Arg *A = Args.getLastArg(OPT_fwchar_type_EQ)) { + Opts.WCharSize = llvm::StringSwitch<unsigned>(A->getValue()) + .Case("char", 1) + .Case("short", 2) + .Case("int", 4) + .Default(0); + if (Opts.WCharSize == 0) + Diags.Report(diag::err_fe_invalid_wchar_type) << A->getValue(); + } + Opts.WCharIsSigned = Args.hasFlag(OPT_fsigned_wchar, OPT_fno_signed_wchar, true); Opts.ShortEnums = Args.hasArg(OPT_fshort_enums); Opts.Freestanding = Args.hasArg(OPT_ffreestanding); Opts.NoBuiltin = Args.hasArg(OPT_fno_builtin) || Opts.Freestanding; |