2012-09-04 90 views
5

我讀這篇文章:http://static.patater.com/gbaguy/day3pc.htm如果CS段寄存器更改會發生什麼情況?

它包括句子

永遠不要更改CS!

但是,如果您修改了CS段寄存器,會發生什麼?爲什麼這麼危險?

+2

'CS' =代碼段。我想改變它是相當於(在某種意義上)到一個變形的'jmp'。 – valdo

+5

該文件看起來相當不可靠:「不要改變CS' !!,但你可以像這樣讀取'CS':'mov ds,cs';把'CS'的值放入'D'S。那麼,在x86中,沒有像'mov ds,cs'和其他任何'mov segreg,segreg'這樣的指令。要讀取'cs'的值,你可以使用'mov reg,cs; mov ds,reg'(其中'reg'可以是'ax','bx','cx'等等)或者'push cs;流行音樂ds'。此外,如果您決定不*更改'cs',則所有的中斷調用都不成問題(例如BIOS,DOS和Linux服務)。 http://web.itu.edu。tr/kesgin/mul06/intel/instr/mov.html – nrz

+1

@nrz:通過'far'調用不能訪問「Linux服務」(中斷/系統調用的工作方式不同;即使這些會導致'cs ',_caller_無法控制'cs'的目標是什麼,這是由操作系統在設置IDT條目/ syscall msrs時決定的)。同其他人一樣,顯然'cs'_can_可以被改變,只是除非目標代碼段存在並且被設置爲可以訪問目標'eip',任何這樣的調用都將導致'#GP'錯誤,並且該應用會中止。 –

回答

7

cs是代碼段。 cs:ip,這意味着cs連同ip(指令指針)指向下一條指令的位置。因此,對csip或兩者的任何更改都會更改下一條指令將被提取和執行的地址。

通常你改變csjmp(跳遠),call(長調用),retfint3intiret。在8088和8086 pop cs也可用(操作碼0x0F)。 pop cs在186+中不起作用,其中操作碼0x0F保留用於多字節指令。 http://en.wikipedia.org/wiki/X86_instruction_listings

在跳遠或長時間通話中沒有任何內在危險。您只需知道您跳到哪裏或打電話的位置,並且在保護模式下您需要有足夠的權限才能執行此操作。在16位實模式下(例如DOS),您可以跳轉並調用您想要的地址,例如。 jmp 0xF000:0xFFF0設置cs0xF000ip0xFFF0,這是BIOS代碼的起始地址,因此重新啓動計算機。不同的內存地址有不同的代碼,因此會導致不同的結果,理論上可能會發生任何事情(如果跳轉到用於格式化硬盤驅動器的BIOS代碼,並使用有效的寄存器和/或堆棧值,則硬盤將被格式化'按照要求')。實際上,對於大多數地址,jmpcall可能會很快導致無效的操作碼或一些其他異常(除以零,除溢出等)。

+0

只更改'cs'通常是錯誤的。通常'cs'和'xip'一起改變或者只是'xip'改變。 –

+3

@AlexeyFrunze那麼,只更改'cs'而不更改/設置'ip' /'eip' /'rip'的唯一方法是'pop cs',它只在8088和8086中可用。在186+中, t改變'cs'而不改變/設置'ip' /'eip' /'rip'。 'pop cs'可能可用於8088/8086(或8088/8086仿真器)的混淆代碼。 – nrz

0

在保護模式和長模式(即不是16位模式)下,包括CS的段寄存器不再只是一個額外的4位地址。它們以分段描述符的表格爲索引,具有基本限制(正常基礎= 0限制= 4GiB,即平坦內存模型),還具有其他屬性。

代碼段描述符確定CPU模式(例如,32位compat模式與64位長模式)。在64位內核上,64位用戶空間進程可能會將某個far jmp轉換爲某些32位代碼。這在實踐中沒有用,甚至在操作系統在上下文切換後返回到您的進程時可能會中斷。

待辦事項:挖掘鏈接,其中有人展示瞭如何做到這一點。我想甚至有一個關於這個問題的最近的問題,有關如何找到正確的細分數字的詳細答案。

相關問題