sprawozdanie ak2l

Upload: ssteku

Post on 14-Jul-2015

68 views

Category:

Documents


0 download

TRANSCRIPT

Krystian Horecki 181079

Wrocaw, dn. 22 maja 2011

Ocena: ....................... Oddano: ..........................

Sprawozdanie z laboratorium przedmiotu Architektura KomputerwRok akad. 2010/201, kierunek: INF PROWADZCY: dr hab. in. Janusz Biernat

1

Spis treci1. Podstawowe konstrukcje programowe z uyciem instrukcji asemblera..........................................3 1.1 Zamiana wielkoci liter we wczytanym z klawiatury cigu znakw.........................................3 1.1.1 Opis wykonania zadania....................................................................................................3 1.1.2 Kod programu....................................................................................................................3 1.1.3 Spostrzeenia.....................................................................................................................4 1.2 Szyfr cezara................................................................................................................................5 1.2.1 Opis wykonania zadania....................................................................................................5 1.2.2 Kod programu....................................................................................................................5 1.2.3 Spostrzeenia.....................................................................................................................7 1.3 Wnioski......................................................................................................................................7 2. Tworzenie i uycie funkcji, funkcji rekurencyjnych........................................................................8 2.1 Algorytm Euklidesa w wersji iteracyjnej i rekurencyjnej..........................................................8 2.1.1 Opis wykonywanego zadania.............................................................................................8 2.1.2 Kod programu....................................................................................................................8 2.2 Wnioski i spostrzeenia...........................................................................................................11 3. Zapoznanie si z technikami pozwalajcymi na uycie w tym samym projekcie rnych jzykw programowania ..................................................................................................................................11 3.1 Wykorzystanie funkcji oraz zmiennych z jzyka asemblerowego w jzyku c........................11 3.1.1 Opis wykonywanego zadania...........................................................................................11 3.1.2 Kod programu..................................................................................................................11 3.1.3 Spostrzeenia...................................................................................................................13 3.2 Wykorzystanie funkcji oraz zmiennych z jzyka C w asemblerze..........................................13 3.2.1 Opis wykonywanego zadania...........................................................................................13 3.2.2 Kod programu..................................................................................................................14 Kod programu z pliku doczanego .c......................................................................................14 Kod pliku Makefile..................................................................................................................15 3.2.3 Spostrzeenia...................................................................................................................15 3.3 Wnioski....................................................................................................................................15 4. Bibliografia.....................................................................................................................................16

2

1. Podstawowe konstrukcje programowe z uyciem instrukcji asemblera1.1 Zamiana wielkoci liter we wczytanym z klawiatury cigu znakw 1.1.1 Opis wykonania zadaniaW wiczeniu tym naleao napisa program, majcy na celu zamian liter we wprowadzonym z klawiatury cigu znakw. Odbywa si to za pomoc ptli wczytujcej kolejne bajty bufora wejciowego do rejestru cl. Nastpnie sprawdzana jest wielko litery oraz to czy jest ona w ogle liter, co odbywa si przy pomocy porwnania jej na pocztku z liter 'a' oraz liter 'z' co daje moliwo stwierdzenia czy znak ten jest ma liter. Do zamiana maej litery na du uywana jest rnica pomidzy literami 'A' i 'a', ktra dodawana jest do liczby trzymanej w rejestrze cl. Po otrzymaniu kodu duej litery wczytywany jest on do bufora, na miejsce dawnej maej litery. Na koniec program wypisuje otrzymany cig znakw na ekranie.

1.1.2 Kod programuKod pliku .sSTDIN = 0 STDOUT=1 READ = 3 WRITE = 4 EXIT =1 KEY =1 .section .bss .lcomm BUFF, SIZE .section .data .equ DIFF, 'A' - 'a' .equ Z, 'Z' .section .text .global _start _start: #czytanie znakow z klawiatury movl $SIZE, %edx movl $BUFF, %ecx movl $STDIN, %ebx movl $READ, %eax int $0x80 #wczyatnie danych o buff do rejestrow

