2016-09-19 53 views
5

當我讀取xv6源代碼時,我對以下聲明的語法感到困惑。任何人都可以解釋給我嗎?聲明「extern struct cpu * cpu asm(」%gs:0「);」是什麼意思?

extern struct cpu *cpu asm("%gs:0"); 
+2

變量聲明後的'asm'通常允許您指定變量的名稱以用於鏈接目的,但在這種情況下,您根本沒有指定名稱,而是一個類別的寄存器引用。 –

+0

下一次 - 請Google首先! –

回答

7

我假設你明白extern struct cpu *cpu是什麼意思。你的問題是:asm("%gs:0")部分是什麼意思?

此代碼使用名爲asm labels的gcc擴展來表示變量cpu由彙編器字符串%gs:0定義。

這不是打算如何使用此擴展程序,而是將其視爲hack

有一個很好的討論gs(和fs)here,但總之gs指向當前線程的本地存儲。 gs中的數據格式取決於您的操作系統(Windows與Linux非常不同)。這個特定的代碼是說在來自gs的偏移量0處,有一個指向struct cpu的指針。

+0

請參閱[關於最近重複的討論](https://stackoverflow.com/questions/47917027/what-does-asm-suffix-mean-in-given-code/47917087?noredirect=1#comment82802441_47917087) hack要麼不編譯+彙編(32位PIC代碼,或者任何時候編譯器試圖將mov地址作爲立即數「寄存」到寄存器中),或者編譯時更糟糕,但是使用錯誤的地址(64位代碼使用RIP相對尋址) –

7

這是asm label的特例。它指示編譯器發出%gs:0而不是通常的符號名稱,如果您引用cpu變量。據推測,%gs之前已被設置爲每個cpu存儲區域,struct cpu指針位於零偏移處。目的是讓每個cpu訪問自己的數據。

+1

所以這只是調用內存在0字節偏移在gs'cpu'引用的段中? –

+1

是的,基本上是正確的。 – Jester

+0

我匆匆瞥了一眼這個問題有點太快,不知道它是如何使用的。 –