linux汇编字符长怎么看,linux – 在内联GNU汇编程序中获取字符串长...
使用GCC的內聯asm來學習匯編的問題在于你花了一半的時間來學習gcc的內聯匯編是如何工作的,而不是實際學習匯編.例如,這是我如何編寫相同的代碼:
#include
int getStringLength(const char *pStr){
int len;
__asm__ (
"repne scasb
"
"not %%ecx
"
"dec %%ecx"
:"=c" (len), "+D"(pStr) /*Outputs*/
:"c"(-1), "a"(0) /*Inputs*/
/* tell the compiler we read the memory pointed to by pStr,
with a dummy input so we don't need a "memory" clobber */
, "m" (*(const struct {char a; char x[];} *) pStr)
);
return len;
}
將此與您的示例進行比較
>我沒有初始化len,因為asm將它聲明為輸出(= c).
>沒有必要復制pStr,因為它是一個局部變量.根據規范,我們已經允許更改它(雖然因為它是const我們不應該修改它指向的數據).
>沒有理由告訴內聯asm將Ptr放入eax,只是讓你的asm將它移動到edi.我只是把edi中的值放在第一位.請注意,由于edi中的值正在發生變化,我們不能僅將其聲明為“輸入”(按規范,內聯asm不得更改輸入值).將其更改為讀/寫輸出可解決此問題.
>沒有必要讓asm零eax,因為你可以有限制為你做.作為附帶好處,gcc將“知道”它在eax寄存器中有0,并且(在優化版本中)它可以重用它(想想:檢查2個字符串的長度).
>我也可以使用約束來初始化ecx.如上所述,不允許更改輸入值.但是由于我將ecx定義為輸出,gcc已經知道我正在改變它.
>由于ecx,eax和edi的內容都是明確指定的,因此不再需要破壞任何內容.
所有這些都使得(略微)更短和更有效的代碼.
但這太荒謬了.怎么了(我能說’哎呀’嗎?)你應該知道這一切嗎?
如果目標是學習asm,那么使用inline asm并不是你最好的方法(實際上我會說在大多數情況下,inline asm是bad idea).我建議您將getStringLength聲明為extern并將其完全寫入asm,然后將其與您的C代碼鏈接.
通過這種方式,您可以了解參數傳遞,返回值,保留寄存器(以及學習哪些寄存器必須保留以及哪些可以安全地用作劃痕),堆棧幀,如何將asm與C鏈接等等.所有對于內聯asm而言,這比gobbledygook更有用.
總結
以上是生活随笔為你收集整理的linux汇编字符长怎么看,linux – 在内联GNU汇编程序中获取字符串长...的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: git 拉取远程其他分支代码_git切换
- 下一篇: linux 其他常用命令