【问题标题】:How to enable __fp16 type on gcc for x86_64如何在 gcc 上为 x86_64 启用 __fp16 类型
【发布时间】:2017-12-19 21:20:11
【问题描述】:

__fp16 浮点数据类型是众所周知的 C 标准扩展,尤其是在 ARM 处理器上使用。我想在我的 x86_64 处理器上运行它们的 IEEE 版本。虽然我知道他们通常没有这些,但我可以使用“无符号短”存储(它们具有相同的对齐要求和存储空间)和(硬件)浮点运算来模拟它们。

有没有办法在 gcc 中请求?

我认为舍入可能有点“不正确”,但这对我来说没问题。

如果这也适用于 C++,那将是理想的。

【问题讨论】:

  • 我认为 x86 目标没有此功能。如果是这样,它会非常慢,因为它都必须在软件仿真中运行,而不是使用 FP 硬件。你为什么要这样做?
  • @CodyGray:半精度浮点数原生支持最近的(Intel 自 Ivy Bridge,AMD 自 Piledriver)x86 CPU(仅作为存储格式,需要转换为单精度才能进行实际计算)。
  • 啊,是的,他们是,@Fanael。感谢您指出了这一点。我错过了他们的介绍。因此,您将使用_mm256_cvtph_ps 作为“加载”(将半浮点转换为浮点),将_mm256_cvtps_ph 作为“存储”(将浮点转换为半浮点)。事实证明,这相当快,并且在内存受限的情况下实际上很有用。 Nonyme,在平台抽象库之类的东西中使用内在函数来实现这一点是否可以接受?还是您对让编译器隐式生成此代码一无所知?
  • 目标是在 x86_64 服务器场上运行为 ARM 设计的庞大代码库。如果“平台抽象库”不需要对代码进行任何修改,那就可以了。但我怀疑这是可行的。注意:我设法通过欺骗语义解析器来定义 __fp16 并将其作为 x86_64 上的函数参数/返回值来欺骗 Clang。然后它设法使用上述内在函数进行转换并使用浮点数进行计算。
  • 我编辑了 clang 源代码以在 X86 目标上添加 __fp16 内置类型(默认情况下它仅在 ARM 上启用)。然后编译器的其余部分自行处理。

标签: c++ c gcc x86 half-precision-float


【解决方案1】:

我没有在 gcc 中找到这样做的方法(从 gcc 8.2.0 开始)。

至于 clang,在 6.0.0 中,以下选项显示了一些成功:

clang -cc1 -fnative-half-type -fallow-half-arguments-and-returns

选项-fnative-half-type 启用__fp16 类型(而不是将它们提升为浮动)。虽然选项 -fallow-half-arguments-and-returns 允许按值传递 __fp16,但 API 是非标准的,请注意不要混合不同的编译器。

话虽如此,它不提供使用 __fp16 类型的数学函数(它会将它们提升到 floatdouble 或从 double 提升)。

这对我的用例来说已经足够了。

【讨论】:

  • 缺少__fp16 数学函数是有充分理由的:x86 对半精度的支持仅限于转换为floatvcvtph2ps 和相反),并且仅适用于 SIMD 向量,不支持标量)。因此,它仅对在加载和存储时以 ALU 转换为代价减少数组的缓存占用空间有用。即使转换为double 也需要两个步骤。您绝对不想在 x86 上的寄存器中传递 __fp16 数据,因为每次计算都必须转换为浮点数并返回。
猜你喜欢
  • 2015-09-23
  • 2011-09-21
  • 2013-01-01
  • 2011-08-12
  • 2018-08-13
  • 2018-09-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多