3

movl %eax, %ebx #sprawdzanie czy buff nie jest pusty cmpl $0, %ebx je end #Wyzerowanie licznika movl $0, %edi #poczatek petli kodujacej start_loop: #przeniesienie kolejnych bajtow do rejeastru movb BUFF(,%edi,1), %cl #Wczytanie kolejnego bajtu bufora do rejestru #Sprawdzanie czy znak jest ma liter cmpb $'a', %cl jl nastepna cmpb $'z', %cl jg nastepna addb $DIFF, %cl movb %cl,BUFF(,%edi,1) nastepna: inc %edi cmpl %ebx,%edi jl start_loop #wyswietlanie znakow na ekranie movl $SIZE, %edx movl $BUFF, %ecx movl $STDOUT, %ebx movl $WRITE, %eax int $0x80 #Dodawanie do kodu litery rnicy pomidzy 'A' i 'a' #Wczytanie z powrotem zmienionego kodu litery do bufora #Przejcie do nastpnej litery #Sprawdzanie czy to nie koniec cigu znakw

movl $EXIT,%eax int $0x80

1.1.3 SpostrzeeniaW zadaniu tym najwaniejszym elementem byy operacje porwnywania znaku wczytanego z klawiatury z maymi literami, a take stworzenie ptli, ktra przechodzi przez wszystkie wczytane litery. W przypadku porwnywania liter zostao to zrealizowane na jeden z kilku moliwych sposobw, gdy oprcz zamieszonego powyej, mona te korzysta z funkcji and oraz funkcji cmp, porwnujc kod z liczb bajtow 01100000, co oznacza e dany znak jest ma liter. Oba sposoby s poprawne, ja za wybraem wersj realizacji za pomoc sprawdzania czy znak jest mniejszy/wikszy od litery z powodu pocztkowego wraenia mniejszego 4

skomplikowania tego rozwizania.

1.2 Szyfr cezara 1.2.1 Opis wykonania zadaniaW wiczeniu tym realizowane jest kodowanie szyfrem cezara. Podobnie jak w poprzednim zadaniu wczytywany jest znak z bufora wejciowego, nastpnie sprawdzane jest to czy jest on liter. Po dodaniu klucza szyfrujcego sprawdzane jest czy warto znaku nie przekroczya wartoci litery odpowiednio 'z' lub 'Z' w przypadku duych liter, a nastpnie ew. nadmiar jest korygowany. Zakodowane litery wczytywane s z powrotem do bufora, a po zakoczeniu kodowania wypisywane na ekranie.

1.2.2 Kod programu.section .data #Kody sytemowe .equ SYS_EXIT, 1 .equ SYS_READ, 3 .equ SYS_WRITE, 4 .equ SYS_OPEN, 5 .equ SYS_CLOSE, 6 .equ SYSCALL, 0x80 .equ KEY,1 .equ Z ,'Z' .equ z,'z' #kody obslugi plikow .equ STDIN, 0 .equ STDOUY, 1 .equ STDERR, 2 .section .bss .equ BUFF_SIZE,500 .lcomm BUFF, BUFF_SIZE .section .text .globl _start _start: 5

#Przygotowanie do wprowadzenia danych z wejscia standardowego movl $BUFF_SIZE, %edx movl $BUFF, %ecx movl $STDIN, %ebx movl $SYS_READ, %eax int $SYSCALL #wyzerowanie licznika petli movl $0, %edi #Zczytanie dlugosci wczytanych danych movl %eax,%ebx subl $1,%ebx konwersja: #Zczytanie kolejnej litery z buff movl $BUFF,%ecx movb (%ecx,%edi,1), %cl #Kontrolowanie czy zczytana warto jest liter movb %cl,%al andb $0x40,%al cmpb $0x40,%al #Przejscie jezeli nie jest litera jne nastepna #Dodanie klucza szyfrujcego do danej litery addb $KEY,%cl movb %cl, %al #Kontrola czy dana litera jest duza czy mala andb $0x20,%al cmpb $0x20,%al je mala_litera #Sprawdzenie czy dany znak nie przekracza zakresu liter #odpowiednio malych lub duzych movb %cl,%al cmpb $Z,%al jle nastepna #jezeli przekracza wykonywane jest odejmowanie by wrocic do #znaku z odpowiedniego zakresu (dzielenie mod 26) subb $26,%cl mala_litera: movb %cl,%al cmpb $z,%al jle nastepna 6

