1

我目前尝试使用 ARM 汇编代码为 iPhone 的 VFP 单元编写程序。VFP 可以进行浮点计算,但 AFAIK 没有整数运算。但是,它可以将浮点数转换为有符号整数(4 个字节)。此外,根据此快速参考:http ://www.voti.nl/hvu/arm/ARMquickref.pdf 似乎它不支持任何移位操作

我想做的是将4个浮点数转换为4个有符号字节,我确信每个浮点数都大于-127且小于127。

如果我有可用的移位操作,我可以将浮点数转换为有符号整数,然后将值向左移动 12 个字节(接下来的两个值分别为 8 和 4 个字节)并将所有四个值按位或。

但是,由于无法转移,我需要找到另一种方法来做到这一点。另外 - 我不能使用整数算术(所以我不能将已经转换的整数乘以 2^n 以进行移位,但我必须改为使用浮点数)。

任何人都知道我怎么能做到这一点?

顺便说一句,对于那些熟悉 ARM 架构的人来说——我不想切换到 Thumb 指令,因为这是在一个对许多元素进行操作的循环中完成的,我不想在这个循环内在 thumb 和 arm 指令之间切换(因为那是昂贵的)

谢谢!

编辑:

附加问题:如何规范化具有三个元素的向量?

4

1 回答 1

2

您需要 VFPftosis指令,它将单精度 FP 值转换为 4 字节整数。如果您在 s0-s3 中有四个浮点数,那么在执行完之后:

ftosis s0, s0
ftosis s1, s1
ftosis s2, s2
ftosis s3, s3

您在 s0-s3 中有四个 4 字节整数,可以使用fstm.

在支持 NEON 的 ARM 处理器上,您可以使用vcvt.s32.f32 q0, q0一条指令进行四次转换。


编辑以回答您的后续问题,这是一个简单的示例函数,它将指向内存中四个浮点数的指针作为输入,并返回打包到单个 int32_t 中的转换值:

_floatToPackedInt:
    fldmias   r0,  {s4-s7}
    ftosizs   s0,   s4
    ftosizs   s1,   s5
    ftosizs   s2,   s6
    ftosizs   s3,   s7
    fmrrs r0, r1,  {s0,s1}
    fmrrs r2, r3,  {s2,s3}
    uxtb      r0,   r0
    uxtb      r1,   r1
    uxtb      r2,   r2
    orr       r0,   r0, r1, lsl #8
    orr       r0,   r0, r2, lsl #16
    orr       r0,   r0, r3, lsl #24
    bx        lr

我并没有真正投入任何精力来调整它,因为如果它们对性能至关重要,你就不会希望以这种方式进行转换;您宁愿对大型值数组进行操作,并将此代码流水线化,以便同时进行多个转换,或者将其与其他也在做有用工作的操作交错。

您可能还想在ssats 之前插入uxtbs 以使任何超出范围的值饱和而不是换行。

另外,请注意此代码在 ARMv7 内核上的性能很差;您肯定会想在该平台上使用 NEON 矢量运算。

于 2010-01-18T23:25:41.410 回答