Itanium (Merced), IA-64

1. 6. 2000

Sdílet

ÚvodJak jsme již řekli, prvním intelovským 64bitovým procesorem se má stát Itanium, dříve zvané Merced, nahrazujíce "starou" architekturu IA-32, reprezentovanou procesory řady x86. (A...

Úvod
Jak jsme již řekli, prvním intelovským 64bitovým procesorem se má stát Itanium,

dříve zvané Merced, nahrazujíce „starou“ architekturu IA-32, reprezentovanou

procesory řady x86. (Ačkoliv se nám název Merced líbí více, v této práci budeme

respektovat rozhodnutí marketingového oddělení firmy Intel, a používat název

Itanium). Přestože IA-64 již existuje v prototypech a intenzivně se chystá

sériová výroba, v materiálech, ze kterých jsme čerpali, jsou mnohé údaje stále

označeny jako pravděpodobné, často proto, že Intel některé detaily prostě

zveřejňovat nehodlá. Upozorňujeme tedy ctěného čtenáře, že konečná verze

procesoru se ještě může v některých detailech lišit od údajů zde uvedených.

Z dostupných informací se ukazuje, k jak zajímavým výsledkům lze dospět

spojením riscového jádra s výhodami CISC procesorů. Design IA-64 (Intel

Architecture) spočívá na Explicit Parallel Instruction Computing (EPIC), takže

můžeme zapomenout na zkušenosti s předchozími známými intelovskými procesory,

včetně zápisu většiny instrukcí assembleru, tak jak jsme se je učili na

procesorech x86. Současný stav odpovídá více RISC procesoru než něčemu jinému,

což se ale netýká množství dostupných instrukcí RISC v případě Intelu znamená

nikoliv Reduced, ale spíše Rich Instruction Set. Je také vhodné uvést, že

přinejmenším první série budou mít zabudovanou speciální IA-32 jednotku pro

převod „starých“ instrukcí na tvar proveditelný na nové architektuře, údajně

bude možné i přepínání těchto dvou modů pomocí speciálních instrukcí. Zatím o

ní ale nemáme bližší informace kromě jednoho nákresu, kde místo jednoho

nicneříkajícího „black boxu“ s nápisem IA-32 jsou boxy tři, jak můžete vidět na

obrázku dole.

Zdá se ale, že můžeme Intelu věřit v tom, že jednotka IA-32 „hardwarově zajistí

plnou kompatibilitu na úrovni instrukcí s předchozí řadou procesorů“. O

rychlosti zpracování v tomto „modu“ nemáme žádné zprávy, v dalším textu již

tedy tuto problematiku zmiňovat nebudeme.

Jako hlavní soupeř architektury IA-64 vystupuje velmi kvalitní procesor Alpha

21264.

Itanium

Stručně lze tento procesor popsat asi takto: superskalární výkonná jednotka

může načítat a provádět v jednom cyklu až šest instrukcí rozdělených do dvou

„balíčků“ (bundle). Procesor využívá desetiúrovňovou pipeline, spekulativní

provádění a jako novinka v IA-64 je jednotka predikátování a rotace registrů.

Dynamické struktury, jako např. samostatná jednotka načítání instrukcí,

neblokující cache a register scoreboarding umožňují předcházet prodlevám v

pipeline zapříčiněným výpadky L1 cache. Itanium obsahuje čtyři celočíselné

funkční jednotky (ALU), dvě jednotky pro zpracování čísel s plovoucí řádovou

čárkou (FPU) a tři jednotky vyhodnocování skoků. Dvě ALU mohou provádět

Load/Store instrukce. Podporovány jsou nejrůznější funkce s FPU a SIMD

instrukce nad celými čísly, post-inkrement ukazatelů pro LD/ST instrukce a

aktualizace loop counteru ve speciálních instrukcích skoku (viz sekce Rotace

registrů). Také schopnost zpracovávat až tři větvení v jednom cyklu je

mimořádná, většina procesorů může zpracovávat jen jedno; negativem je pak

obsazení registrů sloužících k provádění predikce skoků přesto těchto registrů

zbývá ještě dost i na zpracování při větvení bohatého kódu. Výrobce uvádí, že

Itanium dosahuje ve špičce výkonu asi 6 GFLOPS.

Jádro IA-64 sestává z vysokého počtu registrů a výkonných jednotek, což celkový

velmi působivý dojem ještě prohlubuje. Ačkoliv Itanium využívá některé již

dříve známé metody optimalizace provádění instrukcí, jejich vzájemné propojení

do jednoho procesoru je prozatím jedinečné, a podle všeho slibuje nejen že

Intel dožene konkurenci, ale navíc ji může i snadno překonat, právě díky tomu,

že spojil RISC a CISC technologie a elegantně se tak vyhnul problémům, se

kterými se musí potýkat zastánci „čistých“ RISC procesorů při dosahování

vysokých frekvencí zpracování.

Další věcí, jež na první pohled upoutá, je dramatické prohloubení propojení a

spolupráce mezi kompilátorem a procesorem. Např. pro zvýšení výkonnosti

hardwaru oproti RISC a x86 technologii je přenecháno řízení nad predikcí skoku

na kompilátoru, což umožnilo, že procesor zpracovává pouze ty skoky, které

vyžadují dynamickou predikci. Také se využívá vlastnost moderních kompilátorů

tzv. plánování instrukcí (scheduling) tyto údaje jsou odesílány přímo

procesoru, v němž tak odpadla příslušná plánovací logika. Flexibilita je ale

vykoupena značným zesložitěním kompilátoru, dá se však říci, že oprava chyb

kompilátoru je jednodušší než jakékoliv změny v hardwaru. Tato vlastnost jistě

též přispěje v boji s konkurencí, jak ale uvidíme v dalším textu, procesor je v

mnoha velmi zásadních ohledech plně odkázán na správnou práci kompilátoru.

Organizace paměti

IA-64 definuje jeden jednotný, lineární adresový prostor. Jeden znamená, že

instrukce i data sdílejí stejný rozsah paměti. Jednotný znamená, že v paměti se

nenalézají oblasti, které by měly předdefinovanou funkčnost. Konečně lineární

znamená, že adresový prostor neobsahuje segmenty, tj. je spojitý. Z definice

také plynou požadavky na to, aby procesor pracoval s alespoň 54 bity virtuální

adresy a 32 bity reálné adresy.

Itanium implementuje 54bitovou virtuální adresu (51 adresních bitů + 3 bity

indexu regionu) a 44bitovou fyzickou adresu. Registr ID regionu je 18bitový,

což je nejméně, kolik IA-64 povoluje. Architektura též vyžaduje alespoň 16

registrů na ochranné klíče o šířce ID regionu, Itanium má 16 těchto registrů s

šířkou 21 bitů. Podporováno je stránkování paměti s velikostí stránky od

běžných 4 KB až do 256 MB. Přístup k paměti je povolen pouze přes explicitní

použití registrů instrukcemi load a store. Procesor podporuje jak 64-, tak i

32bitové ukazatele, navíc jako novinka se zavedla možnost používat zápis dat

nejen na „intelech“ běžného typu little-endian, ale i big-endian. Některé

operační systémy, o jejichž provoz Intel stojí, jej totiž používají (používá se

např. na procesorech Motorola). K instrukcím se přistupuje vždy v režimu

little-endian, pouze jsou-li data referencována jako big-endian, objeví se

takto v registrech.

O paměťovém podsystému procesoru Intel mnoho přesných informací neuvolnil, ale

předpokládá se, že na čipu jsou dvě 16 KB L1 cache odděleně pro instrukce a pro

data s přístupovou dobou asi 1,5 hodinového cyklu, které zásobuje L2 cache. L2

cache je umístěna v pouzdře s procesorem a její velikost je 256 KB, je schopna

dodávat do L1 256 b za jeden cyklus. Jak datová L1, tak L2 cache mohou

obsloužit dva požadavky typu load v jednom cyklu. Load/store instrukce,

pracující s čísly s plovoucí řádovou čárkou, obcházejí data cache a pracují

přímo s L2, jak ukazuje obrázek. Pro snížení latence je použita metoda

čtyřnásobně prokládané paměti.

Jádro je připojeno k až 4 MB velké L3 cache přes 128b sběrnici pracující na

frekvenci procesoru a schopnou přenosu asi 10 GB/s. Propojení s hlavní pamětí

vede přes sběrnici s rychlostí ve špičce až 4,2 GB/s (asi čtyřnásobek

současných 100MHz sběrnic pro Xeon) na základní desce s čipsetem 82460GX

PCIset. Desky AL460GX pro server s tímto čipsetem stojí za pozornost samy o

sobě, a to nejen kvůli bohatému sběrnicovému vybavení (4F16 channel, 8PCI

hot-plug 64b/66 MHz, 2PCI 64b/33 MHz atd.) , možností instalovat 1 až 4

procesory, ale i podporou pro až 64 GB realizovaných pamětí PC-100 SD-RAM

(odpovídající verzi 1.2). Nakonec i deska BS460GX pro workstation s max. 2

procesory a podporou „pouhých“ 16 GB RWM by nebyla k zahození. Sběrnic má též

dostatek 4F16, 1AGP Pro 4, „jen“ 4PCI/66 a 2PCI/33.

Registry

Itanium je v tomto ohledu samozřejmě navrženo podle filosofie RISC procesorů

„dokud to jde, drž všechno v registrech“. Oproti známým x86 procesorům tady

došlo k jistým změnám, což nejlépe ilustruje obrázek.

Celkem je k dispozici:

- 128 celočíselných registrů s šířkou 64 b + 1 b NaT (o NaT viz sekce

Spekulace), r0=0 implicitně; tyto registry jsou všeobecně použitelné (general

registers)

- 128 registrů pro čísla s plovoucí řádovou čárkou s šířkou 82 b, z toho je 17

b exponent a 64 b mantisa, f0=0,0, f1=1,0 implicitně, mantisa může být užita

pro uložení dvou čísel s plovoucí řádovou čárkou pro SIMD instrukce

- 64 jednobitových registrů na predikáty, p0=1

- 8 registrů skoku o šířce 64 b pro uložení adresy, b0 je Return pointer

- 128 aplikačních registrů, tyto registry mají zvláštní určení. Mnohé z nich

mají v assembleru svoje jména, např. 64bitový ar65 se používá jako Loop Counter

(LC) a je označován ar.lc, obdobně Epilogue Counter (EC, ar.ec). Tyto speciální

registry se používají též při softwarovém pipeliningu.

Dále IP, který může být přímo čten instrukcí mov ip, měněn je i nadále pouze

implicitně vykonáváním resp. načítáním instrukcí.

User Mask – množina jednobitových hodnot, sloužících pro zarovnávání v paměti a

pro monitory výkonnosti a použití FP registrů. Nastavený UM.be bit určuje, zda

procesor bude pracovat s daty tvaru big-endian.

Current Frame Marker – popisuje současný stav rámce registrového zásobníku

všeobecných registrů a FR/PR rotaci, obsahuje také tři hodnoty registrů rotační

báze.

Registry CPUID a n registrů pro monitorování výkonnosti.

Registrů informací o procesoru bude alespoň pět:

Horních 75 % registrů může rotovat obecné i floating point registry r32-r127,

f32-f127, predikátové p16-p63, podle vzorce virtuální registr = fyzický registr

registr rotační báze (RRB).

Soubor instrukcí IA-64

Základní instrukční typy

- Instrukce práce s pamětí, přesuny operandů

- Instrukce pro práci s jednoduchými celými čísly, logické, případně SIMD

instrukce

- Instrukce pro práci s celými čísly, multimediální operace (SIMD)

- Instrukce pro práci s čísly v plovoucí řádové čárce (normální i SIMD)

- Instrukce skoku

Tříd instrukcí je mnoho: logické operace (and), aritmetické (add), srovnávací

(cmp), posuvy a rotace (shl), multimediální (padd), větvení (br), větvení

řídící vykonávání cyklu, zpracování čísel v plovoucí řádové čárce (fma), to

samé jako SIMD (fpma), operace přístupu do paměti a management cache.

Instrukce jsou načítány jako „balíček“, což představuje 341 bitů v instrukčních

slotech, 5 bitů na šablonu. Jeden z bitů v šabloně představuje „Stop“, tj.

značku ukončení bloku.

Šablony

Šablona rozhoduje o namapování instrukcí z instrukčních slotů do prováděcích

jednotek. Povoleno je 122 základní kombinace (z 32 možných) v sudých číslech

není stop bit, v lichých ano.

Balíček je základním kamenem pro instrukční paralelismus, je to základní

jednotka, na kterou se odkazuje Instruction Pointer (IP u Intelu, běžně PC

Program Counter, v ČSN 36 9001 zvaný programový registr), základní jednotka,

kam se provádí větvení programu. Instruction Pointer je dlouhý 64 b a má vždy

hodnotu zarovnanou na délku balíčku, tj. po 16 B a nejnižší 4 b má tedy vždy

nulové. Při vykonávání 32bitových instrukcí je ale v IP nulami rozšířená

32bitová virtuální lineární adresa vykonávané instrukce. Protože 32b instrukce

jsou zarovnávány po slabikách, zmíněné 4 bity v IP musely být zachovány.

Aktuálně prováděný blok kódu může být větší (ve dvou balíčcích paralelně,

případně delší) nebo menší než velikost balíčku. V každém balíčku by měla být

jen jedna operace s čísly s plovoucí řádovou čárkou, důvod a další informace

viz sekci Vykonávání instrukcí.

Zápis instrukcí

Syntaxe:

[(qp)] operátor[.doplňkové určení] r1cíl=r2zdroj[,r3,…,rn[,immediate1,…]]



- povolená pořadí operandů se liší pro jednotlivé instrukce a qp znamená

predikát.

Instrukce jsou z pohledu programátora nadále prováděny sekvenčně, kompilátor

ale rozděluje instrukce do bloků, které nemají žádné konflikty typu write after

write, read after write apod. Jednotlivé bloky jsou odděleny značkami „Stop“.

Programátor ve vyšších programovacích jazycích se o ně naštěstí při zápisu

zdrojového kódu nemusí starat vůbec. V kódu napsaném v assembleru je ale možné

konce bloků explicitně vynutit zápisem dvou středníků, což jsme učinili i v

následujícím výpisu. Explicitní zápis konce bloku se doporučuje používat jen

výjimečně, navíc pokud kompilátor objeví datovou závislost, tak stejně klepne

programátora přes prsty a kód nepřeloží.

Zápis mnoha instrukcí je pro pamětníky assembleru pro x86 novinkou. Všechny

instrukce musí mít kompilátorem dodaný kvalifikační predikát. (IA-64 používá

plně predikátový model viz sekce Predikátování.) Komentáře jsou v assembleru

uvozeny dvěma lomítky //. Změn je však ještě daleko více.

Například:

(p0) cmp.gt p2,p1=r1,r6

(p0) sub r4=r1,r6

;;

(p0) add r4=r4,r1

(p1) add r6=r6,r34

(p2) br Trgt1

;;

(p0) add r4=r4,r6

V tomto kódu se nejprve vypočtou hodnoty predikátů p1 a p2. Predikát p2 se

uplatní tak, že podle jeho hodnoty se buď skočí na dané návěští, nebo bude tato

instrukce ignorována a místo skoku bude k registru r6 bude přičtena hodnota z

registru r34. Predikáty p0 nebudeme již v dalších výpisech uvádět, protože

znamenají nepodmíněné provedení příslušné instrukce a kompilátor je doplňuje

při překladu automaticky.

Celý proces zápisu kódu, tak aby byl zpracovatelný na IA-64, je ale ještě

trochu složitější. Aby procesor věděl, jak nakládat s instrukcemi, musí je

nejprve dekódovat, to ovšem nějaký čas trvá. Konstruktéři Itania proto

vymysleli malý, ale velice efektivní trik procesor si nechá kompilátorem

potřebné informace poslat přímo v balíčku s instrukcemi. Následující příklad

obsahuje dva balíčky uzavřené do složených závorek, povšimněte si použití

predikátování.

{ .iim cmp.gt p8,p9=r3,r6

(p8) sub r12=r3,r6 ld r6=[r6]

}

{ .ii_m add r6=r6,r72

(p9) add r12=r12,100 ;; // značka Stop st [r11]=r12

}

Výrazy .iim a .ii_m specifikují šablonu, m označuje instrukci pracující s

pamětí, i je instrukce pracující s ALU apod. Podtržítko symbolizuje bit

oznamující procesoru, že uvnitř balíčku se vyskytuje značka Stop, a za kterou

instrukcí se nachází.

Itanium tedy má díky tomuto opatření přehled o tom, jaké instrukce bude v

nejbližší době provádět, aniž by je bylo nutné předem dekódovat.

Příklady zajímavých instrukcí:

(p20) ld4 r15=[r30],r8 …natáhni 4 B integer z adresy dané v r30 a proveď na

ni post-inkrement o příslušný krok.

(p4) fma.d.s0 f35=f32,f33,f127 …W = X*Y+Z, vhodné pro zpracování matic nebo

grafické operace

(fms …W = X*Y-Z, fnma …W = -(X*Y)-Z; fpma, fpms, atd. provádějí to samé,

ale jako SIMD)

(p2) add r15=r3,r49,1 …C = A+B+1

Povoleny jsou, jak bylo i dříve zvykem, tzv. přímé operandy s různými délkami,

je-li ale délka menší než 64 b, pak je provedeno znaménkové rozšíření. Oproti

známé instrukční sadě x86 se objevilo mnoho nových instrukcí.

Z/do paměti lze instrukcí load/store číst 1,2,4,8 B nebo číslo typu single,

double, extended, 8 (to je dlouhý integer, např. v případě násobení, nebo

ukazatel). Po load se vždy provede post-modifikace ukazatele, po store nikdy. K

oběma těmto instrukcím kompilátor přidává dva bity pro statickou predikci

prostorové a časové lokality dané paměťové oblasti.

Standardní instrukce Load

(qp) ld.sz.ldtype.ldhintr1 = [r3], r2

(qp) ld.sz.ldtype.ldhintr1 = [r3], immediate9

(qp) ldf.fsz.fldtype.ldhintr1 = [r3], r2

(qp) ldf.fsz.fldtype.ldhintr1 = [r3], immediate9

Platné délky sz: 1,2,3,8 B

fsz: s (ingle), d (ouble), e (xtended), 8 (integer)

Platné typy: s, a, sa, c.nc, c.clr, c.clr.acq, acq, bias

Standardní instrukce Store

(qp) ld.sz.ldtype.ldhint[r3] = r1

(qp) ld.sz.ldtype.ldhint[r3] = r1, immediate9

(qp) ldf.fsz.fldtype.ldhint[r3] = f1

(qp) ldf.fsz.fldtype.ldhint[r3] = f1, immediate9

Platné délky a typy: jako u Load

Typy větvení (skoky) se také rozrostly. Např. podmíněné větvení a volání

procedury (call) může být IP-relativní, kdy k IP je přičten 21bitový

displacement. Dále skoky nepřímé (přes registr větvení s adresou délky 64b)

nebo založené na predikátování. Dále návraty z podprogramů Return nepřímé s

kvalifikačním predikátem (QP), jednoduché smyčky řízené počítadlem, modulo

scheduled counted loops IP-relativní s Ar.lc a Ar.ec, modulo scheduled while

loops IP-relativní s QP a Ar.ec.

Syntaxe zápisu větvení se tak poněkud rozkošatěla.

(qp) Br.btype.bwh.ph.dhtarget25 / b2

(qp) Br.Call.bwh.ph.dhb1 = target25 / b2

Branch Whether Hint (bwh):

sptk / spnt Static Taken / Not Taken

dptk / dpnt Dynamic

Sequential Prefetch Hint (ph):

few / none několik řádků

many

Branch Cache Deallocation Hint (dh):

none

clr smazat

Př.: Ar.lc se automaticky dekrementuje, není třeba obsazovat obecný registr.

/* r3 = 10*(r9+r11) */ mov ar.lc = 10 // počítadlo cyklu ve zvláštním registru

;;

loop: add r3 = r9, r11

br.cloop.sptk loop// podmínka v „počítané“ smyčce

(Pokud je „tělo“ smyčky delší, je nanejvýš vhodné upozornit na to příslušnou

logiku: br.cloop.many.sptk loop.)

Procesor oslňuje především prací s plovoucí řádovou čárkou, neboť každá

load/store instrukce může odstartovat pár double-precision load instrukcí (DP)

pomocí instrukce ldfpd, a každá FPU může spustit dvě DP operace s použitím fma

instrukce. Tím pádem může Itanium načíst čtyři DP operandy a zahájit čtyři DP

operace v jednom cyklu (!), a ještě zbývají dva instrukční sloty na operace s

celými čísly nebo větvení. Většina celočíselných instrukcí se provede za jeden

cyklus. Duální FPU jsou zapojeny jako pipeline pro všechny operace, přesto ale

vykonávání zabírá více cyklů, předpokládají se tři cykly pro add nebo mul.

IA-64 plně podporuje formáty čísel s plovoucí řádovou čárkou podle specifikace

IEEE. Intel na tomto procesoru znovu potvrzuje tradičně výbornou výkonnost

svých procesorů ve zpracování plovoucí řádové čárky.

Instrukční pipeline

Pipeline v Itaniu má deset úrovní, jak ukazuje obrázek. Ze svých deseti úrovní,

což je o dvě až tři úrovně kratší než u Pentia III, těží mnohé výhody, přesto

je díky složitostem x86 architektury ještě o dvě až tři sekce delší než

pipeline u Alphy 21264. Použito bylo též oddělení pipeline pro načítání

instrukcí od pipeline na jejich provádění. To umožňuje pokračovat v načítání

instrukcí i v případě, že výkonná jednotka musí čekat. Naopak výkonná jednotka

může pokračovat v provádění instrukcí z fronty, i když větvení způsobilo

„bublinu“ v pipeline, v intelovské hantýrce resteer.

Ve frontě lze držet až 8 balíčků, tj. 24 instrukcí, což stačí na překrytí

výpadků ve frontě, ale nestačí v případě špatného odhadu větvení. Začátek

pipeline sestává ze tří částí, podrobnější popis zde uvedeného schématu najdeme

v oddíle Predikce skoků.

Po výpočtu IP a výběru adresy v první fázi procesor ve fázi druhé načte

instrukce z instrukční cache a načtená instrukce se dostane do třetí fáze.

Odtud po strávení nula nebo více cyklů ve frontě jsou platné instrukce zařazeny

do prováděcí pipeline, její začátek je fáze EXP. V ní jsou instrukce nejprve

přiřazeny funkční jednotkám a v páté fázi je provedeno přemapování registrů,

ale přístup k rozsáhlému 128položkovému poli registrů si vyžádá ještě i

následující dva cykly. Nakonec je instrukce provedena s využitím DET fáze pro

načtení operandů z cache nebo na provedení větvení. V poslední WRB fázi je

proveden podmíněný zápis výsledků. Podrobnější popis je opět v sekci Predikce

skoků.

Itanium na rozdíl od mnoha jiných procesorů (zejména riscových) neprovádí

instrukce mimo pořadí, přesto ale různě dlouhé doby provádění matematických,

load apod. instrukcí způsobují jejich dokončení mimo pořadí. Procesor proto

obsahuje register scoreboard, který slouží k určení, zda cílový registr je

používán.

Dokud žádná instrukce nepožaduje výsledek vícecyklové operace, tečou instrukce

v pipeline normálně. Tok se zastaví pouze tehdy, pokud chce instrukce

přistoupit k registru, který je ve scoreboardu označen jako nedostupný.

Paralelismus provádění instrukcí

Již delší dobu výrobci hledají cesty, jak zvýšit výkon mikropocesorů pomocí

paralelního provádění instrukcí. Idea paralelismu na úrovni instrukcí

(instruction-level paralelism, ILP) znamená zapojení více výkonných jednotek,

na nichž lze určitou sadu instrukcí spustit paralelně. Pro názornost uvedeme

obrázek.

Běžné programovací jazyky nepodporují přímo zápis instrukcí pro řízení

paralelního provádění do zdrojového kódu. Teprve kompilátor se pokusí stávající

sekvenční tok programu paralelizovat a vytvořit kód vhodně uzpůsobený pro

paralelní vykonávání. Poslední podmínkou úspěchu pak je spuštění tohoto kódu na

hardwaru, který může výhod paralelismu využít.

Jsou tu však některé problémy:

- instrukce větvení (tj. skoky), které zavádějí závislost na řízení

- latence (zpoždění) paměti, tj. čas potřebný k natažení dat z paměti.

Protože chybí obecně použitelné explicitně paralelní programovací jazyky,

veškerá tíha uplatnění ILP spadá na kompilátor „běžného“ programovacího jazyka.

V IA-64 tak kompilátor hraje klíčovou roli při predikátování a spekulativním

řízení při vytvoření kódu s použitím ILP.

Vykonávání instrukcí

Jelikož Itanium neprovádí vykonávání instrukcí mimo pořadí, je každé instrukci

přiřazena výkonná jednotka, jakmile opustí frontu v EXP fází (viz oddíl

Instrukční pipeline). Fronta posílá dva balíčky, tj. šest instrukcí, najednou.

Pole určená pro šablony v každém z nich určují typy každé z instrukcí (integer,

paměť, FP, apod.). Standardní instrukční sada by vyžadovala plně křížové

přiřazování jednotlivých instrukcí do každé z výkonných jednotek, což by se

však negativně projevilo na obsazené ploše čipu a mohlo by to prodloužit délku

cyklu. Oproti tomu IA–64 povoluje pouze omezený počet platných šablon (viz

sekce Soubor instrukcí IA-64). Např. instrukce pro práci s pamětí nemohou být

nikdy ve třetím slotu (Slot 2), zatímco FP instrukce zase nemohou být ve slotu

prvním (Slot 0).

Jak ukazuje obrázek vpravo dole, každá funkční jednotka si musí vybrat

instrukci z ne více než tří možných slotů, což podstatným způsobem zjednodušuje

multiplexory a směrování instrukcí vůbec.

Jak jsme se již zmínili, šablony též indikují konec každé skupiny instrukcí

nastaveným bitem „Stop“. Tyto skupiny plně určuje kompilátor obecně jsou to

takové úseky instrukcí, které neobsahují vzájemné datové závislosti. Pokud se v

šabloně vyskytne Stop, procesor jednoduše počká s vykonáváním následujících

instrukcí na další cyklus. Díky této metodě se Intel vyhnul řešení složité

logiky na testování datových závislostí v průběhu provádění instrukcí, na

jejichž odhalování je v tradičních superskalárních procesorech vynakládáno

značné množství logiky. Její složitost ale roste exponenciálně s počtem

najednou zpracovávaných instrukcí. Procesor Itanium se však takto v tomto

ohledu plně vydává do rukou kompilátoru.

Všechny instrukce z obou balíčků mohou být poslány ke zpracování, pokud šablona

neobsahuje Stop, s výjimkou že je tato značka na konci druhého balíčku, a

pochopitelně pokud se nemusí čekat na některý zdroj (registr, paměť apod.).

Tento druhý případ nastává, pokud se např. musí zpracovávat více než dvě

instrukce pro práci s pamětí. Instrukce neodeslaná v prvním taktu se pošle v

taktu následujícím, přestože tato situace nezpůsobí zastavení instrukční

pipeline, dovoluje naplnit frontu načítaných instrukcí.

Jakmile procesor natáhne a dekóduje instrukce, musí vybrat jejich operandy.

Itanium podporuje registrové rámce a rotaci registrů (viz sekce Registry),

proto přemapovává registry pomocí sedmibitových sčítaček v REN fázi. V další

fázi (WLD) jsou přemapované adresy přesunuty do souboru registrů, k nimž je v

další (REG) fázi přistoupeno. I když je hardware na přejmenovávání registrů v

Itaniu relativně jednoduchý, stejně si tento proces vyžádá tři cykly; např. v

Alpha 21264 nebo Pentiu III to jsou jen dva cykly. Něco z tohoto nárůstu

potřebného času lze přičíst na vrub rozsáhlého vícebránového registrového pole,

ale téměř prázdná WLD fáze vypadá podezřele, podobně jako pozdní přidávání do

pipeline, potřebné pro dosažení požadované pracovní frekvence.

Itanium obsahuje register stack engine (RSE) pro automatickou obsluhu situace,

kdy velikost registrového rámce překročí fyzickou velikost registrového pole. V

tomto případě RSE pozastaví vykonávání a provede potřebné uložení/obnovení

pomocí dvou paměťových portů. V budoucích IA-64 procesorech se počítá s tím, že

RSE využije nepoužité paměťové pozice tak, aby provedl všechna potřebná uložení/

obnovení dat ještě předtím, než budou registry potřeba konstruktéři Itania však

zvolili jednodušší variantu. O použití RSE více v oddíle Rotace registrů.

Predikce skoku

Protože špatný odhad skoku znamená ztrátu devíti cyklů, Itanium se, podobně

jako všechny ostatní moderní procesory, musí snažit za každou cenu těmto chybám

vyhnout. Naprosto zásadní vlastností IA-64 je možnost eliminovat mnohá větvení

pomocí jejich předpovídání (predikování), které dovoluje úplně předejít možnému

chybnému odhadu. Itanium ale nezanedbává ani ty varianty větvení, které nejsou

eliminovány. Pro jejich přesnou předpověď jsou užívány i některé dosud

nepoužité metody.

První je instrukce predikce skoku (BRP), kterou kompilátor může použít tak, aby

se procesor přesněji dozvěděl, jaké má předpokládat větvení, a jak přednačíst

příslušné cílové instrukce. BRP dodává adresu nadcházející instrukce, její

predikovanou cílovou adresu a „důležitost“ větvení spolu s dalšími pomocnými

údaji pro předpovídání.

BRP je implementována pomocí čtyř registrů (target address registers, TARs),

které uchovávají cílové adresy naposledy použitých BRP instrukcí s nejvyšší

prioritou. Každý TAR také uchovává adresu samotné BRP instrukce. Jakmile se

program counter (IP) setká s jednou z těchto adres větvení, cílová adresa je v

následujícím cyklu zapsána do instrukční cache. Takto tedy až čtyři jednotlivá

větvení mohou dosáhnout svého provedení za nula hodinových cyklů procesoru.

Druhá možnost je přesměrování (resteer) načítaného proudu instrukcí ve FET fázi

(viz sekce Instrukční pipeline a obrázek fronty načítání instrukcí).

Zde je implementován konvenční predikovací mechanismus využívající

- osmipoložkový return stack buffer (RSB), sloužící k predikci návratů z

podprogramu,

- 512položkovou branch history table (BHT),

- 64položkovou branch target address cache (BTAC),

používán je však jedinečným způsobem.

Na rozdíl od dalších RISC i CISC procesorů IA-64 poskytuje staticky

predikovanou „nápovědu“ k určení snadno odhadnutelných větvení, která nemají a

dokonce nesmí být ukládána do BHT. Takže ačkoliv BHT v Itaniu je daleko menší

než třeba v Alpha 21264 nebo Athlonu i dalších mikroprocesorech, může dosáhnout

podobné efektivity zaměřením se pouze na ta větvení, která vyžadují dynamické

předpovídání.

BHT má stupeň asociativity čtyři a používá dvouúrovňový PA algoritmus. (Obdoba

postupu známého z nových Pentií.) Každá položka vybraná s použitím adresy

větvení sleduje čtyři naposledy použité případy větvení, do příslušného

posuvného registru je vkládána 1 nebo 0 podle toho, zda se skok provedl nebo

ne. Tato položka indexuje jednu ze 128 tabulek vzorů (jedna na sadu). Šestnáct

položek v každé tabulce vzorů používá standardní dvoubitový vratný čítač na

predikování směru větvení, tj. dva stavy čítače indikují, že se skočit má, dva

že nemá. Stav jednoho z čítačů je modifikován při každé instrukci větvení.

Celková velikost paměti potřebná pro BHT je tedy asi 20 Kb.

Druhá, menší BHT se používá pro větvení na více míst. Tato 64položková

struktura používá stejný algoritmus, ale udržuje si tři history registry na

každou položku, kterou je balíček. Provádí výběr typu „najdi první vybranou“ k

poskytnutí první predikované použité adresy, nebo indikuje, že žádná z

predikovaných nebyla vybrána.

Kompilátor umisťuje adresy přímo do BTAC pomocí BRP instrukcí. Větvení, které

je zaznamenáno v BTAC nebo v RSB (návrat), ihned zařadí správnou cílovou adresu

do pipeline, čímž vzniká jednocyklová díra (tzv. bublina) v načítaném proudu.

Pokud je ale načítací fronta naplněná, tj. je napřed před prováděcí, pak

nedojde k žádnému zpoždění (základní výhoda oddělení front). Pokud BHT

predikuje, že dojde k větvení, ale menší BTAC neobsahuje cílovou adresu, pak

tato musí být spočítána později pomocí jednoho nebo dvou adresových kalkulátorů

(BAC).

Jiná možnost vzniku bubliny nastává ve dvou situacích. BAC1 např. může spočítat

cílovou adresu skoku ve třetím slotu každého balíčku. Převážná většina šablon

klade skok právě do třetího slotu, takže BAC1 může spočítat většinu adres

skoku. Pokud ale nebyl směr větvení předpovězen podle BHT, BAC použije

statickou predikci, jež je zakódovaná do každé instrukce větvení. BAC1 též

obsahuje logiku, která sleduje loop counter (LC) registr a může obejít zpoždění

dané nyní již chybnou adresou čtenou z TARů, pokud LC signalizuje konec smyčky.

Tyto situace způsobí dvoucyklovou bublinu. A konečně, BAC2 může spočítat

cílovou adresu skoku v každém slotu, je-li ale tato jednotka v EXP fázi

použita, pak to způsobí třícyklovou bublinu.

Ve většině případů tyto bubliny nezpůsobí zastavení práce výkonné jednotky, ale

je pochopitelně nutné, aby načítací pipeline byla plná, pokud požadujeme pokrýt

i celkem vzácně se vyskytující třícyklovou bublinu.

Jiný případ, než jsou důsledky výše popsaných akcí, je špatný odhad cílové

adresy. V této situaci dojde k zastavení výkonné jednotky, to jest pokud se v

DET fázi (viz sekci Instrukční pipeline), kdy dochází k vyhodnocení podmínek,

vyhodnotí podmínka větvení jinak, než bylo předpokládáno, a musí se počkat

zmíněných devět cyklů procesoru, než se instrukční fronta znovu naplní. To je

ovšem situace, kvůli které se všechna výše uvedená opatření dělají, naštěstí k

ní ale (alespoň podle údajů výrobce) nedochází příliš často.

Predikátování

Všechny IA-64 instrukce jsou vykonávány podmíněně, podle obsahu jednoho z 64

jednobitových predikátových registrů. Jelikož je k dispozici dostatek funkčních

jednotek, Itanium prostě provádí všechny instrukce v EXE fázi, a případně

jejich výsledky zruší v DET fázi, kdy se uplatní hodnota z predikátového

registru.

Zrušení instrukcí dříve by sice vedlo k vyloučení některých konfliktů v

přístupu ke zdrojům, ale znamenalo by to dřívější přístupy k predikátovým

registrům, což by mohlo narušit plynulý pipelining. Místo toho Itanium čte

hodnotu predikátu společně s ostatními operandy a předá je dál příslušným

logickým obvodům. Designéři si dali práci se zabráněním zdržování chodu

pipeline kvůli instrukci, která má být později zrušena. Pipeline se v normálním

případě musí zastavit, pokud instrukce potřebuje data, která ještě nejsou k

dispozici, ale pokud je instrukce predikátována jako neplatná, pak je tomuto

zdržení zcela zabráněno, je-li příslušný predikát včas předpočítán v

registrovém poli. Pokud musí být predikát předán z předchozí EXE fáze, pak je

zdržení jen jeden cyklus, případně dva, závisí-li výsledek predikátu na

porovnání čísel s plovoucí řádovou čárkou (fcmp).

Než budeme pokračovat, zmiňme alespoň krátce takzvanou závislost na řízení

(control dependency); to znamená, že provedení instrukce závisí na vyhodnocení

směru větvení. Druhý typ je datová závislost (data dependency), kdy požadovaná

data mohou být modifikována předchozími instrukcemi. Obecně taková závislost

brání vykonávání instrukcí paralelně.

IA-64 vytváří podmíněná větvení pomocí predikátování základních instrukcí

větvení. Architektura dovoluje kompilátoru spojit větev programu s instrukcí,

která generuje predikát, což je jedna z mála datových závislostí povolených ve

skupině instrukcí. Pro obsloužení tohoto případu Itanium čeká s vyhodnocením

směru větvení až do DET fáze, což je jeden cyklus po vyhodnocení porovnávací

instrukce v EXE fázi. Ve fázi DET procesor analyzuje až tři podmínky větvení a

vybírá správnou cílovou adresu. V poměrně vzácném případě, že se tato adresa

neshoduje s adresou předpovězenou načítací jednotkou, nastává zpoždění devíti

taktů, jak bylo již uvedeno v sekci Predikce skoků.

Př.: Vezměme opět klasický příkaz if-then-else. Na tradiční architektuře

procesor natáhne data z paměti, porovná podmínku, a tím získá výsledek potřebný

pro větvení. Protože se jedná o podmíněný skok, tradiční kompilátor rozdělí kód

do čtyř základních bloků. „Klasický“ procesor pak vykonává tyto bloky sekvenčně

a instrukce skoku jsou nepřekonatelnou překážkou pro rozvinutí ILP. Kód pro

IA–64 ale jde na věc úplně jinak. Použije predikátování na nesnadno

odhadnutelný výsledek if podmínky. Instrukce porovnávání generuje dva predikáty

(true / false) podle svého výsledku. Then blok se vykoná, má-li predikát

hodnotu true, else blok v opačném případě. Výsledkem je kód bez instrukce

větvení, takže then i else blok se vykonávají paralelně. Jelikož tyto bloky se

vzájemně vylučují, dvě instrukce ukládání výsledku běží zároveň, navíc ukládají

na stejnou adresu. Ale predikát povolí pouze jedné z nich výsledek skutečně

uložit do paměti. Druhý výsledek je zrušen. Tímto způsobem predikátování

podporuje paralelismus na úrovni instrukcí odstraňováním větvení a časových

ztrát při jejich případných špatných odhadech. IA-64 tak konstrukci

if-then-else provádí jako jeden blok.

Ukažme si tento důležitý trik:

Podmínkový registr lze například naplnit pomocí instrukce cmp:

cmp.gt p8,p9=r3,r6

Tato instrukce zjistí, zda je r3 větší než r6. Pokud tomu tak je, pak p8 se

nastaví na true, p9 na false a naopak. Toho lze výhodně použít např. při

zmíněné kompilaci bloku if-then-else. Možností použití je mnoho, ale tento je

pochopitelně nejnázornější. Následující kód

if (r3>r6) { r2=r3-r6;

}

else { r2=r6-r3;

}

lze přeložit jako: cmp.gt p8,p9=r3,r6

(p8) sub r2=r3,r6

(p9) sub r2=r6,r3

Tím jsme závislost na řízení převedli na závislost datovou.

Je vidět, že se takto mikroprocesor vyhne větvení, které by mohlo způsobit

zpomalení programu. Mezi p8, p9 a provedením instrukce sub je vztah read after

write, ovšem architektura procesoru je navržena tak, aby mohl paralelně

zpracovat porovnání a další instrukce, které jsou tímto porovnáním podmíněny.

Oblíbenou částí nejrůznějších nezáživných pojednání bývají příklady „ze

života“, dejme si tedy také jeden takový. Ukážeme si v něm, jak implementovat

příkaz switch z jazyka C pomocí sdružování instrukcí do bloků (skupin) a s

využitím predikátů.

/* C kód */

switch (typ)

{ case \a\: typ=typ+10; break; case \b\: typ=typ+20; break; default: break;

}

bude po převodu do assembleru:

mov1 r1 = typ

ld4 r2 = [r1]

;;

cmp.eq p1,p2=\a\,r2

cmp.eq p3,p4=\b\,r2

;;

(p1) add r2=10,r2

(p3) add r2=20,r2

;;

st4 [r1]=r2

default::

Spekulace

Spekulativní čtení

O spekulativním provádění jsme se zmínili v předchozím odstavci, v této sekci

se podíváme na spekulativní čtení z paměti (ld.s), které se snadno implementuje

na hardwarové úrovni.

Pokud při provádění kódu nastane situace, že instrukcí požadovaný operand (již

připravený v registru) byl změněn, vzniká výjimka. Výjimky nastavují NaT bit a

jsou propagovány skrz následující výpočty. NaT Bit (Not a Thing) je přidán ke

všem všeobecným registrům, pokud je jeho hodnota 1, pak je hodnota uložená v

daném registru neplatná. Floating point registry používají speciální druh

označení NaN, zvanou NaTVal (NaT Value), která se používá stejným způsobem pro

označení neplatnosti výsledků spekulativního provedení ld pro čísla s plovoucí

řádovou čárkou. V příslušných výpočtech procesor nakládá s NaT bitem jako by to

byl 65. datový bit. Testovací instrukce chk.s je jednoduše podmíněný skok podle

hodnoty tohoto bitu. Datová spekulace nijak nebrání průchodu výjimek, například

výpadky stránek jsou obsluhovány okamžitě.

Další příklad ukazuje možnost natáhnout data z paměti před vyhodnocením větvení:

/* C kód */

int add5(int *a)

{ if (a==NULL) return (-1); else return (*a+5);

}

se dá do assembleru převést takto:

add5: ld8.s r1=[r32] cmp.eq p6,p5=r32,r0 ;;

(p6) add r8=-1,r0

(p6) br.ret

(p5) chk.s r1,return_error add r8=5,r1 br.ret ;; …

return_error: …// ošetření chyby, může jej generovat jak programátor, tak i

kompilátor

Pro názornost uvádíme dva následující obrázky.

Dopředné čtení

Instrukce dopředného čtení (advanced load, ld.a) vkládá svoji adresu do ALAT

(advanced load address table). V DET fázi dochází k testování následujících

ukládacích adres proti ALAT a položky, které se shodují, jsou odstraněny.

Pozdější ld.c nebo chk.a instrukce také testují ALAT, pokud je položka

nalezena, procesor provede microtrap (mikropřerušení) a provede znovu příslušný

load, což ale způsobí několikacyklové zdržení, protože pipeline je vyprázdněna.

Ve většině případů však testovací instrukce uspěje bez zdržení. Aby se předešlo

přetížení, Itanium může provádět testovací instrukci v tom samém cyklu jako

instrukci, která data používá. Pokud test selže, „používací“ instrukce je

zrušena.

ALAT má v tomto případě 32 položek a je indexována sedmibitovým ID registrem.

Ukládá pouze podmnožinu fyzického tagu adresy, což zmenšuje požadavky na

ukládací kapacitu, ale způsobuje to chybné detekce shody. Jejich množství je

však malé a důsledkem je pouze znovuprovedení příslušného čtení z paměti.

Př.: Podívejme se teď, jak na IA-64 funguje dopředné čtení. Instrukce ld.a

umožňuje provést potenciálně datově závislé instrukce load v předstihu.

Použijeme-li tuto instrukci, musíme si výsledek naší spekulace ověřit to se

dělá „ověřovací“ instrukcí ld.c, jež musí být umístěna na místě původní

nespekulativní instrukce ld. Pokud se obsah paměti na dané adrese od chvíle

dopředného čtení nezměnil, spekulace uspěla a latence paměti se neuplatní.

Pokud ale ke změně došlo, ld.c provede čtení, jako by to udělala původní

„obyčejná“ ld instrukce.

Příklad ukazuje typický stav funkce obdrží dva ukazatele do paměti, ale neví,

zda neukazují na stejné místo. Pokud jsou oba ukazatele různé, st neovlivní

následující ld a naopak, jedná se tedy o příklad datové závislosti.

/* C kód */

int foo(int *addr1, int *addr2)

{ int h; *addr1 = 4; h = *addr2; return(h+1);

}

Tuto funkci lze přeložit dvěma způsoby:

Normální provedení instrukce load

add r3=4,r0 ;;

st4 [r32]=r3

ld4 r2=[r33] ;;// regular load

add r5=r2,r3// použití načtených dat

Dopředné provedení instrukce Load

ld4.a r2=[r33]// advanced load

add r3=4,r0 ;;

st4 [r32]=r3

ld4.c r2=[r33] ;;// zde se pouze načtená data ověří!

add r5=r2,r3// použití načtených dat

Oba typy spekulativního čtení lze kombinovat, jak ukazuje příklad:

/* C kód */

if (foo2() == NO_ERROR)

{ x=*a;

}

y=x+5;

Kombinovaná spekulace vypadá v assembleru takto:

ld.sa r3=[r40]

br.call b0=foo2

mov r5=NO_ERROR ;;

cmp.eq p1,p0=r8,r5

(p1)chk.a r3,CORRECTION_CODE

adds r5=0×5,r3

Procesory RISC i x86 mohou měnit dynamicky pořadí čtení i zápisu do paměti a

hlídat případné konflikty, provádějíce vlastně ekvivalent dopředného čtení.

ALAT ale poskytuje hardwarově daleko jednodušší řešení tohoto problému.

Některá PowerPC či SPARC procesory používají k odstranění latence čtení

hardwarově i softwarově řízené přednačítání místo spekulativního čtení. IA-64

má však díky své metodě výhodu zápisu dat přímo do registrového pole, což

umožnilo zabránit prodlevám mezi čtením a následným použitím dat, navíc se

podařilo lépe se vyhýbat přednačtení nepotřebných dat, která by plýtvala

drahocenným místem v cache. Itanium implementuje tyto důležité vlastnosti s

minimálním množstvím složitého navrhování příslušných hardwarových struktur.

Rotace registrů

Rotace integer registrů slouží k vytvoření „registrového zásobníku“.

Na IA-32 se s procedurami pracuje takto:

Procedure A call B



Procedure B

// musí se uložit současný stav registrů



// před návratem se musí obnovit do registrů původní stavreturn



A na IA-64?

Procedure A call B



Procedure B alloc // nemusím se zdržovat ukládáním



// ani obnovováním stavu

return

Podívejme se na toto téma podrobněji: efektivní zpracovávání smyček je jedním z

klíčů podmiňujících výkonnost jakékoliv počítačové architektury. Pochopitelně

zpracovávání smyčky jako jednoduchého větvení vede k dost mizerné výkonnosti,

IA-64 proto poskytuje zvláštní podporu vlastnosti rotace registrů.

Větvení obecně zabírá čas, ale pokud kompilátor zná dopředu o jaký typ větvení

se jedná, může se vzniku mnoha typů větvení zabránit jednoduchým opakováním

kódu příslušné smyčky, dvakrát, čtyřikrát i víckrát, což umožní zvýšit

paralelismus kódu. Celá technika se nazývá „rozbalení“ smyčky a není to žádná

novinka, podporuje ji většina RISC architektur.

Provádění smyček

Ani toto řešení není tak snadné, jak by se snad zdálo z prvního pohledu.

Problém s jednoduchým rozbalením smyčky spočívá v neúnosném nárůstu délky

programového kódu. V IA–64 se proto objevilo zajímavé řešení, zvané právě

rotace registrů. To umožňuje řazení smyčky do pipeline s optimální efektivitou

a bez nárůstu objemu kódu.

Jak registry, tak predikáty mohou rotovat podle řízení stanoveného

kompilátorem. Celá operace probíhá tak, že v každém kroku rotace je např.

hodnota z r32 postoupí do r33, z r127 do r32 (proto rotace), podobně se mohou

posunout predikáty. Díky tomu lze provést kód ve smyčce a výsledky jsou

automaticky posouvány do následujících registrů. Když smyčka končí, predikáty

se nastaví na nulu podle vyhrazených registrů loop count a epilog count, a

smyčka je ukončena. Procesor samozřejmě nepřesouvá obsahy registrů, ale logická

čísla registrů udávaná ve strojovém kódu jsou přemapovávána na jména fyzická ve

fázi REN prováděcí pipeline.

Práce s registry s využitím RSE

Při provádění procedur dochází k obdobné situaci. Sada registrů je rozdělena na

dvě části, a to na statickou a logickou. Statickou část tvoří registry r0 až

r31, které jsou společné pro všechny procedury. Logickou část tvoří registry

r32 až r127, které jsou mapovány na registry fyzické. Pokud procedura potřebuje

nějaké registry pro uložení lokálních proměnných, musí si je naalokovat pomocí

instrukce alloc. Procedura má rozděleny své registry na tři části, jež budeme

zvát třídy (viz obrázek):

- vstupní registry (v podstatě jsou též lokální)

- lokální registry

- výstupní registry

Jednotlivé třídy registrů jsou řazeny za sebou, počínaje registrem r32. Vstupní

registry procedury jsou současně výstupními registry volající procedury, takto

si procedury předávají parametry. Lokální registry slouží výhradně pro pomocné

výpočty. Soubor lokálních a výstupních registrů se nazývá rám.

Procedura na svém počátku provede alokaci registrů se třemi parametry, a to

počtem vstupních, lokálních a výstupních registrů, přičemž vstupní registry se

překrývají s výstupními registry volající procedury. Samozřejmě, že při postupu

volání do hloubky může být prostor fyzických registrů brzy vyčerpán, z toho

důvodu mohou být celé rámy odkládány do paměti.

Obdobně jako se u x86 na zásobník ukládají jednotlivé registry, tak u IA-64 se

ukládají na zásobník celé rámce. Velký rozdíl je také v tom, že ukládání na

zásobník na x86 je explicitně řízeno prováděným kódem, na IA-64 nikoliv. Vrchol

zásobníku určuje registr BSP (base stack pointer). Ukládání rámce může trvat

relativně dlouho, proto je prováděno asynchronně a nemůže se o něj v žádném

případě starat software, nýbrž přímo jednotka RSE (Register stack engine, je

popsána v odstavci Vykonávání instrukcí). Provedení instrukce alloc tedy

nezaručuje, že jsou naalokované registry platné. Proto musí aplikace vždy

zkontrolovat, zda jsou registry připraveny. K tomuto účelu slouží instrukce

flushrs. Tato instrukce zastaví provádění programu do té doby, než je na

zásobníku uloženo tolik rámců z fyzických registrů, kolik jich je třeba na

splnění daného alokačního požadavku. Může ale nastat i opačný případ, kdy při

návratu z procedury logické registry volající procedury ještě nejsou uloženy ve

fyzických registrech. Proto byl vytvořen podobný mechanismus, kdy pro návrat do

volané procedury program provede instrukci br.ret. Tato instrukce zastaví

provádění programu do doby, než budou příslušné registry volající procedury

nataženy zpět ze zásobníku.

Spolehlivost a další parametry

Při realizaci Itania byl kladen důraz na spolehlivost, neboť Intel plánuje

nasazení tohoto procesoru i do „mission critical“ prostředí, což jsou typicky

vesmírné sondy, jaderné elektrárny, případně systémy zajišťující chod burzy

apod. Z důvodu zachování maximální rychlosti je L1 cache jištěna paritou,

stejně jako Tag L2 cache. Paritou je jištěna i příkazová / adresní část jak

frontside, tak backside sběrnice. L2 Data cache a datové části obou sběrnic

jsou jištěny kódem ECC. Pro L2 Data cache byl zvolen kód single error

correcting, double error detecting. Pro sběrnici do hlavní paměti pak kód na

detekci čtveřice sousedních chybných bitů, což je vhodné při čtení z jednoho 4

DRAM čipu. Díky použití různých metod Itanium snese relativně mnoho

hardwarových chyb, což je zásadní zejména pro výše zmíněnou sféru výkonných

serverů, pro něž je primárně určeno. Chyby opravené ECC způsobí pouze několik

taktů prodlevy a jsou pro software transparentní, procesor může generovat také

přerušení s malou prioritou pro zaznamenání chyby.

I když bude Itanium vyráběno 0,18mm technologií, stejně plocha jeho čipu

dosáhne asi 300 mm2 a dodáván bude v po tepelné stránce vylepšeném plastickém

pouzdře s asi 700 vývody, což si vynutila široká sběrnice do hlavní paměti.

Procesor pracuje při napětí 3,3 V. Počítá se s tím, že tepelný výkon na 800 MHz

bude minimálně 60 W. Ostatně prohlédnete-li si kteroukoliv prezentaci

praktického nasazení tohoto procesoru, téměř vždy najdete rozsáhlé pojednání o

realizaci tepelných zón ve skříni počítače i odvod tepla z bloku procesoru.

Přímo na čipu má Itanium umístěny tepelné senzory. Je to pochopitelné, problém

s chlazením poroste úměrně tomu, jak jej bude výrobce nutit k vysokým pracovním

frekvencím. Co se týče samotných testovacích konfigurací, Intel a jeho OEM

partneři zkoušejí systémy vybavené dvěma až 64 procesory.

Závěr

Procesor Itanium zásadním způsobem mění poměr mezi procesorem a kompilátorem.

Řeší tak zásadní problém, před který se konstruktéři moderních procesorů

dostali narůstání komplexnosti architektury v důsledku nikoliv snahy o zlepšení

techniky samotných výpočtů, jako spíše pro analýzu toku instrukcí, bookkeeping

pro překlad z původního sledu instrukcí na nový a zpět, a podobně.

Itanium ukazuje, že to lze řešit i jinak, ale ani v něm se konstruktéři

nevyhýbají tomu vložit do hardwaru dynamické sekce, pokud jsou nutné, např.

predikce skoků, předcházení prodlevám při čtení operandů atd. Implementace EPIC

filosofie, predikátování a spekulativní řízení jsou velkým přínosem pro

uplatnění ILP a redukci počtu cyklů při provádění kódu zpracovávajícího celá

čísla.

Ze softwarové stránky je vidět usilovná snaha výrobce zajistit si maximální

podporu nejen ze sféry komerčních výrobců důkazem toho je, že v současné době

(duben 2000) jsou na Itaniu úspěšně otestovány čtyři operační systémy (včetně

Windows a Linuxu) a některé podnikově důležité aplikace databáze, grafika.

Většina z dále uvedených operačních systémů určených pro IA-64 má plánované

první „ostré“ verze až někdy v druhé polovině tohoto roku, alfa-, případně

beta-verze však mají v současné době snad již všichni. Na první pohled vidíme

zástupce všech důležitých výrobců OS: jsou to Windows 64, HP-UX, Linux

Trillian, Monterey (IBM, SCO), Modesto (Novell) a Solaris (SUN).

Ačkoliv Itanium bude mít na trhu zdatné konkurenty, jako jsou Alpha 21264,

UltraSPARC-3 nebo Athlon, pokud Intelu vyjde předpoklad se sázkou na převedení

některých náročných úloh na kompilátory a nasazení vysokého počtu funkčních

jednotek, pak budeme svědky nové etapy směru vývoje moderních procesorů.

Doporučená literatura

Na tomto malém prostoru nelze ani v nejmenším vytvořit komplexní pohled na

Itanium a IA–64. Např. jen pojednání, jak psát optimalizovaný kód pro IA-64

nebo popis programovacího modelu pro výpočty v plovoucí řádové čárce, by si

vyžádalo větší rozsah tohoto článku. Domníváme se však, že skutečný zájemce

sáhne po dalších zdrojích, z nichž jsme ostatně čerpali i my.

IA-64 Detailed Tutorial, CERN 1999

IA-64 Architecture Software Developer\s Manual, Vol. 1–4, Intel, leden 2000

IA-64 Assembly Language Reference Guide, Intel, leden 2000

http://developer.intel.com/vtu­ne/cbts/ia64

http://developer.intel.com/design/IA-64/index.htm

http://www.x86.org

Monterey: www.projectmonterey.com

HP/UX: www.software.hp.com/products/

IA64/index.html

Modesto: www.novell.com/whitepapers/iw/

modesto.html

Linux: www.linuxia64.org

IEEE Computer, červenec 1998

Microprocessor Report 12,13/99