我需要在golang中编写一些asm代码。我读了这个问题Is it possible to include inline assembly in Google Go code?,但是看不到怎么写。
有人可以帮我吗?谢谢。
asm ("bsrl %1, %0;"
:"=r"(bits) /* output */
:"r"(value) ); /* input */
最佳答案
关于the question you found的所有答案都说,不可能在Go中使用任何语法的inline-asm。 GNU C inline-asm语法将无济于事。
但幸运的是,您不需要为bsr
内联asm(它会找到设置的最高位的位索引)。 Go 1.9具有一个内部/内置函数,用于按位操作,这些操作足够接近以至于应该有效地进行编译。
使用 math.bits.LeadingZeros32
获取lzcnt(x)
,对于非零31-bsr(x)
,它是x
。这可能会花费额外的指令,尤其是在仅支持bsr
而不支持 lzcnt
(例如Intel Haswell之前)的CPU上。
或使用 Len32(x) - 1
Len32(x)
返回表示x
所需的位数。它为0
返回x=0
,并且大概为1
返回x=1
,因此它是bsr(x) + 1
,具有0
的定义行为(因此可能会花费额外的指令)。希望Len32(x) - 1
可以直接编译为bsr
。
当然,如果您真正想要的是lzcnt
,则首先使用LeadingZeros32
。
请注意,对于输入= bsr
, 0
保留了未修改的目标寄存器。英特尔的文档只说了一个未定义的值,因此编译器可能不会利用AMD文档和英特尔确实在硬件中提供的这种保证。
但是,至少在理论上,如果编译器可以证明Len32(x) - 1
不为零,则bsr
可以编译为单个x
指令。
关于go - 如何在Golang中编写asm代码 “bsrl”,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/49704245/