【x86】不同架構(gòu)的編址方法
I/O的概念
本人是從單片機(jī)嵌入式入行BIOS,以前接觸的I/O概念是在GPIO中是一個(gè)簡(jiǎn)單的引腳的概念。
GPIO = General Purpose Input / Output
- 是一種簡(jiǎn)單、靈活的引腳接口,用于和外部電路通信。
- 每個(gè) GPIO 引腳可以單獨(dú)配置為輸入或輸出。
?? 特點(diǎn): - 主要面向低速控制、信號(hào)采集、燈、按鈕等。
- 控制的是芯片封裝上的某一個(gè)具體引腳的電平高低。
- 通常直接連到硬件引腳、沒(méi)有復(fù)雜的協(xié)議。
在CPU中,I/O當(dāng)然也是表示輸入/輸出。但是這里的 I/O = Input / Output 設(shè)備接口。是指 CPU 和外設(shè)(比如顯卡、鍵盤、網(wǎng)卡、串口卡等)之間的讀寫接口。
通常對(duì)應(yīng)總線上的地址空間的一部分,比如:
- I/O 地址空間(比如 x86 的 0x0000~0xFFFF I/O 端口)
- 或者是內(nèi)存映射 I/O(MMIO,把外設(shè)寄存器映射到主存空間)
?? 特點(diǎn): - 主要面向 外設(shè)控制器。
- 編程時(shí)訪問(wèn)的是總線上的 I/O 端口或者 MMIO 地址。
- 比如在 x86 里用
in,out指令操作 I/O 端口。
針對(duì)這IO端口和IO內(nèi)存兩個(gè)概念,下面進(jìn)行詳細(xì)介紹。
IO 端口和IO 內(nèi)存
CPU是通過(guò)IO接口/端口和外設(shè)交換數(shù)據(jù)的。8086CPU和外部設(shè)備之間是通過(guò)I/O接口進(jìn)行聯(lián)系的,從而達(dá)到相互間傳輸信息的目的。
每個(gè)I/O芯片上都有一個(gè)端口或幾個(gè)端口,一個(gè)端口往往對(duì)應(yīng)于芯片上的一個(gè)寄存器或一組寄存器。微機(jī)系統(tǒng)要為每個(gè)端口分配一個(gè)地址,這個(gè)地址成為端口號(hào)。各個(gè)端口號(hào)和存儲(chǔ)器單元地址一樣,具有唯一性。
外設(shè)都是通過(guò)讀寫設(shè)備上的寄存器來(lái)進(jìn)行的,外設(shè)寄存器也稱為“I/O端口”,而I/O端口有兩種編址方式:獨(dú)立編址和統(tǒng)一編址。
也就是說(shuō),CPU要控制所鏈接的設(shè)備,需要通過(guò)IO操作設(shè)備上的寄存器來(lái)實(shí)現(xiàn)對(duì)設(shè)備的控制。
一般廠商按照IO空間性質(zhì)將IO劃分為IO端口和IO內(nèi)存。兩者劃分按照空間是否與CPU空間獨(dú)立劃分:

