Index: include/clang/Basic/BuiltinsHSAIL.def =================================================================== --- /dev/null +++ include/clang/Basic/BuiltinsHSAIL.def @@ -0,0 +1,20 @@ +//==- BuiltinsHSAIL.def - HSAIL Builtin function database ----------*- C++ -*-==// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file defines the HSAIL-specific builtin function database. Users of this +// file must define the BUILTIN macro to make use of this information. +// +//===----------------------------------------------------------------------===// + +// The format of this database matches clang/Basic/Builtins.def. + +BUILTIN(__builtin_hsail_fsqrt, "dIbIid", "nc") +BUILTIN(__builtin_hsail_fsqrtf, "fIbIif", "nc") + +#undef BUILTIN Index: include/clang/Basic/TargetBuiltins.h =================================================================== --- include/clang/Basic/TargetBuiltins.h +++ include/clang/Basic/TargetBuiltins.h @@ -146,6 +146,16 @@ }; } + /// \brief HSAIL builtins + namespace HSAIL { + enum { + LastTIBuiltin = clang::Builtin::FirstTSBuiltin - 1, + #define BUILTIN(ID, TYPE, ATTRS) BI##ID, + #include "clang/Basic/BuiltinsHSAIL.def" + LastTSBuiltin + }; + } + /// \brief MIPS builtins namespace Mips { enum { Index: include/clang/module.modulemap =================================================================== --- include/clang/module.modulemap +++ include/clang/module.modulemap @@ -28,6 +28,7 @@ textual header "Basic/BuiltinsARM.def" textual header "Basic/Builtins.def" textual header "Basic/BuiltinsHexagon.def" + textual header "Basic/BuiltinsHSAIL.def" textual header "Basic/BuiltinsLe64.def" textual header "Basic/BuiltinsMips.def" textual header "Basic/BuiltinsNEON.def" Index: lib/Basic/Targets.cpp =================================================================== --- lib/Basic/Targets.cpp +++ lib/Basic/Targets.cpp @@ -5383,6 +5383,130 @@ #include "clang/Basic/BuiltinsHexagon.def" }; +static const unsigned HSAILAddrSpaceMap[] = { + 1, // opencl_global + 3, // opencl_local + 2, // opencl_constant + 4, // opencl_generic + 1, // cuda_device + 2, // cuda_constant + 3 // cuda_shared +}; + +// If you edit the description strings, make sure you update +// getPointerWidthV(). + +static const char *DescriptionStringHSAIL = + "e-p:32:32-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128" + "-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64"; + +static const char *DescriptionStringHSAIL64 = + "e-p:32:32-p1:64:64-p2:64:64-p3:32:32-p4:64:64-p5:32:32" + "-p6:32:32-p7:64:64-p8:32:32-p9:64:64" + "-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128" + "-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64"; + +class HSAILTargetInfo : public TargetInfo { + static const Builtin::Info BuiltinInfo[]; + bool IsLargeModel; + bool FullProfile; + + enum DeviceKind { + HSAIL_NONE, + HSAIL_KAVERI + } Device; + +public: + HSAILTargetInfo(const llvm::Triple &Triple) + : TargetInfo(Triple), + IsLargeModel(false), + FullProfile(true) { + + if (Triple.getArch() == llvm::Triple::hsail) { + DescriptionString = DescriptionStringHSAIL; + } else { + DescriptionString = DescriptionStringHSAIL64; + IsLargeModel = true; + } + + AddrSpaceMap = &HSAILAddrSpaceMap; + UseAddrSpaceMapMangling = true; + } + + uint64_t getPointerWidthV(unsigned AddrSpace) const override { + switch (AddrSpace) { + default: + return 64; + case 0: + case 3: + case 5: + return 32; + } + } + + const char *getClobbers() const override { + return ""; + } + + void getGCCRegNames(const char *const *&Names, + unsigned &NumNames) const override { + Names = nullptr; + NumNames = 0; + } + + void getGCCRegAliases(const GCCRegAlias *&Aliases, + unsigned &NumAliases) const override { + Aliases = nullptr; + NumAliases = 0; + } + + bool validateAsmConstraint(const char *&Name, + TargetInfo::ConstraintInfo &info) const override { + return true; + } + + void getTargetBuiltins(const Builtin::Info *&Records, + unsigned &NumRecords) const override { + Records = BuiltinInfo; + NumRecords = clang::HSAIL::LastTSBuiltin - Builtin::FirstTSBuiltin; + } + + void getTargetDefines(const LangOptions &Opts, + MacroBuilder &Builder) const override { + if (IsLargeModel) + Builder.defineMacro("__HSAIL64__"); + else + Builder.defineMacro("__HSAIL__"); + + if (FullProfile && Opts.OpenCL) { + Builder.defineMacro("cl_khr_fp64"); + } + } + + BuiltinVaListKind getBuiltinVaListKind() const override { + return TargetInfo::CharPtrBuiltinVaList; + } + + bool setCPU(const std::string &Name) override { + llvm_unreachable("meatspin"); + + Device = llvm::StringSwitch(Name) + .Case("kaveri", HSAIL_KAVERI) + .Default(HSAIL_NONE); + + if (Device == HSAIL_NONE) + return false; + + return true; + } +}; + +const Builtin::Info HSAILTargetInfo::BuiltinInfo[] = { +#define BUILTIN(ID, TYPE, ATTRS) \ + { #ID, TYPE, ATTRS, 0, ALL_LANGUAGES }, +#include "clang/Basic/BuiltinsHSAIL.def" +}; + // Shared base class for SPARC v8 (32-bit) and SPARC v9 (64-bit). class SparcTargetInfo : public TargetInfo { static const TargetInfo::GCCRegAlias GCCRegAliases[]; @@ -7090,6 +7214,10 @@ case llvm::Triple::r600: return new AMDGPUTargetInfo(Triple); + case llvm::Triple::hsail: + case llvm::Triple::hsail64: + return new HSAILTargetInfo(Triple); + case llvm::Triple::sparc: switch (os) { case llvm::Triple::Linux: Index: lib/CodeGen/CGBuiltin.cpp =================================================================== --- lib/CodeGen/CGBuiltin.cpp +++ lib/CodeGen/CGBuiltin.cpp @@ -1878,6 +1878,9 @@ case llvm::Triple::r600: case llvm::Triple::amdgcn: return EmitAMDGPUBuiltinExpr(BuiltinID, E); + case llvm::Triple::hsail: + case llvm::Triple::hsail64: + return EmitHSAILBuiltinExpr(BuiltinID, E); case llvm::Triple::systemz: return EmitSystemZBuiltinExpr(BuiltinID, E); default: @@ -6617,6 +6620,14 @@ } } +Value *CodeGenFunction::EmitHSAILBuiltinExpr(unsigned BuiltinID, + const CallExpr *E) { + switch (BuiltinID) { + default: + return nullptr; + } +} + /// Handle a SystemZ function in which the final argument is a pointer /// to an int that receives the post-instruction CC value. At the LLVM level /// this is represented as a function that returns a {result, cc} pair. Index: lib/CodeGen/CodeGenFunction.h =================================================================== --- lib/CodeGen/CodeGenFunction.h +++ lib/CodeGen/CodeGenFunction.h @@ -2585,6 +2585,7 @@ llvm::Value *EmitX86BuiltinExpr(unsigned BuiltinID, const CallExpr *E); llvm::Value *EmitPPCBuiltinExpr(unsigned BuiltinID, const CallExpr *E); llvm::Value *EmitAMDGPUBuiltinExpr(unsigned BuiltinID, const CallExpr *E); + llvm::Value *EmitHSAILBuiltinExpr(unsigned BuiltinID, const CallExpr *E); llvm::Value *EmitSystemZBuiltinExpr(unsigned BuiltinID, const CallExpr *E); llvm::Value *EmitObjCProtocolExpr(const ObjCProtocolExpr *E); Index: lib/Driver/Tools.cpp =================================================================== --- lib/Driver/Tools.cpp +++ lib/Driver/Tools.cpp @@ -1334,6 +1334,13 @@ return ""; } +static std::string getHSAILTargetDevice(const ArgList &Args) { + if (Arg *A = Args.getLastArg(options::OPT_mcpu_EQ)) { + return A->getValue(); + } + return ""; +} + void Clang::AddSparcTargetArgs(const ArgList &Args, ArgStringList &CmdArgs) const { const Driver &D = getToolChain().getDriver(); @@ -1508,6 +1515,10 @@ case llvm::Triple::r600: case llvm::Triple::amdgcn: return getR600TargetGPU(Args); + + case llvm::Triple::hsail: + case llvm::Triple::hsail64: + return getHSAILTargetDevice(Args); } } Index: test/CodeGen/target-data.c =================================================================== --- test/CodeGen/target-data.c +++ test/CodeGen/target-data.c @@ -182,3 +182,11 @@ // RUN: %clang_cc1 -triple bpfeb -o - -emit-llvm %s | \ // RUN: FileCheck %s -check-prefix=BPFEB // BPFEB: target datalayout = "E-m:e-p:64:64-i64:64-n32:64-S128" + +// RUN: %clang_cc1 -triple hsail-unknown-unknown -o - -emit-llvm %s | \ +// RUN: FileCheck %s -check-prefix=HSAIL32 +// HSAIL32: target datalayout = "e-p:32:32-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64" + +// RUN: %clang_cc1 -triple hsail64-unknown-unknown -o - -emit-llvm %s | \ +// RUN: FileCheck %s -check-prefix=HSAIL64 +// HSAIL64: target datalayout = "e-p:32:32-p1:64:64-p2:64:64-p3:32:32-p4:64:64-p5:32:32-p24:64:64-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64" Index: test/Driver/hsail-mcpu.cl =================================================================== --- /dev/null +++ test/Driver/hsail-mcpu.cl @@ -0,0 +1,7 @@ +// Check that -mcpu works for all supported GPUs + +// RUN: %clang -### -target hsail -x cl -S -emit-llvm < %s +// RUN: %clang -### -target hsail -x cl -S -emit-llvm -mcpu=kaveri %s -o - 2>&1 | FileCheck -check-prefix=KAVERI %s +// RUN: %clang -### -target hsail64 -x cl -S -emit-llvm -mcpu=kaveri %s -o - 2>&1 | FileCheck -check-prefix=KAVERI %s + +// KAVERI: "-target-cpu" "kaveri" Index: test/Preprocessor/init.c =================================================================== --- test/Preprocessor/init.c +++ test/Preprocessor/init.c @@ -6606,6 +6606,10 @@ // RUN: %clang_cc1 -x cl -E -dM -ffreestanding -triple=amdgcn < /dev/null | FileCheck -check-prefix AMDGCN %s // AMDGCN:#define cl_khr_fp64 1 +// RUN: %clang_cc1 -x cl -E -dM -ffreestanding -triple=hsail < /dev/null | FileCheck -check-prefix=HSAIL %s +// RUN: %clang_cc1 -x cl -E -dM -ffreestanding -triple=hsail64 < /dev/null | FileCheck -check-prefix=HSAIL %s +// HSAIL:#define cl_khr_fp64 1 + // RUN: %clang_cc1 -E -dM -ffreestanding -triple=s390x-none-none -fno-signed-char < /dev/null | FileCheck -check-prefix S390X %s // // S390X:#define __BIGGEST_ALIGNMENT__ 8