subb $26,%cl nastepna: #Wczytanie do bufora poprawionej porcji danych movb %cl,%al movl $BUFF,%ecx movb %al, (%ecx,%edi,1) #Zwiekszenie licznika petli incl %edi #Porownanie licznika z liczba wczytanych elementow cmpl %ebx , %edi jne konwersja #Wypisanie odpowiednio zaszyfrowanych danych movl $BUFF_SIZE, %edx movl $BUFF, %ecx movl $STDOUY,%ebx movl $SYS_WRITE,%eax int $SYSCALL movl $SYS_EXIT, %eax movl $0, %ebx int $SYSCALL

1.2.3 SpostrzeeniaZastosowany algorytm szyfrowania jest stosunkowo prostym algorytmem, ktry do atwo daje si implementowa w jzyku asemblerowym. Podobnie jak w zadaniu poprzednim tak i tutaj, gwn role odgrywa analizowanie poszczeglnych znakw wczytanych z bufora, a nastpnie odpowiednia ich edycja.

1.3 WnioskiPodczas pierwszych wicze miaem okazje pozna sposoby budowania podstawowych konstrukcji programowych, takich jak ptle i rnego rodzaju warunki. W moich programach uyte zostay : rnego rodzaju skoki warunkowe(je, jne, jl) instrukcje porwnujce(cmpl) ptle zbudowane z etykiet oraz skokw warunkowych podstawowe operacje matematyczne( addl)

7

2. Tworzenie i uycie funkcji, funkcji rekurencyjnych2.1 Algorytm Euklidesa w wersji iteracyjnej i rekurencyjnej 2.1.1 Opis wykonywanego zadaniaPodczas zaj za zadanie mielimy wykona realizacje algorytmu Euklidesa, sucego szukaniu najwikszego wsplnego dzielnika. Algorytm realizowany jest za pomoc funkcji dwch rodzajw: iteracyjnej oraz rekurencyjnej. Sam algorytm Euklidesa polega na wykonywaniu nastpujcych krokw: 1. oblicz c jako reszt z dzielenia a przez b 2. zastp pozycj a liczb b, a pozycj b liczb c 3. jeeli pozycja b = 0, to szukane NWD = a, w przeciwnym wypadku przejd do 1 [2] Poniszy program, oprcz czci waciwej zawiera take realizacj obu wersji algorytmu, z czego jedynie wersja rekurencyjna jest wywoywana, gdy stanowi ona niejako trudniejsz wersje funkcji iteracyjnej patrzc z punktu widzenia obsugi wskanika stosu, przekazywania argumentw i uzyskiwania wynikw. Dziaanie poszczeglnych fragmentw kodu zostao opisane za pomoc komentarzy w kodzie programu.

2.1.2 Kod programu.section .data .equ STDIN, 0 .equ STDOUT,1 .equ READ, 3 .equ WRITE, 4 .equ EXIT,1 .section .bss .equ SIZE,500 .lcomm BUFF, SIZE .section .text .global _start _start: #=============================================== #wrzucanie argumentw funkcji na stos #Arg B pushl $12 8

#arg A pushl $24 #Wywoanie funkcji rekurencyjnej liczcej najwikszy wsplny dzielnik alg. Euklidesa #sposobem rekurencyjnym call euklidesrek #przesunicie wsk. Szczytu stosu na miejsce przed wczytaniem 2 argumentw, czyli o 8 bajtw #do gry addl $8, %esp movl %eax,%ebx movl $EXIT,%eax int $0x80