IO內(nèi)存,也被稱為MMIO(Memory Mapped I/O),將IO空間映射到了內(nèi)存空間,訪問(wèn)這篇IO空間就和訪問(wèn)內(nèi)存一樣沒(méi)什么不同。兩者都是通過(guò)CPU的地址總線和控制總線發(fā)送電平信號(hào)進(jìn)行訪問(wèn),再通過(guò)數(shù)據(jù)總線讀寫數(shù)據(jù)。要想操縱該IO就得首先將該IO映射到CPU的地址中,然后就可以訪問(wèn)該IO,如同訪問(wèn)內(nèi)存。大多數(shù)嵌入式設(shè)備都屬于此。
IO端口,也被稱為PMIO(Port Mapped I/O,有的地方也叫PIO),該IO的空間和CPU空間相互獨(dú)立。兩者互相獨(dú)立,相互不干擾,這種類型IO在X86中比較常見(jiàn),該IO端口有獨(dú)立的空間,所以CPU要想訪問(wèn)該端口就得通過(guò)一些專有函數(shù)或者指令。
獨(dú)立編址
x86 架構(gòu)
獨(dú)立編址指的是CPU訪問(wèn)內(nèi)存和IO端口是分開(kāi)獨(dú)立編址。IO端口地址不占用存儲(chǔ)空間的地址范圍。
這樣,系統(tǒng)中就有了兩類地址--IO地址和存儲(chǔ)地址。CPU如果訪問(wèn)IO端口,則需要使用專用的輸入輸出操作的指令[IN] [OUT] 指令和控制邏輯。
當(dāng)?shù)刂房偩€上有一個(gè)地址過(guò)來(lái),外設(shè)備是不知道給IO端口還是給寄存器的,于是處理器通過(guò)MEMR/MEMW和IOR/IOW兩組控制信號(hào)來(lái)實(shí)現(xiàn)對(duì)I/O端口和存儲(chǔ)器的不同尋址。
獨(dú)立編址也稱為“I/O端口”方式,外設(shè)寄存器位于“I/O(地址)空間”。
對(duì)于x86架構(gòu)來(lái)說(shuō),通過(guò)IN/OUT指令。PC架構(gòu)一共有65536個(gè)8bit的I/O端口,組成64K個(gè)I/O端口,編號(hào)從0~0xFFF,有16位,80x86用低16位地址線A0~A15來(lái)尋址。連續(xù)兩個(gè)8bit的端口可以組成一個(gè)16bit的端口,連續(xù)4個(gè)組成一個(gè)32bit的端口。I/O地址空間和CPU的物理地址空間是兩個(gè)不同的概念,例如I/O地址空間為64K,一個(gè)32bit的CPU物理地址空間是4G。
優(yōu)點(diǎn):
不占用內(nèi)存空間;使用I/O指令,程序清晰,很容易看出是I/O操作還是存儲(chǔ)器操作;譯碼電路比較簡(jiǎn)單(因?yàn)镮/O端口的地址空間一般比較小,所用地址線也比較少)。
缺點(diǎn):
只能用專門的I/O指令,訪問(wèn)端口的方法不如訪問(wèn)存儲(chǔ)器的方法多。
現(xiàn)代的x86 平臺(tái)普通使用了名為內(nèi)存映射(MMIO)的技術(shù),該技術(shù)是PCI規(guī)范的一部分,IO設(shè)備端口被映射到內(nèi)存空間,映射后,CPU訪問(wèn)I/O端口就如同訪問(wèn)內(nèi)存一樣。看Intel TA 719文檔給出的x86/x64系統(tǒng)典型內(nèi)存地址分配表:
BIOS 1M
本地APIC 4K
芯片組保留 2M
IO APIC 4K
PCI設(shè)備 256M
PCI Express設(shè)備 256M
PCI設(shè)備(可選) 256M
顯示幀緩存 16M
TSEG 1M
統(tǒng)一編址
Arm架構(gòu)
外設(shè)結(jié)構(gòu)中的I/O寄存器(即I/O端口)與主存單元一樣看待,每個(gè)端口占用一個(gè)存儲(chǔ)單元的地址,將主存的一部分劃出來(lái)用作I/O地址空間,如,在PDP-11中,把最高的4K主存作為I/O設(shè)備寄存器地址。端口占用了存儲(chǔ)器的地址空間,使存儲(chǔ)容量減小。
此統(tǒng)一編址也稱為“I/O內(nèi)存”方式,外設(shè)寄存器位于“內(nèi)存空間”(很多外設(shè)有自己的內(nèi)存、緩沖區(qū)、外設(shè)的寄存器和內(nèi)存統(tǒng)稱“I/O空間”)。
優(yōu)點(diǎn):
可以利用存儲(chǔ)器的尋址方式來(lái)尋址I/O端口。
缺點(diǎn):
I/O端口占用了存儲(chǔ)空間,而且進(jìn)行I/O操作時(shí),因地址編碼較長(zhǎng),將導(dǎo)致速度較慢。
舉例:
STM32芯片,是32位ARM處理器,它的4GB地址空間被外設(shè)、RAM等瓜分。
總結(jié):
x86是有MMIO的,雖然我們?cè)诒疚闹袑86架構(gòu)劃定為獨(dú)立編址,實(shí)際上因?yàn)镸MIO在Modern x86的應(yīng)用,已經(jīng)模糊了這個(gè)界限,可以說(shuō)x86是統(tǒng)一編址+少量的獨(dú)立IO端口。
一句話: x86 現(xiàn)在本質(zhì)上是“統(tǒng)一編址為主,兼容獨(dú)立 I/O 編址”。
實(shí)際上,這些都是歷史遺留的,為了兼容性而犧牲的歷史包袱,IN/OUT這種輸入輸出的方式完全可以用MMIO來(lái)替代。IN/OUT占著指令編碼,使用起來(lái)需要注意的東西也很多,并且硬件上實(shí)現(xiàn)也很奇怪。

浙公網(wǎng)安備 33010602011771號(hào)