這一章節(jié)主要講述了GPU硬件的發(fā)展歷程却紧,GPU流水管線以及GPU各種著色器的作用及其適用性(由于本章涉及要很多概念上以及專業(yè)術(shù)語的翻譯,有的地方可能沒有理解到位而導(dǎo)致錯(cuò)誤突照,希望大家能夠幫忙指出迂苛,這也是一個(gè)互相進(jìn)步的過程)。
這一章的篇幅略長念祭,這里分為兩篇介紹:上篇主要介紹GPU并行架構(gòu)以及GPU流水管線的各階段可操作程度;下篇主要介紹各著色器的特點(diǎn)及作用碍侦。
數(shù)據(jù)并行架構(gòu)
CPU與GPU對(duì)于處理延遲的不同策略:
CPU:有多重處理器粱坤,大部分CPU芯片包含本地緩存隶糕,內(nèi)存中存放了需要使用的數(shù)據(jù)。以及其他的技術(shù):預(yù)分支站玄,指令重排枚驻,寄存器重命名、緩存預(yù)取等株旷。
GPU:有一個(gè)大的處理器組再登,稱為著色器內(nèi)核,通常有上千個(gè)晾剖。GPU是流處理器锉矢,依次有序的處理相似數(shù)據(jù)集。由于這種相似性(例如齿尽,一系列頂點(diǎn)或者像素)沽损,GPU可以大規(guī)模并行的方式處理數(shù)據(jù)。相鄰數(shù)據(jù)之間保持獨(dú)立雕什,這樣才可以完全并行處理缠俺,不需要等待另一個(gè)處理器的結(jié)果。
原文有一個(gè)GPU架構(gòu)的贷岸,很生動(dòng)的例子:
假設(shè)一個(gè)網(wǎng)格有2000個(gè)像素需要被渲染壹士,以及有一個(gè)最弱的GPU,每次只能執(zhí)行一個(gè)像素偿警。
他開始執(zhí)行第1個(gè)像素躏救,對(duì)寄存器中的值進(jìn)行一系列算法操作(寄存器是本地的,因此可以快速訪問螟蒸,因此不會(huì)發(fā)生延遲)盒使。接下來他需要訪問一張紋理資源,這是一個(gè)獨(dú)立的資源七嫌,并且訪問紋理可能涉及到一些其他的內(nèi)容少办,這時(shí)間,處理器等待訪問紋理的數(shù)據(jù)诵原,什么也做不了英妓,就產(chǎn)生了延遲。想象一下2000個(gè)像素處理完绍赛,延遲有多大蔓纠。
此時(shí)為了使GPU變得更快,給每個(gè)片元一段本地寄存器儲(chǔ)存空間吗蚌。當(dāng)?shù)谝粋€(gè)像素執(zhí)行到訪問紋理腿倚,就記錄下當(dāng)前像素的屬性,以及當(dāng)前執(zhí)行的指令蚯妇,然后開始處理第二個(gè)像素敷燎,依次處理到2000個(gè)像素暂筝。這時(shí)轉(zhuǎn)回到第一個(gè)像素,他的紋理數(shù)據(jù)正好返回懈叹,則執(zhí)行后續(xù)操作乖杠,然后是第二個(gè)像素,直到2000個(gè)像素全部執(zhí)行完畢澄成。這樣看來,單個(gè)像素的執(zhí)行時(shí)間變長了畏吓,但是整體處理的時(shí)間將大大減少墨状。
接下來有幾個(gè)概念:
SIMD: single instruction, multiple data,單一指令菲饼,多重?cái)?shù)據(jù)肾砂。固定數(shù)量的著色器程序同步執(zhí)行同一邏輯。
線程:2000個(gè)片元宏悦,每個(gè)片元的處理稱為一個(gè)線程镐确。此處線程不同于CPU的線程,他包括一部分將數(shù)據(jù)傳送給著色器的內(nèi)存饼煞,以及供著色器執(zhí)行的寄存器空間源葫。
線程束:使用同樣著色器程序的線程組成的組。
例如:要執(zhí)行2000個(gè)線程砖瞧。英偉達(dá)的GPU一個(gè)線程束支持32個(gè)線程息堂。因此就需要62.5個(gè)線程束。每個(gè)線程束的執(zhí)行與單個(gè)GPU例子相同块促。第一個(gè)線程束執(zhí)行荣堰,其中32個(gè)線程同步執(zhí)行同一邏輯,32個(gè)線程會(huì)同時(shí)遇到訪問內(nèi)存的延遲的情況竭翠,因此整個(gè)線程束會(huì)停掉振坚,轉(zhuǎn)向第二個(gè)線程束。直到所有線程束執(zhí)行完畢斋扰,此時(shí)轉(zhuǎn)向第一個(gè)線程束渡八,其訪問內(nèi)存的數(shù)據(jù)返回,那么他開始繼續(xù)執(zhí)行邏輯褥实。過程如圖所示(圖片源自原書):
接下來會(huì)引出兩個(gè)問題:
其一:寄存器使用的數(shù)量呀狼。每個(gè)線程都需要一段寄存器。但是需要的寄存器越多损离,可以執(zhí)行的線程越少哥艇,那么線程束就越少。線程束的不足僻澎,就會(huì)引發(fā)上述訪問內(nèi)存的延遲貌踏。
其二:動(dòng)態(tài)分支:由if和循環(huán)引起的十饥。同一線程束中32個(gè)線程是同步處理同一邏輯,如果遇到分支祖乳,32個(gè)線程都只取其中一個(gè)分支的結(jié)果逗堵,那么另一個(gè)分支則不會(huì)執(zhí)行。一旦其中一個(gè)線程所需結(jié)果不同眷昆,那么32個(gè)線程同時(shí)會(huì)把兩個(gè)流程執(zhí)行一遍蜒秤,然后各取所需,這也叫線程發(fā)散亚斋。
GPU流水管線
先上圖:
依據(jù)可操作性作媚,各步驟涂上了不同的顏色。
綠色是完全可編程模塊:頂點(diǎn)著色器帅刊,曲面細(xì)分著色器纸泡,幾何著色器,像素著色器赖瞒;
黃色是不可編程但是高度可配置的模塊:屏幕映射階段女揭,合并階段;
藍(lán)色是固定執(zhí)行模塊:裁剪栏饮,三角形設(shè)置和遍歷
頂點(diǎn)著色器是完全可編程的階段吧兔,是用來實(shí)現(xiàn)幾何階段。幾何著色器主要用來操作圖元上的頂點(diǎn)抡爹,也可以用來執(zhí)行每圖元著色操作掩驱,銷毀圖元,創(chuàng)建圖元等冬竟。曲面細(xì)分著色器和幾何著色器是可選的欧穴,也并不是所有的GPU都支持這些著色器,尤其是移動(dòng)平臺(tái)泵殴。
裁剪涮帘,三角形設(shè)置和三角形遍歷階段是固定執(zhí)行階段。屏幕映射受窗口和視口所影響笑诅。像素階段是完全可編程的階段调缨。盡管合并階段不是可編程的,但是他是高度可配置的吆你,可以設(shè)置執(zhí)行的各種操作弦叶。合并階段主要是負(fù)責(zé)顏色,深度緩沖區(qū)妇多,混合伤哺,模板緩沖區(qū)以及其他緩沖區(qū)數(shù)據(jù)的更新。
著色器以及圖形API的發(fā)展
直接上圖:
這一部分主要講了dx和opengl的一路發(fā)展歷程,篇幅也很長立莉,這里就不在贅述绢彤,有興趣可以翻翻原書。從圖中就可以看出蜓耻,短短二十幾年茫舶,圖形學(xué)發(fā)展迅速,從最初的固定渲染管線刹淌,到現(xiàn)在的可編程渲染管線饶氏,將來可能發(fā)展為更高度自由的可編程性。也可以看出芦鳍,未來的圖形學(xué)將有不可預(yù)估的可能性嚷往。
小結(jié):
知識(shí)點(diǎn):對(duì)GPU架構(gòu)的實(shí)現(xiàn)有所了解,尤其是線程及線程束的執(zhí)行機(jī)制。對(duì)目前階段的GPU流水階段各階段的可操作程度有所掌握。下一篇文章將著重介紹各種著色器的特點(diǎn)剃根。
參考資料:Real-Time-Rendering-4th