.type euklides, @function euklides: #Wrzucenie wskanika dna sotsu na stos pushl %ebp #Przeniesienie wsk. Szczytu stosu do rejestru wskanika dna stosu movl %esp,%ebp ; #Czytanie parametrw funkcji #Arg A movl 8(%ebp), %ecx #Arg B movl 12(%ebp),%ebx #przerzuca A do tmp movl %ecx,%eax start_loop: #dzielenie liczb, reszta znajduje si w ebx andl $0, %edx divl %ebx #przeniesienie B do A movl %ebx,%ecx #przeniesienie C do B movl %edx,%ebx #Sprawdzenie czy to nie koniec oblicze cmpl $0, %ebx movl %ecx,%eax jne start_loop 9

;

#Zakaczanie funkcji end_euklides: #Ustawienie wskanika stosu na starej pozycji movl %ebp,%esp #Wpisanie do rejestru wskanika programu adresu sprzed wywoania funkcji popl %ebp ret #Wersja funkcji w wykonaniu rekurencyjnym .type euklidesrek, @function euklidesrek: #Wrzucenie adresu wsk dna stosu na stos i wpisanie do niego adresu szczytu stosu pushl %ebp movl %esp,%ebp #Arg A movl 8(%ebp), %ecx #Arg B movl 12(%ebp),%ebx #Warunek kocowy sprawdzanie czy B jest rwne 0 cmpl $0,%ebx jne next_check #Przeniesienie wyniku do rejestru eax, by mona go byo odczyta po wyjciu z funkcji movl 8(%ebp),%eax jmp end_euklides next_check: movl %ecx,%eax #Zerowanie rejestru uywanego w dzieleniu andl $0, %edx divl %ebx #Wrzucanie na stos argumentw dla wywoania nastpnego poziomu rekurencji pushl %edx pushl %ebx call euklidesrek end_euklidesrek: #Zakaczanie funkcji zgodnie z konwencj movl %ebp,%esp popl %ebp ret 10

2.2 Wnioski i spostrzeeniaW przypadku programowania za pomoc funkcji w jzyku asemblerowym bardzo istotne jest pamitanie o zwrceniu odpowiedniej uwagi na obsug wskanika stosu. Bardzo istotne jest by pamita, o potrzebie przekopiowania w momencie wywoania funkcji, adresu jaki jest trzymany w rejestrze wskanika dna stosu(ebp) na stos, a nastpnie wpisanie do ebp adresu aktualnego szczytu stosu. Czynno ta musi by wykonana w odwrotn stron przy zakaczaniu funkcji. Istotnym faktem jest te to, e argumenty funkcji naley umieszcza na stosie w odwrotnej kolejnoci ni chcemy z nich korzysta w funkcji. Spowodowane to jest faktem, e argument umieszczony na stosie jako ostatni jest na samym jego szczycie (ma najniszy adres). Podsumowujc mona stwierdzi, e wiczenie to dao mi moliwo zapoznania si z metod pisania funkcji w jzyku asmeblerowym, a take wiedz na temat budowy i zachowania stosu programu, ktry jest niezbdny do posugiwania si funkcjami w asemblerze.

3. Zapoznanie si z technikami pozwalajcymi na uycie w tym samym projekcie rnych jzykw programowania3.1 Wykorzystanie funkcji oraz zmiennych z jzyka asemblerowego w jzyku c 3.1.1 Opis wykonywanego zadaniaW zadaniu tym wykonany zosta przeze mnie program sucy do pokazania tego w jaki sposb korzysta z funkcji oraz zmiennych napisanych w jzyku asemblerowym, w plikach napisanych w jzyku C. W programie tym w pliku .s stworzone s dwie zmienne majce wartoci liczbowe, bdce zmiennymi globalnymi, a take funkcje wywietlajc za pomoc funkcji bibliotecznej 'printf' na ekranie napis trzymany w pamici. W czci programu napisanej w jzyku C korzystamy ze zmiennych zadeklarowanych w pliku .s po uprzednim zadeklarowaniu ich jako zmienne typu extern. Funkcja jest moliwa do uytku po wczeniejszym zadeklarowaniu jej na pocztku pliku. Najwaniejszym elementem tego programu jest etap linkowania, gdy wymaga on stworzenia z pliku asemblerowego biblioteki, ktra nastpnie linkowana jest do pliku kocowego. Proces ten jest opisany dokadnie w komentarzach kodu pliku Makefile.

