arm,assembly,汇编
1. code
直接上代码和注释
#if __ARM_NEON
#if __aarch64__
if (nn > 0)
{
asm volatile(
"0: \n" // 标志,有点像goto
"prfm pldl1keep, [%1, #128] \n" // 从ptr预加载128bit的数据,有提速,注释后不影响程序正确性, 偏移寻址
"ld1 {v0.4s}, [%1] \n" // 从内存中的ptr加载128bit的数据到v0寄存器,v0.4s相当于将v0用做4个32bit的寄存器
"fabs v0.4s, v0.4s \n" // 使用fabs函数 进行绝对值操作
"subs %w0, %w0, #1 \n" // nn = nn - 1 并更新状态标志位, w?:不知道什么意思
"st1 {v0.4s}, [%1], #16 \n" // 后变址寻址方式, ptr = ptr+16(16是移动的字节数)
"bne 0b \n" // 如果前面的状态标志位如果非0,则向后跳转到 0标志处执行, "后"对应上方的代码
: "=r"(nn), // %0,后面感觉是固定格式
"=r"(ptr) // %1
: "0"(nn),
"1"(ptr)
: "cc", "memory", "v0");
}
#else
if (nn > 0)
{
asm volatile(
"0: \n" // 同上
"vld1.f32 {d0-d1}, [%1] \n" // 同上,只是指令变成了vld1.f32, {d0-d1}是把128bit 的q0寄存器当成了2个64bit的寄存器
"vabs.f32 q0, q0 \n" // 绝对值函数操作
"subs %0, #1 \n" // nn = nn - 1
"vst1.f32 {d0-d1}, [%1]! \n" // 将结果写回到ptr,并更新ptr,不需要算ptr的偏移值
"bne 0b \n" // 同上
: "=r"(nn), // %0
"=r"(ptr) // %1
: "0"(nn),
"1"(ptr)
: "cc", "memory", "q0");
}
#endif // __aarch64__
#endif // __ARM_NEON