SjoerdMeijer updated this revision to Diff 138722.
SjoerdMeijer added a comment.
Addressed comments: simplified the logic in GetNeonType.
https://reviews.llvm.org/D44561
Files:
include/clang/Basic/TargetInfo.h
lib/Basic/TargetInfo.cpp
lib/Basic/Targets/AArch64.cpp
lib/Basic/Targets/ARM.cpp
lib/Basic/Targets/ARM.h
lib/CodeGen/CGBuiltin.cpp
Index: lib/CodeGen/CGBuiltin.cpp
===================================================================
--- lib/CodeGen/CGBuiltin.cpp
+++ lib/CodeGen/CGBuiltin.cpp
@@ -3442,6 +3442,7 @@
static llvm::VectorType *GetNeonType(CodeGenFunction *CGF,
NeonTypeFlags TypeFlags,
llvm::Triple::ArchType Arch,
+ bool HasFloat16=true,
bool V1Ty=false) {
int IsQuad = TypeFlags.isQuad();
switch (TypeFlags.getEltType()) {
@@ -3452,9 +3453,7 @@
case NeonTypeFlags::Poly16:
return llvm::VectorType::get(CGF->Int16Ty, V1Ty ? 1 : (4 << IsQuad));
case NeonTypeFlags::Float16:
- // FIXME: Only AArch64 backend can so far properly handle half types.
- // Remove else part once ARM backend support for half is complete.
- if (Arch == llvm::Triple::aarch64)
+ if (HasFloat16)
return llvm::VectorType::get(CGF->HalfTy, V1Ty ? 1 : (4 << IsQuad));
else
return llvm::VectorType::get(CGF->Int16Ty, V1Ty ? 1 : (4 << IsQuad));
@@ -4338,8 +4337,9 @@
NeonTypeFlags Type(NeonTypeConst.getZExtValue());
bool Usgn = Type.isUnsigned();
bool Quad = Type.isQuad();
+ const bool HasFloat16 = getTarget().hasFloat16Type();
- llvm::VectorType *VTy = GetNeonType(this, Type, Arch);
+ llvm::VectorType *VTy = GetNeonType(this, Type, Arch, HasFloat16);
llvm::Type *Ty = VTy;
if (!Ty)
return nullptr;
@@ -4413,13 +4413,15 @@
case NEON::BI__builtin_neon_vcvt_f32_v:
case NEON::BI__builtin_neon_vcvtq_f32_v:
Ops[0] = Builder.CreateBitCast(Ops[0], Ty);
- Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float32, false, Quad), Arch);
+ Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float32, false, Quad),
+ Arch, HasFloat16);
return Usgn ? Builder.CreateUIToFP(Ops[0], Ty, "vcvt")
: Builder.CreateSIToFP(Ops[0], Ty, "vcvt");
case NEON::BI__builtin_neon_vcvt_f16_v:
case NEON::BI__builtin_neon_vcvtq_f16_v:
Ops[0] = Builder.CreateBitCast(Ops[0], Ty);
- Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float16, false, Quad), Arch);
+ Ty = GetNeonType(this, NeonTypeFlags(NeonTypeFlags::Float16, false, Quad), Arch,
+ HasFloat16);
return Usgn ? Builder.CreateUIToFP(Ops[0], Ty, "vcvt")
: Builder.CreateSIToFP(Ops[0], Ty, "vcvt");
case NEON::BI__builtin_neon_vcvt_n_f16_v:
@@ -5528,7 +5530,8 @@
bool usgn = Type.isUnsigned();
bool rightShift = false;
- llvm::VectorType *VTy = GetNeonType(this, Type, Arch);
+ llvm::VectorType *VTy = GetNeonType(this, Type, Arch,
+ getTarget().hasFloat16Type());
llvm::Type *Ty = VTy;
if (!Ty)
return nullptr;
Index: lib/Basic/Targets/ARM.h
===================================================================
--- lib/Basic/Targets/ARM.h
+++ lib/Basic/Targets/ARM.h
@@ -69,7 +69,6 @@
unsigned Crypto : 1;
unsigned DSP : 1;
unsigned Unaligned : 1;
- unsigned HasFullFP16 : 1;
enum {
LDREX_B = (1 << 0), /// byte (8-bit)
Index: lib/Basic/Targets/ARM.cpp
===================================================================
--- lib/Basic/Targets/ARM.cpp
+++ lib/Basic/Targets/ARM.cpp
@@ -379,7 +379,6 @@
Unaligned = 1;
SoftFloat = SoftFloatABI = false;
HWDiv = 0;
- HasFullFP16 = 0;
// This does not diagnose illegal cases like having both
// "+vfpv2" and "+vfpv3" or having "+neon" and "+fp-only-sp".
@@ -421,7 +420,7 @@
} else if (Feature == "+fp16") {
HW_FP |= HW_FP_HP;
} else if (Feature == "+fullfp16") {
- HasFullFP16 = 1;
+ HasFloat16 = true;
}
}
HW_FP &= ~HW_FP_remove;
@@ -714,11 +713,11 @@
Builder.defineMacro("__ARM_FP_FAST", "1");
// Armv8.2-A FP16 vector intrinsic
- if ((FPU & NeonFPU) && HasFullFP16)
+ if ((FPU & NeonFPU) && HasFloat16)
Builder.defineMacro("__ARM_FEATURE_FP16_VECTOR_ARITHMETIC", "1");
// Armv8.2-A FP16 scalar intrinsics
- if (HasFullFP16)
+ if (HasFloat16)
Builder.defineMacro("__ARM_FEATURE_FP16_SCALAR_ARITHMETIC", "1");
Index: lib/Basic/Targets/AArch64.cpp
===================================================================
--- lib/Basic/Targets/AArch64.cpp
+++ lib/Basic/Targets/AArch64.cpp
@@ -49,6 +49,9 @@
IntMaxType = SignedLong;
}
+ // AArch64 has H-registers and at least some level instruction half-precision
+ // support (as opposed to ARM, where it can be completely unsupported).
+ HasFloat16 = true;
LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
MaxVectorAlign = 128;
Index: lib/Basic/TargetInfo.cpp
===================================================================
--- lib/Basic/TargetInfo.cpp
+++ lib/Basic/TargetInfo.cpp
@@ -32,6 +32,7 @@
TLSSupported = true;
VLASupported = true;
NoAsmVariants = false;
+ HasFloat16 = false;
HasFloat128 = false;
PointerWidth = PointerAlign = 32;
BoolWidth = BoolAlign = 8;
Index: include/clang/Basic/TargetInfo.h
===================================================================
--- include/clang/Basic/TargetInfo.h
+++ include/clang/Basic/TargetInfo.h
@@ -61,6 +61,7 @@
bool TLSSupported;
bool VLASupported;
bool NoAsmVariants; // True if {|} are normal characters.
+ bool HasFloat16; // True if the target has native half-precision support.
bool HasFloat128;
unsigned char PointerWidth, PointerAlign;
unsigned char BoolWidth, BoolAlign;
@@ -361,6 +362,9 @@
return (getPointerWidth(0) >= 64) || getTargetOpts().ForceEnableInt128;
} // FIXME
+ /// \brief Determine whether _Float16 is supported on this target.
+ virtual bool hasFloat16Type() const { return HasFloat16; }
+
/// \brief Determine whether the __float128 type is supported on this target.
virtual bool hasFloat128Type() const { return HasFloat128; }
_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits