2014-03-27 183 views
1

在谷歌搜索的最好我能找到的ARM NEON Intrinsics。 vmulq_lane_f32做什么?

float32x4_t vmulq_lane_f32 (float32x4_t, float32x2_t, const int) 
Form of expected instruction(s): vmul.f32 q0, q0, d0[0] 

其中寻找到霓虹灯程序员指南表明,它是矢量标量乘法。但也有其他的API正是为了这个目的。

float32x4_t vmulq_n_f32 (float32x4_t, float32_t) 
Form of expected instruction(s): vmul.f32 q0, q0, d0[0] 

所以我还不知道的是第一个API的目的是什么以及它里面的lane的概念是什么。 编辑:以上信息来源:http://gcc.gnu.org/onlinedocs/gcc/ARM-NEON-Intrinsics.html

+0

广播由index参数指定的第二个向量参数的元素,并将其乘以第一个向量参数。 –

+1

标量'float'和'float32xN_t'的一个元素在概念上可能是相同的,但就C编译器而言它们是非常不同的。为什么不支持两者? – Notlikethat

回答

0
float32x4_t vmulq_lane_f32 (float32x4_t, float32x2_t, const int) 
Form of expected instruction(s): vmul.f32 q0, q0, d0[0] 

它应该被写成

float32x4_t dst = vmulq_lane_f32 (float32x4_t q, float32x2_t d, const int c) 
Form of expected instruction(s): vmul.f32 dst, q, d[c] 

其中c可以0-1。

在第二个范例

float32x4_t vmulq_n_f32 (float32x4_t, float32_t) 
Form of expected instruction(s): vmul.f32 q0, q0, d0[0] 

float32_t是一个非向量类型含义编译器将产生必要的代码到该参数加载到向量寄存器然后使用它,所以你得到免费的。

使用vmulq_lane_f32您可以明确地告诉使用哪个寄存器,并且必须确保它在之前包含您想要的内容。

$ cat vmulq.c 
#include "arm_neon.h" 

register float32x4_t a asm("q4"); 
register float32x2_t b asm("d10"); 
register float32x4_t c asm("q6"); 
register float32x4_t d asm("q7"); 

void foo() { 
    c = vmulq_lane_f32(a, b, 1); 
    d = vmulq_lane_f32(a, b, 0); 
} 

void bar() { 
    a = vmulq_n_f32(a, 5); 
} 

$objdump -d vmulq.o 

vmulq.o:  file format elf32-littlearm 


Disassembly of section .text: 

00000000 <foo>: 
    0: f3a8c96a vmul.f32 q6, q4, d10[1] 
    4: f3a8e94a vmul.f32 q7, q4, d10[0] 
    8: e12fff1e bx lr 

0000000c <bar>: 
    c: ed9f7b01 vldr d7, [pc, #4] ; 18 <bar+0xc> 
    10: f3a88947 vmul.f32 q4, q4, d7[0] 
    14: e12fff1e bx lr 
    18: 40a00000 .word 0x40a00000 
    1c: 00000000 .word 0x00000000