3.1.2 Kod programu Kod pliku .s zawierajcego funkcj wykorzystywan w programie w jzyku c11

.section .data zdanie: .ascii "Jakies zdanie do wyswietlenia z pliku asm przez funkcje assemblerowa\n" #Sprawienie e zmienna jest widoczna we wszystkich plikach zlinkowanych z plikiem w #ktrym si znajduje .globl liczbaa .size liczbaa,4 liczbaa: .long 5 .globl liczbab .size liczbab,4 liczbab: .long 13 .section .text .globl funkcja .type funkcja, @function funkcja: pushl %ebp movl %esp, %ebp #Umieszczenie na stosie adresu pierwszego arg. wywoania funkcji bibliotecznej #'printf' pushl $zdanie call printf pushl $0 call exit movl %ebp, %esp popl %ebp ret

Kod pliku .c z wywoaniem funkcji z pliku .s oraz korzystajcego ze zmiennych zawartych w pliku .s

#include void funkcja(); extern int liczbaa; extern int liczbab; int main() 12

{ //Wypisanie liczby a i b z pliku asemblerowego na ekranie printf("%d\n",liczbaa); printf("Liczba a:%d Liczba b:%d\n",liczbaa,liczbab); printf("A+B =%d \n",liczbaa+liczbab); //Wywoanie funkcji umieszczonej w bibliotece, ktra zostaa napisana w asemblerze funkcja(); }

Kod pliku Makefile

#Linkowanie pliku program_c.o oraz biblioteki asmasm.so #Biblioteka asmasm.so (-lasmasm) bdzie szukana w aktualnej ciece ( -L) program_c : program_c.o asmasm.so ld -L . -dynamic-linker /lib/ld-linux.so.2 -melf_i386 -o program_c -lasmasm program_c.o #Tworzenie pliku .o programu w jzyku C w wersji 32 bitowej program_c.o : program_c.c gcc -c program_c.c -o program_c.o -m32 #Tworzenie pliku .o z pliku asemblerowego w wersji 32 bitowej asmasm.o : asmasm.s as asmasm.s -o asmasm.o 32 #Tworzenie shared libary(-shared) oraz linkowanie pliku asmasm.o z bibliotek jzyka C (-lc) asmasm.so : asmasm.o ld -shared asmasm.o -o libasmasm.so -melf_i386 -dynamic-linker /lib/ld-linux.so.2 -lc

3.1.3 SpostrzeeniaPo wykonaniu tego zadania mona zauway, e uywanie rnych elementw napisanych w jzyku asemblerowym, w programach napisanych w tym wypadku w jzyku C nie jest skomplikowane. Jedyn trudnoci moe by odpowiednie podlinkowanie bibliotek do plikw. Problem, ktry pojawia si podczas pisania tego programu to fakt, e dynamic linker szuka bibliotek zazwyczaj tylko w katalogach /lib i usr/lib co powoduje bdy spowodowane niemonoci stworzonej biblioteki. Rozwizaniem tego problemu jest dodanie do cieki bibliotek lokalizacji naszej biblioteki poleceniem : export LD_LIBRARY_PATH [1]

3.2 Wykorzystanie funkcji oraz zmiennych z jzyka C w asemblerze 3.2.1 Opis wykonywanego zadaniaW tym zadnaiu wykonany zosta przeze mnie program pokazujcy uycie funkcji napisanej w jzyku C, a take zmiennych z pliku .c w programie napisanym w asemblerze. Program na pocztku umieszcza argumenty funkcji na stosie, w kolejnoci odwrotnej do tej 13

jak jest w jzyku C, a nastpnie wywouje funkcje z pliku napisanego w jzyku C, ktry znajduje si w podlinkowanej bibliotece. Liczby, ktre s przekazywane jako argument s jednoczenie zmiennymi zewntrznymi, znajdujcymi si w pliku .c. Po zakoczeniu dziaania funkcji wynik zapisywany jest w rejestrze eax, a nastpnie kopiowany dla bezpieczestwa trwaoci do rejestru ebx. Nastpnie wywoywana jest jeszcze funkcja biblioteczna 'printf' z uyciem zewntrznych zmiennych, a take odpowiednio sformatowanego cigu znakw, ktra wypisuje na ekran liczy wraz z opisem.

3.2.2 Kod programu Kod pliku .s.section .data zdanie: .ascii "Zdanie do wypisania na ekranie\n\0" opis: .ascii "Liczby z pliku .c: a= %d b= %d \n" .section .text .globl _start _start: pushl a #Wrzucenie na stos zmiennych z pliku .c pushl b call dodaj #wywoanie funkcji z pliku zewntrznego .c pushl $zdanie #Wrzucenie na stos zdania ktre ma by wypisane call printf #Wywolanie systemowej funkcji printf movl %eax, %ebx #Skopiowanie do rej. Ebx wyniku zwrconego przez funkcj pushl b #Wrzucenie na stos liczb z zew. pliku pushl a pushl $opis #Wrzucenie odpowiednio sformatowanego tekstu call printf #Wypisanie tekstu za pomoc funkcji printf pushl $0 movl %ebx,%eax call exit

Kod programu z pliku doczanego .c

#include //Zmienne ktre s wykorzystywane w pliku .s int a = 5;14

int b=11; //Funkcja wywoywana w programie napisanym w asemblerze int dodaj(int a, int b) { return a+b; }

Kod pliku Makefile

#Linkowanie do pliku kocowego pliku .o oraz biblioteki zawierajcej plik, ktry by #napisany w jzyku C apsm_p_c : asm_p_c.o dodawanie2.so ld -L . -dynamic-linker /lib/ld-linux.so.2 -melf_i386 -o asm_p_c -ldodawanie2 asm_p_c.o asm_p_c.o : asm_p_c.s as --gstabs asm_p_c.s -o asm_p_c.o dodawanie.o : dodawanie.c gcc -c dodawanie.c -o dodawanie.o #Tworzenie biblioteki z pliku dodawanie.o dodawanie2.so : dodawanie.o ld -shared dodawanie.o -o libdodawanie2.so -melf_i386 -dynamic-linker /lib/ldlinux.so.2 -lc

3.2.3 SpostrzeeniaW gruncie rzeczy korzystanie z elementw napisanych w jzyku C w programach w jzyku asemblerowym jest bardzo podobne do sytuacji w poprzedniego zadania, take w tym wypadku jedyn trudno moe sprawia linkowanie oraz tworzenie obiektw dzielonych, sucych do przechowywania kodu.

3.3 WnioskiPodczas tego wiczenia miaem okazj pozna sposb korzystania w asemblerze z kodu napisanego w C, a take w C z kodu napisanego w asemblerze, ktre byy umieszczane w plikach .so (shared objects). W wiczeniu tym naleao wykorzysta kilka uytecznych opcji linkera oraz komend , takich jak: -L (szukanie biblioteki w biecym katalogu) -shared (Tworzenie biblioteki z pliku .o) -lc (Linkowanie biblioteki jzyka C) 15

-dynamic-linker /lib/ld-linux.so.2 (pozwala na linkowanie plikw bibliotek) dodawanie cieki do cieki bibliotek: export LD_LIBRARY_PATH

Byo to wiczenie wyjtkowo przydatne z uwagi na moliw w przyszoci potrzeb korzystania z elementw asemblera w jzykach wyszego poziomu, w celach optymalizacyjnych.

4. Bibliografia[1] Jonathan Bartlett, Programming from the Ground Up [2] http://pl.wikipedia.org/wiki/Algorytm_Euklidesa

16