簡體   English   中英

.seh_stackalloc和堆棧對齊

[英].seh_stackalloc and stack alignment

我正在為GNU匯編器編寫一些x64匯編。 我一直在嘗試閱讀有關.seh_ *指令的信息,但我沒有找到太多有關它們的信息。 gas文檔根本沒有提及它們。

但是據我了解,如果我的代碼可能在SEH展開操作期間位於堆棧中,則我希望使用它們。 並且由於我的代碼可以進行堆棧操作並調用其他函數,因此SEH是一種可能,因此我應該使用它們。

通常,我認為我做對了:

.seh_proc FCT
FCT:

push %rbp
.seh_pushreg    %rbp

mov  %rsp, %rbp
.seh_setframe   %rbp, 0

push %r14
.seh_pushreg %r14

lea -(iOffset + iBytes)(%rsp), %rsp
.seh_stackalloc iOffset + iBytes

andq $-16, %rsp <---- But what about this?

.seh_endprologue

etc...

但是還有一點不清楚。 我有以下指示:

andq $-16, %rsp

我到底如何告訴SEH我正在執行堆棧對齊? 這可能會將堆棧調整為從15個字節(極不可能)到8個字節(極可能)到0字節(一定可能)的任何位置。 由於實際數量可能要等到運行時才能確定,因此我陷入了困境。

我想我可以跳過.seh指令,但是如果在那里保留了8個字節的堆棧,那我可能已經浪費了時間,不是嗎? 那不是在這里破壞了整個目的嗎?

或者,我可以省略對齊方式。 但是,如果我調用其他函數(例如memcpy),是否不應該對齊堆棧? 根據MS

堆棧將始終保持16字節對齊,除非在序言中

也許我可以通過這種方式“推理”我的方式? 如果打電話給我的那個人做對了(如果...),那么當他call ,堆棧就對齊了,所以現在我差了8個字節(返回地址)加上我在序言中所做的一切。 我可以依靠嗎? 似乎很脆弱。

我嘗試查看其他代碼,但是不確定我是否相信自己所看到的內容。 我懷疑gas因濫用.seh_ *而報告錯誤。 您可能只會在實際異常期間看到問題(甚至在那時也不總是如此)。

如果我要這樣做,我想做對。 看起來堆棧對齊是很平常的事情,所以有人必須在這里找到解決方案。 我只是沒有看到它。

看着gcc輸出的一些代碼,我想我知道答案了。 我的“推理”方法步入正軌。

調用函數時,堆棧會臨時變得不對齊(由於call ),但幾乎立即通過pushq %rbp重新對齊。 此后,總是使用16的倍數來調整堆棧(對於局部變量或用於調用函數的參數的堆棧空間等),因此在序言結束時,堆棧始終會再次正確對齊,並保持這種方式直到下一個call

這意味着,雖然andq $-16, %rsp可用於對齊堆棧,但如果我正確地編寫了序言,則andq $-16, %rsp

注意:葉子函數(即不調用其他函數的函數)不需要對齊堆棧( https://msdn.microsoft.com/zh-cn/library/67fa79wz.aspx )。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM