architektura - kapitanat.pl

Transkrypt

architektura - kapitanat.pl
architektura
IA-64
Maciej Mazur
Wstęp.......................................................................................................................................... 3
Główne idee IA-64 ..................................................................................................................... 3
Zgodność z IA-32 oraz PA-RISC ___________________________________________________ 3
64 bitowość ____________________________________________________________________ 4
Współpraca Kompilatora z procesorem_______________________________________________ 5
Równoległość wykonania instrukcji (ILP) ____________________________________________ 5
Mechanizmy zastosowane w architekturze IA-64 .................................................................... 6
EPIC czyli paczkowanie instrukcji __________________________________________________ 6
Cechy zestawu instrukcji __________________________________________________________ 9
Rejestry ______________________________________________________________________ 11
Rejestry rotujące _______________________________________________________________ 22
Spekulatywne wykonywanie kodu oraz spekulatywny dostęp do pamięci ___________________ 24
Skoki (zapobieganie, przewidywanie, unikanie) _______________________________________ 27
Pierwszy procesor IA-64 Itanium ........................................................................................... 29
Rozkład rejestrów w Itanium______________________________________________________ 29
Instrukcje procesora Itanium ______________________________________________________ 32
Otoczenie procesora Itanium ______________________________________________________ 32
Przewidywania dotyczące procesorów opartych na IA-64 ..................................................... 32
Porównanie Itanium z innymi procesorami ___________________________________________ 32
Oprogramiowanie dedykowane dla IA-64____________________________________________ 32
Kolejne procesory IA-64 _________________________________________________________ 33
Słownik..................................................................................................................................... 34
Zakończenie ............................................................................ Błąd! Nie zdefiniowano zakładki.
2
Wstęp
W roku 1988 firmy Intel oraz HP nawiązały współpracę, której owocem jest nowa
architektura procesora nazwana IA-64. Procesory z tej rodziny, są w pełni 64 bitowe i
zapewniają pełną kompatybilność z architekturami IA-32 znanej także pod nazwą x86, oraz
PA-RISC. Pierwszym procesorem który ma być stworzony na bazie IA-64 jest Itanium,
(zwany dawniej Meced) który przygotowywany jest przez firmę Intel.
Architektura Ia-64 została zaprojektowana, aby przezwyciężyć dotychczasowe ograniczenia
stworzone przez tradycyjne architektury, oraz nie stawiać barier w przyszłości. Aby to
osiągnąć IA-64 ma w sobie całą listę innowacji technicznych wspomagających równoległość
wykonywania instrukcji. Te innowacje to przede wszystkim: spekulatywne wykonywanie
kodu, predykaty, wielka liczba rejestrów, rotujące rejestry, zaawansowana technologia
przewidywania i zapobiegania skokom, oraz wiele innych. W tej architekturze wykorzystuje
się 64 bitowe adresowanie pamięci, co jest wymagane przy rosnącym zapotrzebowaniu na
pamięć przez obecne programy. Architektura IA-64 posiada innowacyjną jednostkę
zmiennoprzecinkową oraz inne udogodnienia, aby zaspokoić zapotrzebowanie na wielką moc
obliczeniową stawiane przez takie aplikacje jak CAD/CAE lub naukowe aplikacje
numeryczne
Architektura IA-64 jest bardzo nowoczesną architekturą, chociaż czerpie dużo z istniejących
już rozwiązań.
IA-64 cechuje się własnościami, które pozwalają utrzymać osiągi na wysokim poziomie,
jednocześnie usuwają bariery, dla późniejszego zwiększenia osiągów. Architektura IA-64
opiera się na następujących zasadach:
• Równoległe wykonanie kodu
- mechanizm współpracy pomiędzy kompilatorem, oraz procesorem
- grupowanie zasobów dla zwiększenia korzyści równoległości instrukcji
- duża liczba różnorodnych rejestrów
- wsparcie dla wielu zespołów wykonujących
• Cechy które podnoszą korzyści równoległego wykonywania instrukcji
- spekulatywne wykonywanie kodu
- predykaty (które usuwają skoki)
- programowe "unrolowanie" krótkich pętli
• Inne ważne cechy które podwyższają efektywność wykonywania programów
- specjalne wsparcie dla modularności oprogramowania
- wysoka wydajność jednostki zmiennoprzecinkowej
- instrukcje typowo multimedialne
Główne idee IA-64
Zgodność z IA-32 oraz PA-RISC
Architektura IA-64 została tak zaprojektowana, aby była kompatybilna dotychczasowymi
rozwiązaniami takimi jak IA-32 oraz PA-RISC. Ponieważ architektura PA-RISC jest w miarę
nowoczesną architekturą, nie mającą takiego balastu starych rozwiązań jak IA-32, to nie ma
większych problemów z zachowaniem kompatybilności. Większy problem to zgodność z IA32. Pamiętając, że pierwsze procesory tego typu były projektowane w zamierzchłych jak na
dzisiejsze technologie czasach, niosą one ze sobą wiele rozwiązań z którymi nie da się w
prosty sposób utrzymać kompatybilności. Inżynierowie projektujący architekturę IA-64
3
zdecydowali się na swego rodzaju sprzętowy emulator. Procesor z rodziny IA-64 może być
przestawiony w tryb pracy IA-32 i zachowywać się zupełnie jak procesor z serii x86. Za
punkt odniesienia uznano procesor Pentium III Xeon.
Trzy specjalne instrukcje oraz przerwania zostały zdefiniowane, aby zapewnić przestawienie
się procesora pomiędzy zestawem instrukcji IA-32 a IA-64. Te instrukcje to:
- jmpe (instrukcja IA-32) – Skok do jakiejkolwiek instrukcji IA-64, czyli zmiana
zestawu instrukcji na IA-64
- br.ia (instrukcja IA-64) – Skok do instrukcji IA-32, zmiana zestawu instrukcji na
IA-64
- przerwania które przestawiają procesor do stanu IA-64 i obsługują w tym trybie
żądanie.
- rfi (instrukcja IA-64) – "return form interruption" powrót z przerwania. Instrukcja ta
została zdefiniowana do powrotu do zestawu IA-32 lub IA-64
Instrukcje jmpe oraz br.ia dostarczają niskopoziomowego mechanizmu do przejścia
pomiędzy zestawami instrukcji. Te dwie instrukcji są zwykle włączane do kodu, aby
zaimplementować potrzeby linkowania oraz wywoływania dynamicznego lub statycznego
zlinkowanych bibliotek.
Problem odpowiednich rejestrów rozwiązano w dwojaki sposób. Główne rejestry zostały
dodane specjalnie dla trybu IA-32, chociaż oczywiście można z nich korzystać w trybie 64bitowym. Rejestry te znajdują się jako odpowiednie Rejestry Aplikacyjne. Dodatkowo
rejestry ogólnego przeznaczenia, oraz zmienno-przecinkowe są odpowiednio mapowane do
pracy w trybie IA-32. Przykładem może być mapowanie rejestrów SIMD, które są mapowane
w rejestrach zmiennoprzecinkowych. Dane każdego 128-bitowe rejestru SIMD znajdują się
fizycznie w dwóch 82-bitowych rejestrach zmiennoprzecinkowych po 64 bity w każdym.
Zarówno Intel jak i Hewlett-Packard podkreślają, iż jedynie programy kompilowane z myślą
o IA-64 będą w stanie spożytkować nowe cechy architektury, jednakże obydwaj producenci
twierdzą iż programy napisane z myślą o istniejących już systemach będą działać na IA-64.
Dla dodatkowej pewności HP oferuje specjalne narzędzia pod nazwą Software Transition Kit.
Ten zespół programów umożliwia przetestowanie istniejącego oprogramowania pod kątem
używalności na IA-64, a także ewentualne jego uzdatnienie. Narzędzie to jak na razie jest
pomyślane do pracy z programami kompilowanymi z języków C, C++, Fortran, oraz Cobol.
Microsoft zapewnia, iż w nowym systemie Windows dla IA-64, (który ma się ukazać w tym
samym terminie co pierwszy procesor IA-64) będą działać wszystkie programy napisane dla
dzisiejszego Windowsa, a aby wykorzystać cechy nowego procesora należy tylko ponownie
skompilować źródła bez żadnych poprawek.
64 bitowość
Dzisiejsze 32-bitowe architektury najczęściej mogą adresować do 4 GB pamięci operacyjnej.
Jest też tak w przypadku 32-bitowych produktów Intela. To całkowicie wystarcza przy
dzisiejszych wymaganiach głównych aplikacji. Jednak rozwój oprogramowania szczególnie
wielkich baz danych kontynuuje wzrost zapotrzebowania na pamięć. Szacuje się iż, rozmiar
pamięci operacyjnej będzie szybko zwiększał się w kolejnych generacjach komputerów. W
odpowiedzi na zapotrzebowanie architektury 64-bitowe zwiększają zdolności systemów do
adresowania wielkich przestrzeni pamięci operacyjnej. Różnica w osiągach może być
widoczna dla aplikacji których zapotrzebowanie na pamięć będzie większe niż owe 4 GB.
Przykładami aplikacji które w najbliższym czasie mogą przełamać taką granicę mogą być
wielkie bazy danych, serwery różnorodnych usług internetowych, oraz nowa linia aplikacji
4
biznesowych. Cena pamięci stale maleje, co powoduje, że wkrótce, będzie opłacalne
posiadanie pamięci operacyjnej liczonej w dziesiątkach gigabajtów. Połączenie takiej ilości
pamięci oraz 64-bitowej szyny adresowej będzie pozwalało na znaczące polepszenie osiągów
w wielu systemach.
IA-64 nie jest pierwszą architekturą która używa 64-bitowego adresowania. Dzisiejsze
RISCowe architektury takie jak HP’s PA-RISC, Sun UltraSPARC, Compaq Alpha, oraz IBM
PowerPC, są już 64-bitowe. Ale „64-bitowość” to tylko element sukcesu, potrzebne jest
również wsparcie do obsługi wielkich rozmiarów pamięci (a to nie tylko szeroka szyna
adresowa). IA-64 będzie posiadała wszystkie potrzebne cechy aby pracować z tak dużą
przestrzenią pamięciową, a cechy te to: dostosowany sprzęt, system operacyjny, oraz
oprogramowanie które będzie potrafiło korzystać z takich zdolności systemu.
Współpraca Kompilatora z procesorem
Kluczową ideą cechującą architekturę IA-64 to przesunięcie wszystkich możliwych zadań z
procesora do kompilatora. Takie podejście daje możliwość takiego przygotowania kodu
wykonywalnego, którego procesor nie będzie musiał już analizować. Dzisiejsze procesory
analizują kod w poszukiwaniu sposobów wykonania go równolegle, lub aby przewidzieć
możliwe w najbliższym czasie skoki. Podejście bazujące na przerzuceniu tych zadań do
kompilatora, powoduje możliwość lepszego przeanalizowania kodu. Kompilator ma do
dyspozycji kod źródłowy, a nie tylko wykonywalny, oraz dużo więcej czasu na obliczenia.
Mechanizmy zastosowane w procesorach są tak skonstruowane, aby praca poświęcona na
analizę była z nawiązką wyrównana przez oszczędności które są poczynione, gdyż inaczej jest
to nie opłacalne. Kompilator nie ma takiego ograniczenia. Jedynym problemem jest właściwe
przekazanie informacji z kompilatora do procesora.
IA zawiera mechanizmy takie jak: pola template w paczkach instrukcji, wskazówki co do
przewidywania skoków, oraz podpowiedzi jakie dane ładować do cache, które pozwalają
kompilatorowi na optymalne przygotowywanie kodu wykonywalnego. Dodatkowo IA
pozwala skompilowanemu programowi na zarządzanie zasobami procesora korzystając z
informacji czasu wykonania. Taki mechanizm pozwala na zminimalizowania opóźnień
systemu związanymi ze skokami oraz niecelnymi zapisami danych do cache.
Każdy zapis oraz odczyt z pamięci w IA ma 2 bitowe pole podpowiedzi w cache, w którym
kompilator koduje przewidywaną częstotliwość dostępu do tej porcji danych. Niektóre dane
które mogą być wykorzystywane tylko raz przez cały czas wykonywania programu, natomiast
inne mogą być potrzebne bardzo często. Pole przewidywanej częstotliwości dostępu służy
właśnie do tego, aby procesor na tej podstawie decydował o ewentualnym załadowaniu części
pamięci do cache. Taka technika pozwala na lepsze zarządzanie pamięcią cache,
zredukowanie chybionych zapisów do pamięci, szczególnie iż w obecnym czasie zwiększają
się dysproporcje pomiędzy szybkością pamięci cache oraz zwykłej.
Równoległość wykonania instrukcji (ILP)
Wzrost osiągów mikroprocesorów osiąga się poprzez zwiększanie częstotliwości zegara, oraz
przez zwiększanie ilości wykonanej pracy w jednym cyklu zegarowym. Procesory IA-64 będą
zwiększać ilość wykonanej pracy w jednym cyklu zegara poprzez możliwość zwiększenia
korzyści z wewnętrznej równoległości wykonywania. Dzisiejsze mikroprocesory już czerpią
korzyści z równoczesnego wykonywania instrukcji. Wiele typów procesorów dynamicznie
planuje wykonanie równoległe obserwując zależności występujące w strumieniu instrukcji.
Taki sposób grupowania instrukcji do równoległego wykonania wyraźnie podwyższa osiągi
5
procesora, ale nie jest oczywiste czy wychodzenie ponad standardowe dzisiejsze cztero
drożne wykonanie jest warte swojego nakładu pracy. Jeśli wierzyć zapewnieniom IA-64
będzie w stanie działać znakomicie powyżej czterokrotnym równoczesnym wykonywaniem.
Będzie to możliwe oczywiście nie z istniejącymi binariami. Taka równoległość jest możliwa
przy pomocy kompilatorów które będą w stanie bardziej dokładnie przeanalizować kod
źródłowy pod kątem równoległego wykonania. Dodatkowo być może bardziej popularne
staną się języki programowania które umożliwiają programiście najbardziej optymalne
zaplanowanie równoległego wykonania. Dzisiejsze języki programowania odzwierciedlają
naturę konwencjonalnych komputerów. Problemy które mają naturę równoległą (na przykład
operacje na macierzach) są dzisiaj reprezentowane poprzez wielokrotnie zagnieżdżone pętle.
Zaawansowane kompilatory dla maszyn z równoległym przetwarzaniem (na przykład
dzisiejsze superkomputery) potrafią z powrotem przekształcić takie pętle na równoległa
reprezentację problemu. Umożliwia to znaczne zyski na szybkości w komputerach
równoległych lub wektorowych. Nic jednak nie da takich pożytku z równoległego wykonania
jak generowanie binariów z kodu źródłowego w którym równoległość jest już jasno
wyrażona. Nie powodowałoby to niepożądanego zjawiska polegającego na linearyzowania
problemów przez programistę, po czym te problemy zostają powtórnie (z tym, że już
maszynowo) przekształcane do pierwotnej struktury. Taka prawidłowość oczywiście tyczy się
również architektury IA-64. Co prawda Intel oraz HP będą prowadzić wspaniałe wsparcie dla
istniejącego oprogramowania, poprzez sprzętową zgodność, ale nie ma co się spodziewać ze
to oprogramowanie będzie czerpać większe korzyści z równoległości zaimplementowanej w
IA-64 (co tyczy się nie tylko równoległości, ale również innych zaawansowanych
mechanizmów zawartych w IA-64). Kod źródłowy zrekompilowany dla potrzeb IA-64 będzie
zapewne działać dużo lepiej, jednakże można oczekiwać iż tylko wyraźne wyrażenie
równoległości przez programistę będzie powodowało pełne wykorzystanie równoległości w
IA-64.
Instruction Level Parallelism (ILP) czyli równoległość wykonywania instrukcji, to możliwość
wykonywania wielu instrukcji w tym samym czasie. Architektura IA-64 pozwala na
grupowanie niezależnych od siebie instrukcji w paczki (po 3 instrukcje). Dla zwielokrotnienia
efektu równoległości można przygotować wiele paczek dla jednego cyklu zegarowego. O
takie przygotowanie kodu do wykonania troszczy się kompilator. Wyposażony w dużą liczbę
zasobów do równoległego wykonywania instrukcji, procesor IA-64 pozwala kompilatorowi
zaplanować pracę w przód, oraz zaplanować równoczesne wątki do obliczeń. Kompilatory dla
tradycyjnych architektur są często ograniczone w swoich możliwościach wykorzystania
informacji o możliwym równoległym wykonywaniu kodu, ponieważ te informacje nie zawsze
musiały być prawdziwe. IA-64 pozwala kompilatorowi na wykorzystanie tych informacji, bez
obawy o poprawność wykonania programu. W tradycyjnych architekturach procedury
ograniczają osiągi dopóki potrzebne rejestry nie zostaną zwolnione i zostaną tam załadowane
potrzebne dane. Natomiast IA-64 pozwala kompilatorowi na takie przygotowanie kodu, że
operacje na rejestrach można zaplanować wcześniej.
Mechanizmy zastosowane w architekturze IA-64
EPIC czyli paczkowanie instrukcji
Po ostatniej rewolucji w dziedzinie zestawu instrukcji jaka nastąpiła w roku 1980 kiedy to
powstał Reduced Instruction Set Computing (RISC), Intel oraz Hewlett-Packard przygotowali
6
nowy zestaw instrukcji IA-64. Zbliżyli się oni tym sposobem do ideału procesora
wykonującego operacje równolegle.
Główną ideą przyświecającą technologii EPIC jest grupowanie instrukcji w paczki, która to
paczka jest ładowana cala w jednym takcie zegara. Co prawda idea grupowania instrukcji w
paczki zastosowana w IA-64 znana już była z procesorów typu VLIW, jednak metoda
zastosowana w architekturze IA-64 wydaje się być wiele lepsza.
Procesory VLIW (Very Long Instruction Word) były pierwszą architekturą, opracowaną z
założeniem, że kod maszynowy ma być w taki sposób przygotowany, że instrukcje mają sobie
wzajemnie nie przeszkadzać. Takie instrukcje były grupowane w paczki. Istniały dwa
rozwiązania, pierwsze procesory miały ustaloną długość paczki, w kolejnych długość paczki
zmieniała się. Procesory tego typu nie upowszechniły się ponieważ na drodze stanęły
problemy które architektura VLIW nie była w stanie przezwyciężyć.
Głównym problemem był nadmierny rozrost kodu spowodowany niemożnością grupowania
instrukcji które są współzależne i jedna korzysta z wyników drugiej. Problemom tego typu
zapobiegano poprzez stosowanie szczelin paczkach. Tak więc w jednym cyklu zegarowym
procesor dostawał w najgorszym przypadku jedną instrukcję, a dalej pustkę, gdyż długość
paczki była stała. Zastosowano inne rozwiązanie tego problemu, a mianowicie zmienną
długość paczki. Niestety pojawił się kolejny problem, nie wiadomo czy nie poważniejszy od
poprzedniego. Przy zmiennej ilości instrukcji w paczkach kompilator tak układał instrukcje,
że były one dedykowane dla konkretnego procesora. Zdarzało się tak zwykle przy dużych
paczkach, z dużą ilością instrukcji. Instrukcje te niekiedy były konkretnie dedykowane do
określonych jednostek wykonawczych w procesorze. To zmuszało do rekompilacji
programów nawet dla kolejnego procesora z serii. Dodatkowo wykluczone zostało przez to
przetwarzanie oparte na wielu procesorach bez uprzedniej rekompilacji kodu. Obecnie
technologię VLIW stosuje się raczej tylko w specjalizowanych procesorach (na przykład
Texas Instruments DSP C6201), lub technologia ta jest stosowana tylko w specjalnych
jednostkach wewnątrz procesorów.
IA-64 idzie dalej niż poprzednie (CISC, RISC, VLIW) zestawy instrukcji i niosąc ze sobą
nowe cechy które zostały nazwane EPIC (czyli Explicitly Paralel Instruction Computing) co
po polsku można przetłumaczyć Przetwarzanie Wyraźnie Równolegle. Ta strategia powinna
dać procesorom serii IA-64 palmę pierwszeństwa wśród wszystkich innych zestawów
instrukcji. Co prawda technika Epic jest podobna do VLIW, ale IA-64 redukuje dwie
niedogodności czyli brak skalowalności oraz duże rozrost kodu powstającego przy
kompilowaniu programów dla procesorów VLIW. Owe problemy pokonano zaopatrując
procesory oparte na architekturze IA-64 w takie cechy jak: bardzo duża liczba rejestrów
(około 4 razy więcej niż typowy procesor RISC) bezpośredni dostęp do wszystkich rejestrów
przez oprogramowanie, co eliminuje potrzebę mapowania rejestrów, oraz przyspieszony
dostęp do cache. Kiedy jest zapotrzebowanie na dostęp do danych spekulatywne ładowanie
może całkowicie zniwelować opóźnienie spowodowane przez dostęp do cache, nawet jeśli w
międzyczasie odbywają się skoki. Poza tym niektóre skoki mogą być w ogóle wyeliminowane
całkowicie poprzez stosowanie predykatów.
Główną rolę w metodzie EPIC odgrywa kompilator. Nowoczesny kompilator analizuje
program pod kątem wyszukiwania przeszkód dla równoległego wykonywania instrukcji, a
później układa instrukcje dla optymalnego wykorzystania procesora. Dzieje się to już w
niektórych dzisiejszych kompilatorów dla superskalarnych procesorów, jednak większość
obecnych kompilatorów dla architektur CISC lub RISC przygotowuje kod "szeregowo" nie
analizując powiązań między instrukcjami. Zadanie zaplanowania równoległości pozostaje
7
procesorowi, który ponownie analizuje kod instrukcja po instrukcji, aby w końcu móc
wykonać je równolegle. Dzisiejszy zestaw instrukcji typu CISC czy RISC nie daje
możliwości na transfer danych dotyczących sposobu równoległego wykonania od kompilatora
do procesorem, tak aby zaplanować wcześniej sposób wykonania. Istnieje wiele wad takiego
rozwiązania, po pierwsze kompilator ma wiele czasu na poszukiwanie najlepszego sposobu, a
po drugie praca wykonywana by była tylko raz przy tworzeniu kodu maszynowego.
Przeniesienie tych zadań do procesora powoduje, iż praca musi być wykonywana przy
każdorazowym wykonaniu programu, co gorsza niekiedy wielokrotnie. Dodatkowo procesor
traci na dodatkową analizę swoją cenną moc obliczeniową, a co za tym idzie marnuje zyski z
równoległego wykonania.
Główną ideą przyświecające technologii EPIC jest grupowanie instrukcji w paczki (bundles).
Uniknięto tutaj problemu nadmiernego rozrostu kodu stosując unikalny format paczki w
której znajdują się instrukcje. Paczka ma długość 128 bitów i zawiera 3 instrukcje oraz tzw.
template. Każda instrukcja ma długość 41 bitów, template natomiast 5 bitów.
Format paczki instrukcji
127
87 86
46 45
5 4
0
instrukcja 1
instrukcja 2
instrukcja 3
template
41
41
41
5
Dane zawarte w template sygnalizują czy instrukcje w paczce mogą być wykonywane
jednocześnie, lub czy jest przymus wykonanie jednej lub więcej szeregowo w związku np. z
konfliktem rejestrów. Template informuje jednocześnie czy paczka może być wykonana
jednocześnie z następną z kolei paczką. Daje to możliwość układania paczek w łańcuchy
tworząc grupy instrukcji dowolnej długości. Ściśle rzecz biorąc zdefiniowany jest tak zwany
stop który odgranicza instrukcje które mogą być wykonane razem od tych które mają czekać
na zwolnienie zasobów. I tak jeśli wszystkie bity w template są w stanie niskim to nie ma
żadnych „stopów” na przeszkodzie, jeśli wartość pola template wynosi 1 to stop znajduje się
po 3 instrukcji (następna paczka musi czekać), jeśli wynosi 2 to stop znajduje się po 2
instrukcji i tak dalej analogicznie. Ogólna zasada mówi, że jeżeli najmniej znaczący bit w
template ma wartość zero to paczka nie może być wykonywana równolegle z następną w
kolejce. Dodatkowo informacje w template informują o typie jednostki wykonującej tą
instrukcje. Jeśli wartość pola template wynosi 0 to znaczy, że pierwsza instrukcja ma być
przetwarzana przez jednostkę zarządzającą pamięcią, a druga oraz trzecia przez jednostkę
arytmetyki stałoprzecinkowej. Niestety na 5 bitach nie da się zakodować wszystkich
możliwości ułożenia stopów, wraz z określeniem jaka jednostka wykonawcza ma zajmować
się daną instrukcją.
Tabela przedstawiająca zaimplementowane kombinacje:
Template
0
1
2
3
4
5
6
00
01
02
03
04
05
06
instrukcja 1
instrukcja 2
instrukcja 3
M
M
M
M
M
M
I
I
I
I
L
L
I
I
I
I
X
X
8
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
07
08
09
0A
0B
0C
0D
0E
0F
10
11
12
13
14
15
16
17
18
19
1A
1B
1C
1D
1E
1F
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
F
F
M
M
I
I
B
B
I
I
I
I
I
I
F
F
B
B
B
B
B
B
M
M
B
B
M
M
B
B
B
B
M
M
F
F
B
B
legenda:
M – (Memory unit) jednostka zarządzająca pamięcią
I – (Integer ALU) stałoprzecinkowa jednostka arytmetyczno-logiczna
F – (Floating-point unit) zmiennoprzecinkowa jednostka arytmetyczno-logiczna
B – (Branch unit) jednostka wykonująca skoki
L – (Long Imidate Integer) jednostka stałoprzecinkowa, ale instrukcje tak zaznaczone
zajmują dwa miejsca w paczce, są to instrukcji rozszerzone
nieużywane wartości pola template, są to wartości zarezerwowane, ich wystąpienie
powoduje Generalny Błąd Ochrony
„stop” po danej instrukcji
Taki układ danych w paczce jaki posiada IA-64 jest bardziej złożony niż czysty VLIW
jednakże pozwala na stworzenie rodziny kompatybilnych binarnie procesorów, a takie
rozwiązanie jest dużo lepsze niż ewentualne późniejsze dodawanie specjalnych układów w
procesorach które będą transformować kod od nowych wymagań.
Paczki instrukcji w programie wykonywalnym są ułożone od najmniejszego do największego
adresu. Instrukcje w paczce o mniejszym adresie są uważane za poprzedzające instrukcje z
paczki o większym adresie. Kolejność bajtów w każdej paczce w pamięci to tzw. little-endian.
Cechy zestawu instrukcji
Każda instrukcja jak to zostało zauważone przy okazji omawiania paczkowania instrukcji ma
długość 41 bitów. Istnieją jednakże tak zwane instrukcje rozszerzone (extended) które
9
zajmują 82 bity czyli dwa miejsca w paczce instrukcji. Instrukcje w IA-64 są podzielone na 6
kategorii. Każda instrukcja może być wykonana przez jeden lub więcej typów jednostek
wykonawczych.
Tabela przedstawiająca powiązania pomiędzy typem instrukcji a jednostką wykonawczą, do
która wykonuje daną instrukcję.
Typ instrukcji
Typ jednostki wykonawczej
Opis
A
stałoprzecinkowa
arytmetyczno-logiczna
stałoprzecinkowa lub zarządzająca
pamięcią
I
stałoprzecinkowa, nie
arytmetyczno-logiczna
stałoprzecinkowa
M
operująca na pamięci
zarządzająca pamięcią
F
zmiennoprzecinkowa
zmiennoprzecinkowa
B
skok
zarządzająca skokami
rozszerzona
stałoprzecinkowa
L+X
Ogólnie format instrukcji kodowany za pomocą 41 bitów można przedstawić za pomocą
następującego schematu:
0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0
opcode
misc
pole3
pole2
pole1
qp
0-5
qp – (qualifying predicate register source) - pole zawierające adres odpowiedniego
rejestru predykatów
6-12 pole1 – pole które jest w większości typów instrukcji wykorzystywane do
przechowywania adresu źródłowego lub docelowego odpowiedniego
rejestru (ogólnego przeznaczenia lub zmiennoprzecinkowego). Inaczej jest
w przypadku instrukcji skoków, pole to jest wtedy dodatkowo podzielone.
Pierwsze 3 bity zajmuje zakodowany typ skoku, lub adres źródłowy albo
docelowy rejestru skoków, następne 3 bity są ignorowane, a ostatni bit
pola zawiera kod operacji wcześniejszego pobierania. Jeszcze inaczej
interpretuje się to pole w przypadku instrukcji porównania. Wtedy
pierwsze 6 bitów to adres docelowego rejestru skoków, a ostatni bit kod
komplementarnej relacji porównania
13-19 pole2 – pole to jest przez większą część instrukcji używane do przechowywania
adresu źródłowego lub docelowego odpowiedniego rejestru (ogólnego
przeznaczenia lub zmiennoprzecinkowego). W przypadku instrukcji
alokacji w polu tym zapisana jest wielkość ramki. W tym polu mogą się
także znajdować w zależności od instrukcji takie informacje jak: pozycja
bitu testowego, lub bitu uzyskanego, przewidziana najbliższa maska
20-26 pole3 – pole to jest przez większą część instrukcji używane do przechowywania
adresu źródłowego lub docelowego odpowiedniego rejestru (ogólnego
przeznaczenia, zmiennoprzecinkowego lub aplikacyjnego). Instrukcje
10
multimedialne wykorzystują to pole do zakodowanie stanu licznika
przesunięć. Może być to pole także wykorzystane do zapisania najbliższej
przewidzianej maski, pozycji bitu testowego
27-36 misc – pole różnego przeznaczenia, w tym polu mogą znajdować się najróżniejsze
informacje. Przykładem może być: rozszerzenie pola opcode, różne flagi
wykorzystywane przez instrukcje, licznik przesunięć, podpowiedzi przy
instrukcjach skoku, itp.
37-40 opcode – (major opcode) główny kod instrukcji, opisany niżej dokładniej
Każde 4 ostatnie bity (37:40) w instrukcji to tak zwany główny kod instrukcji (major opcode).
główny
kod
instrukcji
0
00
1
01
2
02
3
03
4
04
5
05
6
06
7
07
8
08
9
09
10
0A
11
0B
12
0C
13
0D
14
0E
15
0F
I/A
M/A
Misc
mem mgnt
mem mgnt
Deposit
Shift/Test bit
MM Mpy/Shift
ALU/MM ALU
Add Imm
Int Ld +Reg/getf
Int Ld/St + Imm
FP Ld/St+Reg/setf
FP Ld.St+lmm
ALU/MM ALU
Add Imm
Compare
Compare
Compare
Compare
Compare
Compare
typ instrukcji
F
B
L+X
FP misc
FP misc
Misc/indi branch
indirect call
Nop
misc
FP Compare
FP Class
IP-rel branch
IP-relative call
movl
fma
fma
fms
fms
fnma
fnma
fselect/xma
Nieużywane pola głównego kodu (czyli puste miejsca w tabeli) można interpretować na trzy
sposoby:
instrukcja jest interpretowana jako NOP
zarezerwowana wartość pola, wystąpienie takiej wartości powoduje
generowanie błędu
generowanie błędu, jeśli rejestr predykatowy specyfikowany przez pole qp
instrukcji (bity 0:5) ma wartość 1, lub interpretowanie instrukcji jako NOP w
przeciwnym wypadku
Rejestry
Architektura IA-64 jest tak pomyślana aby większość zasobów procesora udostępniać
bezpośrednio oprogramowaniu. Nie jest inaczej z rejestrami. Ilość rejestrów jest jedną z
kluczowych cech IA-64 która odróżnia tą architekturę od procesorów IA-32, a także od
procesorów RISCowych. Co prawda nowe procesory RISCowe mają już dużą fizyczną liczbę
rejestrów, ale i tak liczba rejestrów pomyślana dla IA-64 jest dużo większa. Istnieje wiele
11
zalet dużej liczby rejestrów, główną zaletą jest to iż nie trzeba się często odwoływać do
pamięci operacyjnej. Kompilator ma dostęp do całego zestawu rejestrów, co umożliwia mu
śmielszą optymalizację kodu. Przykładem może być technika „wyrolowywania” pętli. W
porównaniu z IA-32 duży zestaw rejestrów zmiennoprzecinkowych powiada dodatkową
zaletę, a mianowicie eliminuje niepożądany mechanizm stosu zmiennoprzecinkowego. W
programach dla x86 większość operacji zmiennoprzecinkowych mogło operować jedynie na
szczycie ośmioelementowego stosu, co zmuszało na częste używanie bezcelowego w IA-64
instrukcji fxch (exchange witch top of stack) czyli wymiany szczytu stosu rejestrów. Już
procesory które mają tylko 32 rejestry zmiennoprzecinkowe nie doznają tej niedogodności, a
pierwsza implementacja IA-64 ma nieć tych rejestrów aż 128. Wadami wielkiej liczby
rejestrów są: zajmowanie fizycznie dużej ilości miejsca w procesorze, ale nie wydaje się to
znaczącą wadą, gdyż pierwsza implementacja IA-64 będzie wykonana w technologii 18
mikronów. Główną wadą takiej ilości jest zwiększenie długości każdej instrukcji związanej z
adresacją rejestrów.
Przegląd rejestrów dostępnych w architekturze IA-64:
Rejestry Ogólnego Przeznaczenia GR
(General Purpose Registers) Są to 64-bitowe rejestry które mogą być wykorzystywane do
przechowywania wszystkiego rodzaju danych. Są one jednak zwykle używane przy
obliczeniach stałoprzecinkowych, oraz multimedialnych. Rejestry te są podzielone na dwie
części statyczną oraz stosową. Część statyczna zajmuje jedną czwartą całego zestawu jest
dostępna bezpośrednio przez oprogramowanie. Część stosowa zajmująca pozostałą pulę to
rejestry rotujące są one dostępne poprzez tzw. rejestry RRB (Rotating Register Base, zwane
także Register Rename Base) które wskazują od którego numeru rejestry stosowe są wolne i
można z nich korzystać. Pierwszy rejestr ogólnego przeznaczenia jest rejestrem specjalnym i
jest tylko do odczytu, ma on zawsze wartość 0. Próba zapisu danych do rejestru zerowego
powoduje wygenerowanie błędu.
Rejestry NaT
(Not a Thing registers) Są to 1-bitowe rejestry z których każdy jest dodatkiem do
odpowiedniego rejestru ogólnego przeznaczenia. Jeden bit zawarty w tych rejestrach ma za
zadanie informować czy dane zawarte w rejestrach ogólnego przeznaczenia są poprawne.
Wykonywanie spekulatywnych operacji przez procesor IA-64 daje możliwość nietrafnego
załadowania rejestru. Bity NaT informują właśnie o poprawności danych związanym z tym
mechanizmem.
Rejestry Zmiennoprzecinkowe FP
(Floating point registers) Są to 82-bitowe zmiennoprzecinkowe rejestry które są używane przy
obliczeniach zmiennoprzecinkowych. Rejestry te są podzielone na dwie części. Pierwsza
część zajmująca jedną czwartą zestawu nazwana jest częścią statyczną Rejestry od 8 do 31 są
używane w trybie IA-32 jako rejestry zmiennoprzecinkowe, oraz multimedialne znane z
procesorów IA-32. Reszta rejestrów nazwana jest częścią rotująca. Część to jest dynamicznie
przydzielana oprogramowaniu aby przyspieszyć wykonywanie pętli. Pierwsze dwa rejestry są
tylko do odczytu i mają wartość +0.0 oraz +1.0. Jeśli któryś z tych rejestrów jest używany
jako rejestr docelowy jakiejś operacji to generowany jest błąd. Rejestry te nie są wyposażone
w dodatkowe bity typu NaT, jest jednak możliwość sygnalizowania niepoprawności danych
związanych z mechanizmem spekulatywnego dostępu do danych. Specjalna wartość NaTVal
(Not a Thing Value) jest wpisywana do odpowiedniego rejestru gdy dane nie zostały trafnie
przewidziane do załadowania.
12
Format rejestru FP:
81
80
64 63
0
znak
wykładnik
część znacząca
1
17
64
pole znaczące – (significand) w polu tym znajdują się cyfry znaczące liczby. Bit 63 jest
częścią całkowitą liczby, natomiast pozostałe bity są częścią
ułamkowa.
wykładnik – (exponent) w tym przechowywany jest wykładnik liczby. Jeśli wszystkie
bity wynoszą 1 to stan taki interpretowany jest jako nieskończoność. Jeśli
wszystkie bity wynoszą 0, oraz wszystkie bity pola znaczącego są równe
zero, oznacza to iż liczba wynosi 0. Natomiast w przypadku jeśli
wszystkie bity tego pola wynoszą 0 natomiast pole znaczące nie wynosi
zero to stan taki interpretuje tak że liczba jest typu IEEE double-extended
real (pseudo)denormal
znak – (sign) pole to określa czy liczba jest dodatnia (bit wynosi 0) czy ujemna (bit
wynosi 1)
Wartość zawarta w tym rejestrze można wyrazić:
-
przy założeniu, że wykładnik jest różny od zera
(-1)(znak) · 2(wykładnik - 65535) · (część_znacząca[63].część_znacząca[62:0])
-
przy założeniu, że wykładnik jest równy zero
(-1)(znak) · 2(- 16382) · (część_znacząca[63].część_znacząca[62:0])
Rejestry Aplikacyjne AR
(Application Registers) są rejestry różnego przeznaczenia, włączając w to rejestry specjalnego
przeznaczenia, rejestry kontrolne, oraz rejestry, które zostały dodane do architektury IA-64
dla zachowania zgodności z architekturą IA-32. Rejestry aplikacyjne mogą być adresowane
tylko przez jednostkę zarządzającą pamięcią (M-unit) albo przez stałoprzecinkową jednostkę
arytmetyczno-logiczną (ALU).
Tabela przedstawiająca listę wszystkich rejestrów aplikacyjnych:
Numer
rejestru
AR 0-7
AR 8-15
AR 16
AR 17
AR 18
AR 19
Nazwa
Opis
KR 0-7
Rejestry jądra
Zarezerwowane
Rejestr konfiguracji stosu rejestrów
Wskaźnik powrotu
Wskaźnik powrotu dla pamięci
Rejestr kolekcji rejestrów NaT
RSC
BSP
BSPSTORE
RNAT
typ
jednostki
wykorzystuj
ącej rejestr
M
M
M
M
M
M
13
AR 20
AR 21
AR 22-23
AR 24
AR 25
AR 26
AR 27
AR 28
AR 29
AR 30
AR 31
AR 32
AR 33-35
AR 36
AR 37-39
AR 40
AR 41-43
AR 44
AR 45-47
AR 48-63
AR 64
AR 65
AR 66
AR 67-111
AR 112-127
FCR
EFLAG
CSD
SSD
CFLG
FSR
FIR
FDR
CCV
UNAT
FPSR
ITC
PFS
LC
EC
Zarezerwowane
Rejestr kontroli zmiennoprzecinkowej
Zarezerwowane
Rejestr flag aplikacji
Rejestr segmentowy programu
Rejestr segmentowy stosu
Rejestr flag kontrolnych
Rejestr statusu zmiennoprzecinkowego
Rejestr instrukcji zmiennoprzecinkowych
Rejestr danych zmiennoprzecinkowych
Zarezerwowane
Rejestr porównania oraz wymiany
Zarezerwowane
Rejestr kolekcji użytkownika rejestrów NaT
Zarezerwowane
Rejestr statusu operacji zmiennoprzecinkowych
Zarezerwowane
Licznik przedziałów czasowych
Zarezerwowane
Ignorowane
Poprzedni stan funkcji
Licznik pętli
Licznik instrukcji końcowych
Zarezerwowane
Ignorowane
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M
M lub I
I
I
I
I
M lub I
Rejestry jądra (KR 0-7 – AR 0-7)
(Kernel Registers) Osiem dostępnych dla użytkownika rejestrów. Są to rejestry 64 bitowe. Ich
zadaniem jest przekazywanie informacji z systemu operacyjnego do aplikacji. Rejestry te
mogą być czytane przez wszystkie poziomy uprzywilejowania, ale zapisywane mogą być
jedynie przez najbardziej uprzywilejowany poziom. Rejestry KR 0, KR 1, oraz KR 2 są także
używane do trzymania dodatkowych informacji przeznaczonych dla zestawu instrukcji IA-32.
Dzieje się to wtedy kiedy aktywnym jest zestaw instrukcji IA-32.
Rejestr konfiguracji stosu rejestrów (RSC – AR 16)
(Register Stack Configuration Register) Jest to 64-bitowy rejestr używany do kontroli operacji
na stosie rejestrów wykonywanych przez RSE (Register Stack Engine) architektury IA-64.
format rejestru RSC:
63
30 29
rv
34
16 15
loadrs
14
5
rv
11
4
be
1
3
2 1
pl
2
0
mode
2
mode – (tryb) pole to kontroluje w jaki sposób RSE zapisuje oraz odczytuje ramki
na/ze stosu gdy pole to jest ustawione w postaci
00 RSE pracuje leniwie (emforced lazy)
10 oznacza tryb intensywnego odczytu (load intensive)
01 oznacza tryb intensywnego odczytu (stroe intensive)
11 oznacza tryb szybki (eager)
14
pl – (privilege level) pole to określa w jakim poziomie uprzywilejowanie ma pracować
RSE
be – (big endian) pole to kontroluje sposób zapisu oraz odczytu danych przez RSE.
Jeśli bit ten jest ustawiony w pozycji 1 to znaczy że dostęp odbywa się według
kolejności big-endian, natomiast jeśli w pozycji 0 to znaczy, że według kolejności
little-endian
loadrs – pole to jest używane przez instrukcję loadrs do synchronizacji RSE
rv – (reserved) pole zarezerwowane
Wskaźnik powrotu (BSP – AR 17)
(Backing Store Pointer) Jest to 61 bitowy rejestr. Rejestr jest tylko do odczytu, przechowuje
on adres miejsca w pamięci w którym jest zapisane miejsce rejestru GR 32 z aktualnej ramki
stosu. Co prawda rejestr ten zajmuje całe 64 bity, ale 3 bity są ignorowane.
Format rejestru BSP
63
3 2
0
pointer
ig
61
3
Wskaźnik powrotu dla pamięci (BSPSTORE – AR 18)
(Backing Store Pointer for Memoru Strores) Jest to 61 bitowy rejestr. W rejestrze tym
przechowywane są informacje o miejscu pamięci w którym RSE zapisze następną ramkę
stosu.
Format rejestru BSPSTORE
63
3 2
0
pointer
ig
61
3
Rejestr kolekcji rejestrów NaT (RNAT – AR 19)
(RSE NaT Collection Register). Jest to 64 bitowy rejestr który jest używany przez RSE do
tymczasowego przechowywania wartości rejestrów NaT. Dane są do tego rejestru zapisywane
kiedy RSE zapisuje następną ramkę stosu. Bit 63 zawsze przy czytaniu zwraca zero i
ignorowane są wszystkie próby zapisu do niego.
Format rejestru RNAT
63 62
0
ig
RSE NaT Collection
1
63
REJESTRY IA-32 (AR 21-30)
Rejestry IA-32 zostały dodane w celu zapewnienia kompatybilności z architekturą IA-32. Jest
to zestaw rejestrów w których znajdują się rejestry znane z procesorów serii x86.
15
Rejestr FCR (AR 21) – w rejestrze tym znajdują się znane z IA-32 rejestry FCW, oraz
MXCSR.
Rejestr EFLAG (AR 24) – rejestr ten odpowiada rejestrowi o takiej samej nazwie w IA-32
Rejestr CSD (AR 25) – rejestr ten odpowiada rejestrowi o takiej samej nazwie w IA-32 mimo
iż istnieje lekka modyfikacja formatu
Rejestr SSD (AR 26) – rejestr ten odpowiada rejestrowi o takiej samej nazwie w IA-32 mimo
iż istnieje lekka modyfikacja formatu
Rejestr CFLG (AR 27) – w rejestrze tym znajdują się rejestry CR0/CR4 znane z IA-32.
Rejestr FSR (AR 28) – w rejestrze tym znajdują się rejestry FSW, FTW, MXCSR znane z IA32.
Rejestr FIR (AR 29) w rejestrze tym znajdują się rejestry FOP, FIP, FCS znane z IA-32.
Rejestr FDR (AR 30) w rejestrze tym znajdują się rejestry FEA, FDS znane z IA-32.
Rejestr porównania oraz wymiany(CCV – AR 32)
(Compare and Exchange Value Register) Jest to 64-bitowy rejestr który zawiera dane
używane przez instrukcję cmpxchg.
Rejestr kolekcji użytkownika rejestrów NaT (UNAT – AR 36)
(User Nat Collection Register) Jest to 64-bitowy rejestr który jest używany do tymczasowego
przechowywania wartości rejestrów NaT. Dane do tego rejestry są zapisywane kiedy zostają
wykonane instrukcje ld8.fill oraz ld8.spill
Rejestr statusu operacji zmiennoprzecinkowych (FPSR – AR 40)
(Floating-point Status Register). Jest to 64-bitowy rejestr w którym przechowywane są
informacje o operacjach zmiennoprzecinkowych. Za pomocą tego rejestru można
dynamicznie kontrolować te operacje. Rejestr ten jest podzielony na 5 pól, jednym jest pole
które opisuje sposób obsługi błędów, oraz 4 zestawy informacji statusowych (1 główny
zestaw oraz 3 alternatywne).
Format rejestru FPSR:
63
58 57
45 44
32 31
19 18
6 5
0
rv
sf3
sf2
sf1
sf0
traps
6
13
13
13
13
6
traps – (zapadki) bity w tym polu sygnalizują odpowiadające tym bitom błędy będą
generowane
sf0 – (status field 0) główne pole statusu
sf1 – (status field 1) alternatywne pole statusu nr 1
sf2 – (status field 2) alternatywne pole statusu nr 2
sf3 – (status field 3) alternatywne pole statusu nr 3
rv – (reserved ) pole zarezerwowane
Format pola traps:
5
4
3
2
1
0
id ud od zd dd vd
1
1
1
1
1
1
vd – bit w stanie wysokim blokuje wystąpienie błędu IEEE – Invalid Operation
16
dd – bit w stanie wysokim blokuje wystąpienie błędu – Denormal/Unnormal Operand
zd – bit w stanie wysokim blokuje wystąpienie błędu IEEE – Zero Divide
od – bit w stanie wysokim blokuje wystąpienie błędu IEEE – Overflow
ud – bit w stanie wysokim blokuje wystąpienie błędu IEEE – Underflow
id – bit w stanie wysokim blokuje wystąpienie błędu IEEE – Inexact
Każda instrukcja arytmetyczna wykonująca operacje zmiennoprzecinkowe ma specyfikator
pola statusu. Specyfikator ten określa które z 4 pól statusu będzie używane do kontroli nad
daną instrukcją.
Format pola statusu:
12
11
10
9
8
7
6
i
u
o
z
d
v
td
5
rc
4
3
pc
2
1
1
1
1
1
1
1
2
2
1
0
wre ftz
1
1
ftz – (Flush-To-Zero) tryb czyszczenia do zera
wre – (Widest Range Exponent) wielkość wykładnika
pc – (Precision Control) kontrola precyzji
rc – (Rounding Control) kontrola zaokrąglania 00
td – (Traps disabled) tryb w którym zapadki (traps) są zablokowane, nie dotyczy
głównego pola statusu.
v – (invalid operation)
d – (Denornal/unnormal)
z – (Zero divide)
bity te sygnalizują pojawienie się błędu który jest
włączony w polu traps
o – (Overflow)
u – (Underflow)
i – (Inexact)
Licznik przedziałów czasowych (ITC – AR 44)
(Interval Time Counter) Jest to 64 bitowy rejestr w którym liczone są kolejne takty zegara.
Aplikacje mogą bezpośrednio odczytywać ten licznik i w ten sposób dokonywać obliczeń
wykorzystujących pomiar czasu, lub mierzących jakieś osiągi. System może zabronić dostępu
do tego rejestru dla nieuprzywilejowanych aplikacji. Kiedy dostęp jest zabroniony, odczyt
tego rejestru (z poziomów nieuprzywilejowanych) powoduje błąd. Dane do tego rejestru
mogą być zapisywane jedynie przez najbardziej uprzywilejowany poziom. Rejestr ten jest
równoważny rejestrowi TSC (Time Stamp Counter) znanego z IA-32 i może być
odczytywany za pomocą instrukcji rdtsc (read time stamp counter). System może zabronić
dostępu także w przypadku korzystania z trybu IA-32. W tym przypadku kiedy następuje
wykonanie instrukcji rdstc (z poziomów nieuprzywilejowanych) powoduje błąd.
Poprzedni stan funkcji (PFS – AR 64)
(Previous Function State) Rejestr ten zawiera wiele pól, które określają poprzedni stan układu
rejestrów. Wartości do tych pól są kopiowane automatycznie przy wywołaniu z odpowiednich
rejestrów, dla przyspieszenia wywoływań procedur.
17
Kiedy instrukcja br.call jest wykonana pola są inicjowane nowymi wartościami, a
poprzednia wartości PFS są tracone. Kiedy wywoływana jest instrukcja br.ret
odpowiednie pola są z powrotem kopiowane do odpowiednich rejestrów.
Format rejestru PFS
63
62 61
58 57
52 51
38 37
0
ppl
rv
pec
rv
pfm
2
4
6
14
38
pfm – (Previous Frame Marker) jest to odpowiednik Oznaczenia Aktualnej Ramki
Stosu (CFM). Pole to tak jak rejestr CFM jest dodatkowo podzielone na pola:
RRB.PR, RRB.FR, RRB.GR, SOR, SOL, SOF
pec – (Previous Epilog Count) jest to odpowiednik rejestru EC, (nie biorąc pod uwagę
części ignorowanej tego rejestru)
ppl – (Previous Privilege Level) jest to odpowiednik pola pl w rejestrze konfiguracji
stosu rejestrów (RSC). Operacja przywracania wartości z tego pola do
oryginalnego miejsca może spowodować zmianę aktualnego poziomu
uprzywilejowania
rv – (Reserved) pola zarezerwowane
Licznik pętli (LC – AR 65)
(Loop Count) Jest to rejestr 64-bitowy. Rejestr ten wykorzystuje się do zliczania przebiegów
pętli. Wartość zawarta w tym rejestrze jest zmniejszana o 1 przy każdym skoku
wykonywanym w pętli w której jest określona ilość przebiegów.
Licznik instrukcji końcowych (EC – AR 66)
(Epilog Count) Jest to rejestr którego 6 bitów jest używane do zliczania ostatnia część
(epilog) pętli. Epilog jest to ostatnia część pętli w której potok instrukcji nie jest już pełny,
lecz powoli opróżnia się (ostatnia instrukcja pętli została już załadowana). Rejestr ten jest
wykorzystywany w mechanizmie „wyrolowywania” pętli
Format rejestru EC
63
6 5
0
ig
epilog count
58
6
Rejestry Predykatów PR
(predicate registers) są to 1 bitowe rejestry które kontrolują warunkowe wykonywanie
instrukcji oraz skoków. Są one używane do przechowywania rezultatów porównań. Rejestry
predykatów są podzielona na dwie części. Pierwsza jest nazwana statyczną i zajmuje jedną
czwartą całej liczby. Pozostała część rejestrów nazwana jest częścią rotującą. Rejestry te są
dynamicznie przydzielane oprogramowaniu, podczas wykonania pętli. Pierwszy rejestr jest
tylko do odczytu i ma zawsze wartość prawda. Kiedy ten rejestr jest używany jako cel zapisu
jakiegoś wyniku, to wynik ten jest tracony.
18
Rejestry Skoków BR
(Branch registers) są to 64-bitowe rejestry które są używane do specyfikowania docelowego
adresu skoku. Umożliwiają sprawniejsze działanie jednostki przewidywania skoków, oraz
wykonywania skoków.
Wskaźnik Instrukcji IP
(Instruction pointer) Jest to rejestr 64 bitowy. W rejestrze tym przechowywany jest adres
paczki instrukcji w której znajduje się aktualnie wykonywania instrukcja IA-64. Rejestr IP
może być odczytywany bezpośrednio, jednakże nie może być bezpośrednio zapisywany.
Rejestr ten jest inkrementowany, kiedy paczka zostanie wykonana. Rejestr jest inicjowany
nową wartością, w przypadku wykonania skoku.
Oznaczenie Aktualnej Ramki Stosu CFM
(Current Frame Marker) Jest to zespół podrejestrów o łącznej długości 38 bitów. Każda
ramka rejestrów jest powiązana ze rejestrem oznaczenia ramki. W tym rejestrze
przechowywane są dane na temat aktualnego stanu ramki stosu. Rejestr ten nie może być
bezpośrednio odczytywany, ani nie można do niego bezpośrednio nic zapisać, z poziomu
aplikacji.
Rejestr ten podzielony jest na podrejestry, które zawierają informacje na temat długości
niektórych elementów ramki stosu, oraz trzy rejestry zmiany RRB (Rotating Register Base),
które są używane przy rotowaniu rejestrów.
Format rejestru CFM:
37
32 31
25 24
18 17
14 13
7 6
0
RRB.PR
RRB.FR
RRB.GR
SOR
SOL
SOF
6
7
7
4
7
7
RRB.PR (Rotate Register Base for Predicate Registers) – podstawa rotujących
rejestrów predykatowych (6 bitów)
RRB.FR (Rotate Register Base for Floating-point Registers) – podstawa rotujących
rejestrów zmiennoprzecinkowych (7 bitów)
RRB.GR (Rotate Register Base for General Registers) – podstawa rotujących rejestrów
ogólnego przeznaczenia (7 bitów)
SOR (Size Of Rotating portion of stack frame) – długość rotującej części ramki stosu
dodatkowo można obliczyć ilość rotujących rejestrów który wynosi 8*SOR
(4 bity)
SOL (Size Of Locals portion of stack frame) – długość lokalnej części ramki stosu
(7 bitów)
SOF (Size Of stack Frame) – całkowita długość ramki stosu (7 bitów)
Przy wywołaniu rejestr CFM jest kopiowany do pola PFM (Previous Frame Marker) w
rejestrze PFS (Previous Function State). Nowe wartości zapisywane do rejestru CFM tworzą
nową ramkę stosu. Wszystkie pola RRB są inicjowane wartością 0.
Rejestry PMD
(Performance Monitor Data) Jest to zestaw 64 bitowych rejestrów zawierających dane na
temat osiągów komputera. Rejestry te mogą być edytowane tylko przez uprzywilejowane
programy, które mają dostęp do niskich poziomów uprzywilejowania. Wartości rejestrów
19
PMD mogą być bezpośrednio odczytywane bez pomocy aplikacji. System operacyjny jest
upoważniony do strzeżenia skonfigurowanych przez użytkownika rejestrów. Jeśli rejestry te
czytamy z poziomów które nie są wystarczająco uprzywilejowane to rejestry te zwracają zero.
Rejestry te są używane do lepszej informacji o osiągach procesora, działają zarówno dla
zestawu instrukcji IA-64 jak i IA-32.
Rejestry PMD są podzielone na dwie części. Pierwsza część to tzw. rejestry (PMC) w których
znajdują się informacje używane do konfiguracji. Reszta to właściwe rejestry PMD. Znajdują
się w nich jedynie dane dotyczące osiągów.
Rejestr Maski Użytkownika UM
(User Mask) Jest 6 bitów flag które informują o aktualnych ustawieniach procesora. Maska
użytkownika jest częścią rejestru stanu procesora (PSR). Są one dostępne przez aplikacje
napisane dla IA-64.
Format rejestru Maski Użytkownika:
5
4
mfh mfl
1
1
3
2
1
0
ac
up
be
rv
1
1
1
1
rv – (reserved) pole zarezerwowane
be – (big endian enable) pole to kontroluje sposób zapisu oraz odczytu z/do pamięci.
Jeśli bit jest ustawiony w pozycji 1 znaczy to ze dostęp do pamięci jest według
metody big-endian, natomiast jeśli bit jest ustawiony w pozycji 0 oznacza to
dostęp do pamięci według metody little-endian.
Bit ten jest ignorowany jeśli procesor pracuje w trybie IA-32. W tym trybie dostęp
do pamięci jest zawsze ustawiony jako little-endian
up – (user performance monitor enable) pole to kontroluje dostęp do rejestrów PMD
dla użytkownika. Jeśli bit jest ustawiony w pozycji 1 znaczy to, że rejestry PMD
są aktywne, natomiast jeśli bit ma wartość 0 znaczy to, że rejestry PMD są
zablokowane
ac – (alignment check) pole to kontroluje kiedy będzie generowany błąd ustawienia
danych w pamięci. Wartość 1 tego bitu powoduje generowanie błędu przy
każdym nieustawionym dostępie do pamięci, natomiast ustawienie tego bitu w
pozycji 0 powoduje, że nieustawiony dostęp do pamięci może powodować błąd,
ale nie musi.
mfl – (Mark Floating-point Lower) Ten bit sygnalizuje dostęp do statycznej części
rejestrów zmiennoprzecinkowych. Bit ten jest ustawiany w pozycji wysokiej
wtedy gdy jakakolwiek instrukcja która używała statycznej części rejestrów
zmiennoprzecinkowych zakończyła swoje działanie. Bit ten nie jest nigdy
automatycznie zerowany, aby sprawdzić następne odwołanie do statycznej części
rejestrów zmiennoprzecinkowych należy wcześniej wpisać do tej części maski
użytkownika zero.
mfh – (Mark Floating-point Higher) Ten bit sygnalizuje dostęp do rotującej części
rejestrów zmiennoprzecinkowych. Bit ten jest ustawiany w pozycji wysokiej
wtedy gdy jakakolwiek instrukcja która używała rotującej części rejestrów
zmiennoprzecinkowych zakończyła swoje działanie. Bit ten nie jest nigdy
automatycznie zerowany, aby sprawdzić następne odwołanie do rotującej części
rejestrów zmiennoprzecinkowych należy wcześniej wpisać do tej części maski
użytkownika zero.
20
Rejestry Identyfikacji Procesora CPUID
(Procesor Identification) Są to rejestry które identyfikują konkretny egzemplarz procesora,
każdy rejestr ma po 64 bity. Rejestry te są podzielone na dwie grupy. Pierwsza grupa nazwana
stała (fixed region), która zajmuje rejestry od 0 do 4, oraz grupa zwana zmienna (variable
region), czyli rejestry od 5 w górę. Zapis do rejestrów identyfikacji procesora jest niemożliwy
ponieważ nie ma instrukcji które by umożliwiały taką operację.
Informacja o producencie procesora jest umieszczona w pierwszym oraz drugim rejestrze
CPUID. W rejestrze tym wyspecyfikowana jest nazwa producenta zapisana w formacie
ASCII. Sumarycznie długość napisu nie może przekraczać 16 bajtów, gdyż każdy rejestr ma
długość 64 bitów, co w sumie daje wartość 16 bajtów na nazwę producenta. Bity które są po
ostatnim znaku aż do końca drugiego rejestru wynoszą zero.
Numer seryjny procesora jest umieszczony w rejestrze o numerze 2. Jeżeli konkretny model
procesora posiada numer seryjny to rejestr ten zwraca 64 bitowy numer seryjny, w
przeciwnym wypadku rejestr ten jest zablokowany i odwołanie do niego zwraca zero.
Jeżeli numer seryjny istnieje to jest powiązany z 32-bitową informacją o wersji procesora,
która jest zawarta w rejestrze o numerze 3.
format rejestru CPUID.[3]
63
40 39
32 31
24 23
16 15
8 7
0
rv
archerev
family
model
revision
number
24
8
8
8
8
8
number – numer ostatniego zaimplementowanych w danym procesorze rejestru
CPUID, wartość ta jest o jeden mniejsza niż wynosi liczba wszystkich rejestrów
CPUID
revision – numer poprawki procesora, liczba ta mówi nam do jakiego wydania należy
dany procesor
model – numer ten reprezentuje model procesora, jest to numer unikalny wśród
procesorów danej rodziny
family – numer rodziny procesorów, jest to unikalny numer i nie może się powtarzać
archrev – (architecture revision) jest to numer który mówi nam ile było zmian
architektury do czasu wyprodukowania danego procesora
rv – (reserved) pole zarezerwowane
Kombinacja 64 bitowego numeru seryjnego wraz z 32 bitową informacją o wersji jest
wartością unikalną i nie może się powtarzać wśród procesorów IA-64.
W rejestrze CPUID o numerze 4 mają znajdować się informacje o cechach procesora
wykonanego w architekturze IA-64. Jest to zestaw flag które pokazują czy dana cecha jest
zaimplementowana w konkretnym procesorze. Kiedy bit wynosi 1 znaczy to, że procesor
obsługuje daną czynność, w przeciwnym przypadku wartość wynosi zero. Rejestr ten nie
zawiera cech zestawu instrukcji IA-32.
Na dzień dzisiejszy istnieje specyfikacja jedynie jednego bitu z tego rejestru. Bit ten znajduje
się w polu o numerze 0 i informuje czy procesor obsługuje instrukcję brl (Long BRanch)
czyli tak zwanego długiego skoku.
21
Rejestry rotujące
Przydzielanie rejestrów zaimplementowane w oprogramowaniu
Jedną z kluczowych koncepcji zastosowanych w IA-64, jest idea przeniesienia części zadań
dotychczas wykonywanych bezpośrednio w procesorze do oprogramowania. Jednym z
przykładów jest przydzielanie zestawu rejestrów. Większość procesorów dla serwerów sama
mapuje małą liczbę logicznych rejestrów (8-32) z większej liczby fizycznych rejestrów (na
przykład ponad 80 jak to ma miejsce w procesorze Alpha 21264). Ponieważ oprogramowanie
ma dostęp jedynie do rejestrów logicznych, sprzęt musi przydzielać oraz przeliczać dostęp
używając dodatkowej tablicy. To znacznie wydłuża czas wykonania potoku instrukcji, oraz
często także jego wielkość. IA-64 eliminuje ten mechanizm z procesora i swój wielki zestaw
udostępnia bezpośrednio dla oprogramowania. Takie postępowanie jest korzystniejsze w
większości przypadków, za wyjątkiem krótkich pętli. W tej krótkiej sekwencji kodu która jest
wykonywana wiele razu iteracyjnie, może być niewystarczająca liczba instrukcji, aby
zrównoważyć czas ładowania instrukcji. To może powodować niepożądane przestoje. W
innych procesorach problem ten rozwiązano zamieniając kolejność instrukcji, tak aby w
wolnym czasie wykonać trochę niezależnego kodu. Dodatkowe instrukcje mogą powodować
konflikty rejestrów, gdyż instrukcje z pętli mogą wskazywać na te same rejestry, na które
wskazują dodatkowe instrukcje. Problem konfliktów jest rozwiązywany właśnie przez
sprzętowe przydzielanie rejestrów logicznych. W IA-64 problem będzie rozwiązywany, przez
„wyrolowywanie" pętli w oprogramowaniu. Ta technika kompilacji zwielokrotnia instrukcje
pętli, często kilka razy, aby powstała wystarczająca ilość instrukcji.
Dla przykładu kopiująca pamięć pętla:
for(i=0;i<n;i++)
*b++=*a++;
po wyrolowaniu może wyglądać tak
m=n/3;
for(i=0;i<m;i++){
*b++=*a++;
*b++=*a++;
*b++=*a++;
}
Każdy zestaw z zwielokrotnionych przebiegów pętli jednakże może wymagać oddzielnego
zestawu rejestrów, aby zapobiegać kolizjom. Z tego powodu, IA-64 ma bardzo dużo
dostępnych rejestrów. Wadą takiego rozwiązania jest to, iż duplikowanie instrukcji może
powodować ogromny rozrost wielkości kodu.
Rotujące Rejestry nie powodują rozrostu kodu
Aby zredukować rozrost wielkości kodu IA-64 używa mechanizmu "rotujących rejestrów".
Technika ta dzieli zestaw rejestrów na 2 części. Jedna czwarta ogólnej liczby rejestrów
(stałoprzecinkowych, zmiennoprzecinkowych i predykatów) jest zarezerwowana dla
zmiennych globalnych. Reszta czyli trzy czwarte "rotuje" czyli jest kolejno przydzielana.
Dostęp do nich jest poprzez przesunięcie którego wartość jest przechowywana w specjalnych
rejestrach RRB.
22
RRB (rotating register base – podstawa rotujących rejestrów) trzy rejestry
- RRB.GR (RRB.general register) – dla rejestrów ogólnego przeznaczenia o
długości 7 bitów
- RBB.FR (RRB.floating-point register) – dla rejestrów zmiennoprzecinkowych o
długości 7 bitów
- RBB.PR (RRB.predicate register) – dla rejestrów predykatów o długości 6 bitów
Do operacji na tych rejestrach zdefiniowano specjalne instrukcje:
-
clrrrb (clear RBB) – czyszczenie wszystkich rejestrów RRB
clrrrb.pr (clear RBB predicate) – czyszczenie rejestru RRB.PR
br.ctop – dekrementacja rejestru RRB gdy warunek pętli jest umieszczony
szczycie ciała pętli, o stałej liczbie przebiegów (counted loop).
br.wtop – dekrementacja rejestru RRB gdy warunek pętli jest umieszczony
szczycie ciała pętli, gdzie liczba przebiegów zależy od warunku (while loop).
br.cexit – dekrementacja rejestru RRB gdy warunek pętli jest umieszczony
końcu ciała pętli, , o stałej liczbie przebiegów (counted loop).
br.wexit – dekrementacja rejestru RRB gdy warunek pętli jest umieszczony
końcu ciała pętli, gdzie liczba przebiegów zależy od warunku (while loop).
na
na
na
na
Specjalna instrukcja CR.CTOP zmniejsza każdorazowo odpowiedni rejestr jeden na końcu
każdego przebiegu pętli, pozwalając instrukcjom z następnego przebiegu używać następnego
zestawu rejestrów. Nazwa rotowanie bierze się stąd, iż jeśli wartości zawarta w rejestrach
RRB wskazuje na ostatni rejestr to następną porcją są rejestry z dołu, wygląda na to jakby
rejestry były zamknięte w koło i aktywna była część, która porusza się ruchem rotującym.
Instrukcje w pętli można podzielić na trzy fazy: instrukcje początkowe (prolog), instrukcje
środka (kernel), oraz instrukcje końcowe (epilog). Za kryterium podziału uważa się
zapełnienie potoku instrukcji do wykonania. Podczas wykonywania instrukcji początkowych
potok nie jest kompletny, dopiero zapełnia się, podczas wykonywania instrukcji środkowych,
potok jest pełny. Jak łatwo się domyślić podczas trwania fazy epilogu potok się opróżnia.
Rotowanie rejestrów predykatów daje możliwość wychwycenia instrukcji które są
wykonywane na początku (prologu) wykonywania pętli, oraz tych na których pętla kończy
swoje działanie (epilogu). Jeżeli te instrukcje zostaną na dodatek wcześniej właściwie
przewidziane to rotowanie rejestrów predykatowych umożliwia wykonanie tych instrukcji
tylko raz. Instrukcji startowych na początku przebiegu, oraz końcowych na końcu. Daje to
ogromne korzyści, gdyż potok cały czas jest pełny. Niekiedy może się zdarzyć, że instrukcje
początkowe pętli są potrzebne później przy inicjowaniu kolejnych przydziałów rejestrów
predykatowych, jednakże można je wykonać początkowo także dla jeszcze nie potrzebnych
rejestrów, co całkowicie eliminuje te instrukcje ze ścieżki krytycznej programu. Wystrzegając
się krzyżowania się zestawu rejestrów, oraz usprawnieniu procesu rotowania projektanci IA64 dodali kilka specjalnych rejestrów. Tymi rejestrami (oprócz rejestrów RRB) specjalnymi
są:
-
LC (loop count – licznik pętli) 64-bitowy rejestr który jak sama nazwa wskazuje
zawiera informacje który przebieg pętli właśnie się wykonuje
EC (epilogue count – licznik instrukcji końcowych) 6-bitowy rejestr kontrolujący
wykonanie instrukcji kończących pętlę.
23
Użycie specjalnych rejestrów pozwala instrukcji CR.CTOP wykonać wiele operacji prościej i
szybciej niż w tradycyjnych procesorach które mapują rejestry. Metoda przydzielania
rejestrów w IA-64 pozwala na rozwiązanie problemu krótkich pętli. Można to oczywiście
było zrobić całkowicie w kompilatorze, jednakże powodowałoby to duży rozrost kodu.
Technika rotujących rejestrów powoduje konieczność większej komplikacji (dodanie kilku
rejestrów, oraz instrukcji operujących na nich) przy budowie procesora, jednakże ta
komplikacja jest mniejsza niż w przypadku koncepcji mapowania rejestrów i udostępniania
tylko tylu ile jest w danej chwili potrzebne. Wydawać by się mogło iż wychwytywanie
instrukcji początkowych oraz końcowych może być niekorzystne w pętlach które wykonują
niewielką liczbę przebiegów. Powodem mogłyby być nadmierne koszy związanych z analizą
kodu przy poszukiwaniu prologu i epilogu, które mogą być później nie zrekompensowane
przez zyski z jednego potoku. Te obawy są bezpodstawne, gdyż dla procesora opartego na
architekturze IA-64 już dla kilku przebiegów zyski szybkości są widoczne. W dzisiejszych
rozwiązaniach rzadko stosuje się technikę wyrolowywania pętli, za wyjątkiem programów
numerycznych w których przetwarzanie długie tablice amortyzuje narzut związany
przetwarzaniem końca oraz początku pętli
Spekulatywne wykonywanie kodu oraz spekulatywny dostęp do
pamięci
Są dwa typy spekulacji związane z mechanizmami procesora. Spekulatywne wykonanie kodu,
oraz spekulatywny dostęp do danych. W obydwu, kompilator paczkuje instrukcje w taki
sposób aby operacje opóźniające ścieżkę krytyczną danego problemu były wykonywane
wcześniej. Kompilator będzie ustawiał instrukcje spekulatywne, jeżeli jest powód aby mieć
nadzieję iż taka spekulacja będzie korzystna. Aby osiągnąć korzyść muszą byś spełnione dwa
warunki: prawdopodobieństwo potrzeby poprawiania działania kompilatora jest znikomo
małe, oraz wcześniejsze wykonanie jakiejś operacji umożliwia późniejszą optymalizację
(ILP)
Spekulatywne wykonywanie kodu (Control speculation)
Idea spekulatywnego wykonywania kodu to optymalizacja wykonania programu przez
kompilator która polega na wcześniejszym wykonaniu instrukcji lub grupy instrukcji, zanim
przebieg programu dotrze do miejsca normalnego wykonania tych instrukcji. W przypadku
zastosowania tego mechanizmu instrukcje są już wykonane w tym momencie gdy dopiero
miały być załadowane. Technika to pozwala na zwiększenie efektów z równoległego
wykonywania instrukcji (ILP), oraz zaoszczędzenie czasu przy wykonywaniu instrukcji które
zajmują dużo mocy procesora. W efekcie całkowity czas wykonania programu skraca się.
Istnieje możliwość nietrafnego wykonania instrukcji, spowodowana skokiem do innej części
kodu, niż ta która została już wykonana. Jeśli dane nie zostały prawidłowo przewidziane to
istnieje mechanizm który zapisuje takie zdarzenie. Sygnalizacja polega na wstawieniu
specjalnego znacznika do docelowego rejestru, w którym znajdują się rezultaty wykonanych
spekulatywnie instrukcji. Znaczniki te są inaczej reprezentowane w rejestrach ogólnego
przeznaczenia a inaczej w rejestrach zmiennoprzecinkowych. Z rejestrami ogólnego
przeznaczenia skojarzony jest specjalny bit NaT (Not a Thing). Jeśli w ten bit ma wartość 1
oznacza to, iż dane w odpowiednim rejestrze ogólnego przeznaczenia nie mogą być
wykorzystane. W rejestrach zmiennoprzecinkowych wystąpienie nieprawidłowo
załadowanych instrukcji które korzystały z tych rejestrów jest sygnalizowane przez specjalną
wartość umieszczaną w tym rejestrze zwaną NaTVal (Not a Thing Value)
24
Aby lepiej zilustrować działanie spekulatywnego wykonania kodu można podać następujący
przykład:
if(a>b)
instrukcja1;
else
instrukcja2;
Jeśli kompilator spodziewa się, że warunek (a>b) będzie prawdziwy to nakazuje wykonanie
instrukcja1 wcześniej, zanim ten warunek będzie sprawdzany. W normalnym przypadku
instrukcja1 była by wykonana dopiero kiedy warunek (a>b) będzie sprawdzony i okaże się
prawdziwy, może się również zdarzyć taka sytuacja, że instukcja1 nie byłaby w ogóle
wykonana. Jeśli kompilator użył techniki spekulatywnego wykonania kodu, pozostaje później
jedynie czy warunek rzeczywiście został prawidłowo przewidziany
Wszystkie instrukcje zostały na dwie kategorie: spekulatywne (te które można używać
spekulatywnie) oraz nie-spekulatywne (te które nie można). Nie-spekulatywne instrukcje nie
powodują późniejszego sprawdzania czy naprawdę miały być wykonane (nie są później
ustawiane wartości NaT). Stosowanie takich instrukcji wcześniej zanim jest znane miejsce ich
wykonania jest niebezpieczne. Instrukcje spekulatywne są wyposażone w mechanizmy
sprawdzania i można je bezpiecznie stosować zanim znane jest miejsce ich wykonania.
Ładowanie do rejestrów ogólnego przeznaczenie, oraz zmiennoprzecinkowych jest możliwe
za pomocą instrukcji spekulatywnych (ld.s, ldf.s, ldfp.s) jak i nie-spekulatywnych
(ld, ldf, ldfp).
Sprawdzanie czy dane w rejestrach są poprawne wykonuje się za pomocą instrukcji chk.s.
Instrukcja ta powinna być wykonana zanim zostanie osiągnięty punkt gdzie spekulatywnie
wykonane instrukcje miały miejsce pierwotnie. Instrukcja ta testuje wystąpienie znacznika
niepoprawności danych. Jeśli ten nie jest znaleziony to spekulatywne wykonanie zakończyło
się sukcesem i dalej przebieg programu toczy się normalnie. Jeśli jednak znacznik taki jest to
spekulatywne wykonanie zakończyło się niepowodzeniem i instrukcje muszą zostać
powtórzone.
Spekulatywny dostęp do pamięci (Data speculation)
Spekulatywny dostęp do danych nazywany jest także zaawansowanym ładowaniem
(advanced loads)
W dzisiejszych systemach procesor działa zwykle o wiele szybciej niż pamięć. Spodziewane
jest tylko pogłębienie tej przepaści. W ten sposób opóźnienie w dostępie do danych jest
poważnym problemem dla dzisiejszych systemów. Aby zredukować niekorzystny wpływ
takiego wąskiego gardła tradycyjne architektury stosują pozwalają kompilatorowi oraz
procesorowi na zaplanowanie wcześniejszego ładowania danych z pamięci, niż to jest
rzeczywiście potrzebne. Niestety dla dzisiejszych systemów barierą która nie pozwala zawsze
zastosować tą technikę są skoki. Spekulatywny dostęp do danych polega na przeprowadzeniu
ładowania danych z pamięci zanim zostanie wykonane zapisanie do pamięci które
rzeczywiście ma poprzedzać ładowanie. Jedynym warunkiem użycia tego mechanizmu jest to
aby relacja między adresem pod który zapisujemy dane, a adresem skąd ładujemy dane była
wyznaczona niedwuznacznie. Nie ma bariery skoków, dane mogą być ładowane do pamięci
nawet przed skokiem za którym pamięć może być potrzebna. Za takim postępowaniem kryją
się problemy. Jeżeli nie zostanie prawidłowo przewidziana pamięć do załadowania, zostaną
załadowane dane które nie są poprawne. Trzeba jakoś poradzić sobie z takim problemem,
gdyż w przeciwnym wypadku mogą wystąpić poważne błędy jeśli taki błąd zostanie
25
zignorowany. Istniały do tej pory dwa podejścia do zaistniałej sytuacji. Dodanie specjalnego
sprawdzania błędów, niestety taka alternatywa, niweluje dotychczasowe zyski szybkościowe,
lub tzw. „work without net” czyli ryzykowanie wystąpienia katastrofalnych niewykrywalnych
błędów, poprzez wyłączenie dodatkowej kontroli.
IA-64 wybiera tzw. złoty środek, oferując nowe rozwiązanie. Podstawową ideą tego
rozwiązania jest to iż, do danych połączony jest bit NaT (Not a Thing) który informuje czy
błąd został wygenerowany podczas ładowania danych czy nie. Ten bit wskazuje, ze dane
przechodzące różne operacje np.: arytmetyczne, przemieszczenia, były sprawdzone przez tzw.
instrukcję chk. (instrukcja ta została tak zaprojektowana, że nie zabiera dodatkowego czasu
procesora.)
Taka taktyka sprawia, że kompilator może śmiało ładować spekulatywnie dane przed czasem,
bez płacenia niepotrzebnej kary przy wyjątkowych sytuacjach. Jest to znakomita korzyść w
porównaniu z dotychczasowymi rozwiązaniami, gdzie traci się albo na dodatkowym
sprawdzaniu błędów, albo naraża się na ryzyko. Używanie bitu NaT oraz sprawdzania
dodatkowego, bez użycia głównej mocy obliczeniowej procesora pozwala na używanie
spekulatywnego dostępu do pamięci bardzo efektywnie. Dodatkową korzyścią z bitu NaT jest
to, że może on być używany do sygnalizowania strukturalnych błędów jakie można znaleźć w
językach C/C++. Ponieważ kompilator może zaplanować wykonanie instrukcji chk kiedy
chce, możliwe jest bezpieczne odwlekanie wystąpienia błędów, aż do najlepszego momentu
na obsłużenie ich. Taka technika wspierająca strukturalną obsługę błędów jest jedną z
kluczowych cech IA-64 i gwarantuje stabilność systemu.
Mechanizm obsługi błędów polega na następującym algorytmie:
IA-64 trzyma ścieżki wszystkich ładowań, które są zaplanowane przed możliwymi
konfliktami zapisu w specjalnej tablicy. Tablica ta jest nazwana ALAT (Advanced Load
Addres Table – tablica adresów zaawansowanego ładowania). Kiedy napotkany jest zapis do
pamięci który powoduje konflikt z danymi zapisanymi w tablicy, to ten zapis jest usuwany z
tablicy. Natomiast sposób sprawdzania załadowanych danych polega na przeglądnięciu
tablicy. Brak wpisu w tablicy sygnalizuje ze wartość należy ponownie załadować, aby
osiągnąć poprawny rezultat. Metoda z tablicą ładowań jest unikalna i pozwala ładować dane
na tyle wcześniej, aby opóźnienie w dostępie do pamięci zostało praktycznie w całości
zniwelowane.
Podobnie jak przy spekulatywnym wykonywaniu kodu tak i przy spekulatywnym dostępie do
pamięci instrukcje są podzielone na dwie kategorie. Pierwsza kategoria to ta które bezpiecznie
można używać przy spekulatywnym dostępie do pamięci, natomiast druga to taka która nie
zawiera mechanizmu sprawdzania poprawności załadowanych danych.
Korzyści ze spekulatywnego dostępu do danych są oczywiste, procesor nie musi czekać na
dane, a trzeba zauważyć, że dostęp do fizycznej pamięci ram jest wolny w porównaniu z
szybkością procesora.
Badania prowadzone nad tą technologią czyli nad spekulatywnym wykonywaniem kodu, oraz
spekulatywnym dostępem do pamięci wykazały następujące wnioski.
W ogólnych zastosowaniach technika to poprawia osiągi procesora o 79% w porównaniu z
systemami nie posiadającymi spekulatywnych mechanizmów.
Największe korzyści z zastosowania spekulatywnego wykonywania kodu, oraz
spekulatywnego dostępu do pamięci można zauważyć dla programów które wymagają
częstego dostępu do cache. Takie zachowanie jest typowe na przykład dla systemów
operacyjnych czy wielkich baz danych.
26
Skoki (zapobieganie, przewidywanie, unikanie)
Procesory IA-64 posiadają rejestry predykatów, każdy po 1 bicie. Większość instrukcji
procesorów IA-64 zawiera pole predykatu. Idea zastosowania predykatów polega na
wykonywaniu instrukcji tylko wtedy gdy wyróżniony rejestr predykatowy zawiera wartość
prawda. Wartości w rejestrach predykatowych są wytwarzane przez instrukcję CPM która
porównuje wartości dwóch rejestrów (używając rozmaitych sposobów porównań), lub przez
instrukcję TBIT (test bit). Pojedyncza instrukcja CPM lub TBIT zapisuje wynik swojego
działania w jednym rejestrze predykatowym, oraz automatycznie zapisuje negacje wyniku w
innym rejestrze predykatowym. Taki mechanizm pozwala bardzo efektywnie wykonać częstą
konstrukcję IF-THEN-ELSE, przy niewielkim nakładzie pracy przypadającym na każdy blok,
a co najważniejsze unika się skoków które występują w takiej konstrukcji w liczbie 2, z czego
1 jest bardzo trudny do przewidzenia.
dla przykładu
RISC lub CISC
IA-64
instr 1
instr 2
instr 1
instr 2
IF
cmp(a==b)
jump_equ e1
THEN
instr3
instr4
jump e2
(PR1)
(PR1)
instr3
instr4
e1:
instr5
instr6
(PR2)
(PR2)
instr5
instr6
e2:
instr7
instr8
ELSE
PR1,PR2 ←cmp(a==b)
instr7
instr8
Jak widać technika zastosowana w IA-64 całkowicie eliminuje oba skoki, nie ma więc obawy
związanej z przestojami spowodowanymi przez nietrafione przewidywanie skoków, oprócz
tego wielkość kodu różni się w porównaniu z tradycyjnymi architekturami na korzyść IA-64.
Dodatkową zaletą jest możliwość wykonania kodu równolegle, co nie jest możliwe przy
konwencjonalnym wykonaniu kodu.
Technika predykatów była już znana wcześniej, ale nigdy w tak ogólnym przypadku.
Niektóre istniejące procesory (np. Alpha, Sparc v9, MIPS IV) mają podobne mechanizmy,
które oferowały niektóre dobrodziejstwa stosowania predykatów, ale tylko w przypadku
instrukcji MOV. Metoda predykatów zastosowana w IA-64 pozwala na stosowanie jej w
każdym z typów instrukcji. Jednak nie wszystkie skoki mogą być wyeliminowane przy
zastosowaniu predykatów.
27
Powołując się na badania Uniwersytetu z Illinois można stwierdzić, że ponad połowa
wszystkich skoków może być wyeliminowana, oraz 43% wszystkich skoków które
tradycyjnie były by błędnie przewidziane. Eliminacja takiej ilości skoków powinno zwiększyć
osiągi procesora o około 5 do 10 %.
Podstawowa instrukcja skoku w IA-64 używa 21- bitowego względnego przesunięcia. Celem
skoku musi być pierwsza instrukcja w paczce. Pozwala to na skoki do instrukcji które są
oddalone od siebie nie dalej niż 16 MB. Wyrównanie celu skoku do początku paczki
powoduje uproszczenie jednostki wykonującej skoki, oraz pozwala na rozszerzenie zasięgu
skoku, powoduje jednak rozrost kodu, związany z dodaniem średnio jednej instrukcji NOP na
jeden skok. Skoki związane z instrukcjami warunkowymi zostały rozwiązane za pomocą
rejestrów predykatowych, natomiast skoki związane z wywoływaniem procedur, powrotem z
nich oraz podobne używają specjalnego zestawu rejestru zwanych rejestrami skoków (branch
registers). Rejestry te są używane (zamiast rejestrów stałoprzecinkowych w tradycyjnych
rozwiązaniach) do przechowywania docelowego adresu skoku. Takie rozwiązanie pozwala na
uniknięcie używania stosu wywołań/powrotów gdzie zwykle przyjęło się przetrzymywać
adres powrotny.
W przewidywaniu skoków bardzo pomocny jest rejestr LC (licznik pętli) który zawiera liczbę
przebiegów pętli które jeszcze mają być wykonane. Większość tradycyjnych jednostek
przewidywania skoków błędnie przewidywało ostatni kończący wykonanie pętli skok.
Zadanie to w IA-64 wydaje się łatwe. Jednostka przewidywania skoków poprawnie przewidzi
ten skok patrząc właśnie na wartość w rejestrze LC. Ponieważ w danej chwili spodziewany
jest jedynie jeden skok związany z pętlą, istnieje tylko jeden licznik pętli.
Innym mechanizmem który jest pomocny przy przewidywaniu skoków to 2-bitowe pole
zawarte w instrukcji skoku (hint) w którym kompilator daje wskazówkę procesorowi.
Pierwszy bit pokazuje czy jest większe prawdopodobieństwo na wykonanie skoku czy nie.
Niektóre skoki prawie zawsze prowadzą w jedną stronę, co powoduje iż kompilator może
sugerować ten kierunek. Drugi bit sygnalizuje czy informacja o skoku powinna być
przechowywana czy też jednostka przewidywania skoków powinna zignorować ten skok
zwalniając miejsce dla bardziej skomplikowanych skoków. Procesor ma zawsze ostatnie
słowo w procesie przewidywania skoków i może zignorować sugestie zawarte w instrukcjach.
Kombinacja programowego oraz sprzętowego przewidywania, wraz z dodatkowymi
wskazówkami (typu rejestr LC) powinna dać lepsze rezultaty niż dotychczasowe tylko
sprzętowe rozwiązania.
Tak jak niektóre procesory RISCowe (np. PA-RISC), IA-64 może wykonywać w jednym
cyklu zegarowym porównanie, oraz instrukcję skoku. Jest jednak różnica w osiąganiu tego
celu. PA-RISC posiada specjalną instrukcję porównaj-i-skocz, IA-64 zamiast łączyć
instrukcję porównania (która dodatkowo zapełnia rejestry predykatowe) z instrukcją skoku,
układa te dwie instrukcje w jednej paczce, przy czym instrukcja skoku musi być ostatnią z
instrukcji. W specjalnym przypadku dwie instrukcje skoku mogą być położone w jednej
paczce. Powstaje wtedy tzw. rozgałęziony skok (multiway branch). Również taki układ
skoków może zostać wykonany w jednym cyklu. Sprawdzany jest wtedy warunek oraz
wyznaczany skok do wykonania (jeśli o ogóle któryś ma zostać wykonany)
28
Pierwszy procesor IA-64 Itanium
Pierwszym procesorem który będzie wykonany w architekturze IA-64 będzie Itanium.
Producentem tego procesora będzie firma Intel. Procesor jest znany także znany pod nazwą
Merced. Nazwa Merced była to robocza nazwa tego procesora, jednak forma Intel
zdecydowała się na zmianę nazwy tego produktu przy wypuszczeniu na rynek. Procesor
spodziewany jest na rynku w połowie 2000 roku. Procesor ten dedykowany będzie do pracy w
serwerach i stacjach roboczych.
Rozkład rejestrów w Itanium
W procesorze Itanium ilość rejestrów przedstawia się następująco:
Rejestry ogólnego przeznaczenia – 128 sztuk, adresowane od rejestru GR[0], który jest
tylko do odczytu, do rejestru GR[127]. Rejestry od GR[0] do GR[31] to rejestry statyczne,
natomiast rejestry od GR[32] do GR[127] to rejestry rotujące
Rejestry NaT – 128 sztuk, po jednym rejestrze NaT do każdego rejestru ogólnego
przeznaczenia.
Rejestry Zmiennoprzecinkowe – 128 sztuk, adresowane od rejestru FP[0], który wraz z
rejestrem FP[1] są tylko do odczytu. Rejestry od FP[0] do FP[31] to rejestry statyczne,
natomiast rejestry od FP[32] do FP[127] to rejestry rotujące.
Rejestry Aplikacyjne – 128 sztuk
Rejestry Predykatów – 64 sztuki. Rejestr PR[0] jest tylko do odczytu. Rejestry od PR[0] do
PR[15] to rejestry statyczne, natomiast od PR[16] do PR[63] to rejestry rotujące.
Rejestry Skoków – 8 sztuk.
Wskaźnik Instrukcji – Jeden 64-bitowy rejestr.
Oznaczenie Aktualnej Ramki Stosu – Zestaw rejestrów zajmujący 38 bitów.
Rejestry PMD – 18 sztuk.
Rejestry od 0 do 3 to tzw. rejestry statusu przepełnienia (Performance Contuer Overflow
Status Registers).
Rejestry 4-7 to tzw. rejestry ogólne rejestry badania osiągów (Preformance Contuer
Configuration/Data Registers), w rejestrach tych znajdują się zarówno części związane z
konfiguracją (PMC) jak i właściwe rejestry PMD przechowujące dane.
Rejestry 8-9 to rejestry (Opcode Match Registers)
Rejestry 10-11 to tzw. rejestry konfiguracji zdarzeń systemowych (Instruction/Data Event
Addres Configuration Registers)
Rejestry danych zdarzeń systemowych zajmują (jeśli procesor jest w tym trybie badania
konfiguracji) miejsca 0-3 oraz 17.
Rejestr 12 to tzw. rejestr konfiguracji skoków krokowych (Branch Trace Buffer Confguration
Register)
Rejestru danych skoków krokowych zajmują (jeśli procesor jest w tym trybie badania
konfiguracji) miejsca 8-16
Rejestr 13 to tzw. rejestr sprawdzania zasięgu adresu (IA-64 Instruction Address Range
Check Register)
29
Rejestr Maski Użytkownika – Jeden rejestr składający się z pięciu 1-bitowych flag.
Rejestry Identyfikacji Procesora – 5 rejestrów.
Liczba podstawowych rejestrów raczej będzie taka sama także i w innych procesorach serii
IA-64. Gdyby się wzrosła ilość rejestrów ogólnego przeznaczenia, lub zmiennoprzecinkowych, musiałoby to pociągać za sobą zmianę długości instrukcji, ponieważ zestaw
128 bitowych rejestrów jest adresowany za pomocą 7 bitów, gdyby ta liczba wzrosła adres
musiałby zawierać co najmniej 8 bitów co by wiązało się ze zwiększeniem długości instrukcji
o średnio 3 bity.
W procesorach innych niż Itanium prawdopodobne są jednakże rozszerzenia w zestawie
Rejestrów Aplikacyjnych który to zestaw posiada wiele pól ignorowanych lub
zarezerwowanych. Możliwa jest także zmiana ilości rejestrów identyfikacji procesora, gdzie
nawet explicite jest podane ile tych rejestrów posiada odpowiedni procesor w cpuid[3]. Do tej
pory nie zdołaliśmy się zorientować w ile rejestrów PMD został wyposażony procesor
Itanium.
Wracając jeszcze do rejestrów, lub części rejestrów, które są zarezerwowane, lub ignorowane,
to takie miejsca występują nie tylko w rejestrach Aplikacyjnych i miejsca te mogą być w
przyszłości wykorzystane.
30
31
Instrukcje procesora Itanium
W procesorze Itanium zaimplementowano następujące instrukcje w kolejności alfabetycznej:
(Mega)
Otoczenie procesora Itanium
Istnieje już prototyp chipsetu który będzie zarządzał działaniem otoczenia procesora Itanium.
Chipset ten posiada kodową nazwę 460GX. Układ ten będzie zawierał cechy które są
wymagane w komputerach do poważnych zastosowań, takich jak serwery, czy stacje robocze
wielkiej mocy. Dla przykładu wszystkie magistrale systemowe, oraz wszystkie rodzaje
pamięci (w tym cache) będą chronione przed przekłamaniami danych. Nieprawidłowe dane
będą jeśli to możliwe poprawiane, w przeciwnym wypadku będą zaznaczane jako
niepoprawne, co będzie powodowało zastopowanie odpowiedniego procesu, bez
zastopowania całego systemu. Możliwe jest także wykrycie nieprawidłowej części pamięci i
wyłączenie jej z dalszej pracy systemu. Chipset umożliwia także prace większej ilości
procesorów Itanium jednocześnie. W takiej konfiguracji każdy procesor jest sprawdzany
przez pozostałe, co minimalizuje możliwość wystąpienia błędu. Chipset 460GX umożliwia
stosowanie techniki tzw. hot-plugging/hot-swapping czyli możliwość podłączania, oraz
zmieniania sprzętu podczas pracy systemu. Tyczy się to zarówno pamięci masowej jak i
urządzeń PCI oraz AGP. Magistrala AGP jest tutaj standardowo w wersji 4x. Użycie 460GX
umożliwia pracę z pamięcią operacyjną nie przekraczającą 16 GB. Dostęp do tej pamięci jest
poprzez magistralę której przepustowość ograniczona jest przez 3.2 GB/s.
Przewidywania dotyczące procesorów opartych na
IA-64
Porównanie Itanium z innymi procesorami
Co prawda jest jeszcze za wcześnie aby obiektywnie stwierdzić czy pierwszy procesor oparty
na architekturze IA-64 będzie konkurencyjny dla innych procesorów na rynku w momencie
pojawienia się go na rynku. Intel szacuje, że Itanium będzie więcej niż konkurencyjnym
produktem w porównaniu z obecnymi architekturami RISC. Jest jednak jasne iż wybór
alternatywnych architektur będzie większy.
Wśród innych znaczących producentów procesorów przeznaczonych dla serwerów oraz stacji
roboczych warto zwrócić uwagę na IBM który zamierza znacząco zwiększyć moc swoich
procesorów PowerPC, zmieniając materiał do wyrobu swoich chipów na miedź. Sun
kontynuuje wzrost swojego udziału na rynku serwerów Unixowych swoją generacją
procesorów UltraSPARC. Także Compaq nie poddaje się i zamierza wprowadzić na rynek
nowy procesor Alpha EV7 (niemal w tym samym czasie co Intel Itanium). Procesor ten jest
projektowany do pracy w częstotliwościach powyżej 1Ghz. Co ciekawsze Hewlett-Packard
zamierza kontynuować ulepszanie swoich systemów opartych na procesorach PA-RISC
dopóki procesory IA-64 całkowicie nie zdeklasują tych systemów. A warto zauważyć, że
Hewlett-Packard jest współprojektantem architektury IA-64.
Oprogramowanie dedykowane dla IA-64
Mimo tego wszystkiego większość sprzedawców systemów zamierza zaangażować się we
wspieranie architektury IA-64 a nawet późniejsze przestawienie się z architektury RISC na
32
IA-64. Do tej pory IBM, Sun, HP, oraz Compaq zapowiedzieli stworzenie swoich wersji
UNIXa działających na platformie IA-64. Dodatkowo praktycznie gotowe jest już jądro
systemu Linux mające działać na nowej platformie Intela. Także inni producenci systemów
bacznie przyglądają się nowej technologii. Dotyczy to zarówno producentów systemów
UNIXowych, jak i innych. Microsoft zapowiedział wypuszczenie Windowsa dla procesora
Itanium, praktycznie tuż po premierze samego procesora. Bardzo podobnie ma się rzecz w
przypadku systemu NetWare firmy Novell.
Co prawda nowy procesor Itanium jest dedykowany do zadań profesjonalnych, to Intel bardzo
liczy na implementację najpopularniejszego obecnie w zadaniach domowych oraz biurowych
systemu czyli Windows firmy Microsoft. System ten posiada bogaty zestaw oprogramowania,
oraz jest bardzo rozpowszechniony, to stanowi jego niezaprzeczalne zalety. Intel stoi na
stanowisku, iż architektura którą on zaprojektował pozwala na uruchamianie istniejących
aplikacji typu IA-32 w nowym systemie Windows. Microsoft jednakże sygnalizuje, że
większość, jeżeli nie wszystkie aplikacje napisane dla IA-32 będą wymagać jedynie
rekompilowania aby skorzystać ze wszystkich cech IA-64. Tak więc jeśli ktoś chce się
przesiąść z IA-32 na procesor Itanium to powinien liczyć się ze zmianą systemu oraz z
potrzebą zakupienia nowych wersji aplikacji
Itanium pierwszy procesor IA-64 jest przez wiele korporacji postrzegany jako następny
procesor w ich planach zmiany sprzętu. Zmiana istniejących komputerów na nowe z
procesorem Itanium, jak zapewnia wiele niezależnych źródeł powinno znacznie zwiększyć
moc sprzętu. Dodatkową zaletą jest to, iż zapowiada się iż produkt Intela będzie dosyć
popularny, a co za tym idzie jego cena na pewno będzie znacznie niższa niż dzisiejsze
superkomputery. Podobnie rzecz się ma z wszelkiego rodzaju serwisem, który będzie tańszy,
oraz bardziej dostępny.
Kolejne procesory IA-64
Itanium nie jest jedynym procesorem nad którym pracują inżynierowie Intela. Licząc, że
Itanium wejdzie na rynek w zaplanowanym terminie czyli w połowie roku 2000, należy
przypuszczać, iż teraz procesor jest już gotowy. Zapowiadane są już kolejne procesory
zbudowane na podstawie architektury IA-64. Najbliższymi po Itanium procesorami które
mają wyjść na rynek to McKinley, oraz Willamette.
McKinley – to procesor który ma być następcą Itanium. Debiut tego procesora spodziewany
jest na połowę roku 2001, jednak znając dotychczasowe prace Intela można się spodziewać
opóźnienia tego terminu do początku 2002. Procesor ten tak jak Itanium będzie dedykowany
dla komputerów dużej mocy, oraz wszelkiego rodzaju serwerów.
Willamette – procesor ten spodziewany jest w roku 2001. Jest to ukłon Intela w stronę
prywatnych użytkowników komputerów których nie stać na procesory typu Itanium. Będzie
to uproszczona konstrukcja, spełniająca jednakże wymagania zastosowań domowych oraz
małych biur.
Deerfield – kolejny procesor Intela zbudowany w technologii IA-64 zapowiadany na połowę
roku 2002.
Madison – procesor Intela zapowiadany na rok 2003.
33
Słownik
ALAT - (Advanced Load Address Table) tablica adresów zaawansowanego ładowania, jest
ona używana w mechanizmie obsługi błędów związanych ze spekulatywnym dostępie do
pamięci. W tablicy tej trzymane są ścieżki wszystkich spekulatywnych ładowań.
Bundle – paczka w której umieszcza się instrukcje zaplanowane do załadowania w jednym
cyklu zegara. Paczka taka ma wielkość 128 bitów. W takiej paczce mieszczą się trzy
instrukcje po 41 bity każda, oraz 5-bitowe pole tzw. template.
CISC – (Complex Instruction Set Computing) Architektura cechująca się szerokim zestawem
złożonych instrukcji, małym zestawem rejestrów. Instrukcje mają różną długość i są
wykonywane w różnej ilości cykli zegarowych. Przykładem procesorów wykonanej w tej
architekturze jest seria IA-32.
EPIC – (Explicitly Paralell Instruction Computing) „przetwarzanie wyraźnie równoległe”
Architektura cechująca się grupowaniem instrukcji w paczki (bundles), które to instrukcje
można wykonać równolegle. Instrukcje mają stałą długość, ilość rejestrów jest duża.
IA-32 – (Intel Architecture 32-bit) Dzisiejsza podstawowa architektura Intela. Jest to 32bitowa architektura CISC, zwana również pod nazwą x86.
Itanium – Pierwszy procesor zrealizowany w architekturze IA-64. Procesor ten ma pojawić
się na rynku w połowie 2000 roku, jego producentem jest firma Intel.
Merced – Kodowa nazwa pierwszego procesora IA-64. Rynkowa nazwa tego procesora
brzmi Itanium.
NaT – (Not a Thing) Rejestry które mówią, że dane w rejestrach ogólnego przeznaczania, nie
są poprawne, odpowiednikiem tego rozwiązania w rejestrach zmiennoprzecinkowych są
wartości NaTValue.
PA-RISC – (Architecture Precision RISC) Architektura procesorów
produkowanych przez firmę Hewlett-Packard. Znana także jako HP-PA
RISCowych
RISC – (Reduced Instruction Set Computing) Architektura cechująca się niewielkim
zestawem prostych instrukcji, oraz dużym zestawem rejestrów. Instrukcje mają stałą długość i
są wykonywane w jednym cyklu zegarowym. Przykładem procesorów wykonanych w tej
architekturze jest sera PA-RISC.
VLIW – (Very Long Instruction Word) – pierwsza architektura pomyślana z myślą o
grupowaniu instrukcji przeznaczonych do równoległego wykonania.
34

Podobne dokumenty