Wykład 3: Jak działa typowy mikroprocesor? Budowa procesora rodziny Intel80x86 Architektury CISC i RISC Instrukcje skoków warunkowych Stos Instrukcje operujące na ciągach danych Pętle
Fragment kodu programu: Język „wysokiego poziomu”: x:=1; for i:=1 to 10 do x:=x*2; Assembler: Mov [edx],$3f800000 Mov [eax],$00000001 ... „kod maszynowy”: C7 02 00 00 80 3F C7 00 01 00 00 00 ...
Kodowanie instrukcji za pomocą bajtów:
Rys. Umiejscowienie logiczne mikroprocesora w systemie mikroprocesorowym
Sygnały na „pinach” procesora.
Instrukcje wejścia/wyjścia (Input/Output):
Budowa mikroprocesora typu CISC Complete Instruction Set Computer
Budowa mikroprocesora typu RISC Reduced Instruction Set Computer
Podstawowe różnice pomiędzy CISC a RISC (Load Execution Store): znacznie ograniczony zestaw instrukcji operacje ALU tylko na rejestrach prosty tryb adresowania - uproszczone odwołania do pamięci wszystkie instrukcje identycznej długości (32 bity) znacznie prostsza konstrukcja procesora CISC rozbudowane instrukcje operacje arytmetyczne bezpośrednio na lokalizacjach w pamięci możliwość zawansowanego programowania w języku maszynowym różna długość instrukcji często występujące instrukcje - 8 bitów rzadsze, rozbudowane instrukcje o większej długości znaczne różnice czasu wykonania poszczególnych instrukcji
w trybie rzeczywistym: rejestry segmentowe Adresowanie pamięci w trybie rzeczywistym: rejestry segmentowe Przestrzeń adresowa wynosi 1MB ale w obrębie segmentu tylko 64kB
Adresowanie pamięci: tryby adresowania mov AX,1234h - natychmiastowy mov AX,[1234h] - bezpośredni mov EAX,DS:{CS,ES}[ESI] - pośredni DS – Data Segment (ES) CS – Code Segment mov EAX,[ECX+EBX*2{4,8}+stała] - pośredni skalowany z przemieszczeniem movs EAX,[ESI] - operacja łańcuchowa (ESI,EDI – wskaźnik źródła (Source) i przeznaczenia (Destination)
Przykłady: var tablica:array[0..100] of single; i:integer; y:single a) y:=tablica[10h] mov EAX,[tablica+40h] b) y:=tablica[i+10h] mov ebx,i lea ecx,tablica mov eax,[ecx+$10+ebx*4]
IP (Instruction Pointer) Wskaźnik rozkazów: IP (Instruction Pointer) PC (Program Counter):
i instrukcje skoków warunkowych Rejestr statusowy SR ( Status Register ) i instrukcje skoków warunkowych Instrukcje zmianiające stan znaczników (flag) CLC, CLD ,CLI – kasujące STC, STD, STI - ustawiające
Instrukcje skoków warunkowych Dotyczące operacji arytmetycznych na liczbach bez znaku JB/JNAE (Below) CF=1 JNB/AE (Not Below) CF=0 JBE/JNA (Below Equal) CF=1 lub ZF=1 JNBE/JA (Not Below Not Equal) CF=0 i ZF=0 Dotyczące operacji arytmetycznych na liczbach ze znakiem U2 JL/NGE (Less) SF<>OF JGE/NL (Greater Equal) SF=OF JLE/NG (Less Equal) ZF=1 lub SF<>OF JG/NLE (Greater) ZF=0 i SF=OF Pozostałe JE/JZ (Equal) ZF=1 JNE/JNZ (Not Equal) ZF=0 JS (Sign) SF=1 JNS (Not Sign) SF=0
Instrukcje skoków warunkowych - przykład Sekwencja instrukcji w Pascal-u: var a,i:integer; (32 bity) if i<10 then a:=i else a:=10; Przykład zapisu w assemblerze CMP dword ptr [i],$0a JGE +$0c mov EAX,[i] mov [a],EAX JMP +$0a +$0c: mov [a],$0000000a +$0a:
Instrukcje skoków warunkowych - przykład Sekwencja instrukcji w Pascal-u: var a:single; (32 bity) if a>10 then a:=10; Przykład zapisu w assemblerze: Sposób 1 fld a fcomp stała fstsw ax sahf jbe +$0a mov [ar],$41200000a +$0a: ... Sposób 2 (nowy) fld a fld stala fcomi ST,ST(1) jbe omin mov [ar],$41200000 +$0a: ...
(adres wierzchołka stosu = SS:SP) Stos i podprogramy: (adres wierzchołka stosu = SS:SP) Adres wierzchołka stosu = SS:ESP Stos „rośnie w dół” Przy operacjach odkładania na stos (PUSH) modyfikowany jest wskaźnik stosu a następnie zapisywana odpowiednia wartość Zdejmowanie ze stosu (POP) w kolejności: pobranie wartości z pamięci wskazywanej SS:ESP do odpowiedniego rejestru a następnie zwiększenie wartości wskaźnika ESP
(adres wierzchołka stosu = SS:SP) Stos i podprogramy: (adres wierzchołka stosu = SS:SP) 500:(Start) ... 510: call procedura1 516: ... koniec: .... (Procedura1) 1000: call procedura2 1006: ret (Procedura2) 2000: nop ret
Ramki stosu Wierzchołek stosu (SS:ESP) przesuwany jest w dół w celu zarezerwowania jego fragmentu do innych celów Przed przesunięciem zawartość ESP zapamiętywana jest w specjalnym rejestrze EBP. Powstaje w ten sposób tzw. „ramka stosu” (ang. Stack Frame) czyli obszar pamięci od SS:EBP do SS:ESP Powrót do sytuacji początkowej następuje poprzez przywrócenie początkowej wartości rejestru ESP (skopiowanie jej z rejestru EBP) Zastosowania: zmienne lokalne procedur i funkcji przekazywanie parametrów do procedur i funkcji
Ramki stosu: -przykład Function f3(d1,d2:integer) :integer; stdcall; var d3:integer; begin d1:=1; result:=d1+d2+d3; end; ... var a,b,c:integer; .... b:=1; c:=2; a:=f3(b,c);
Ramki stosu: przykład cd.: Function f3(d1,d2:integer) :integer; stdcall; var d3:integer; begin d1:=10; result:=d1+d2+d3; end; ... var a,b,c:integer; b:=1; c:=2; a:=f3(b,c);
Instrukcje operacji na ciągach: (MOVS, LODS, STOS) LODSB/W/D = MOV AL,DS:(ESI) ADD/SUB ESI, 1/2/4 STOSB/W/D = MOV ES:(EDI),AL. ADD/SUB EDI, 1/2/4 MOVSB/W/D = MOV ES:(EDI),DS:(ESI) CLD, STD - zmiana kierunku w górę/ w dół
Instrukcje dotyczące pętli: (LOOP) Sekwencja instrukcji w Pascal-u: var i:integer; for i:=10 downto 0 do Begin End; Przykład zapisu w assemblerze: mov ecx,10 petla: loop petla Sekwencja instrukcji w Pascal-u: var i:integer; for i:=0 to 10 do Begin End; Przykład zapisu w assemblerze: mov ecx,10 petla: loop petla
Instrukcje dotyczące pętli: (REP) var tablica_źródłowa, tablica_przeznaczenia : array(1..1000) of integer; Przykład: MOV ECX,1000 LEA ESI,tablica_źródłowa LEA EDI,tablica_przeznaczenia CLD REP MOVSW
Instrukcje dotyczące pętli: (REP) var tablica_przeznaczenia : array(1..1000) of integer; Przykład: MOV ECX,1000 MOV EAX,0 LEA EDI,tablica_przeznaczenia CLD REP STOSW