|
|
Zadania domowe z kompilowania programów
|
|
|
===
|
|
|
|
|
|
Rozwiązania proszę umieścić w Waszym repozytorium w katalogu `compile/zadX/`, gdzie `X` to numer
|
|
|
zadania.
|
|
|
|
|
|
Zadanie 1.
|
|
|
---
|
|
|
Zademonstruj, że potrafisz kompilować programy napisane w wielu plikach:
|
|
|
|
|
|
* napisz program, który wczyta dwa słowa złożone z małych literek alfabetu angielskiego
|
|
|
i wypisze ich [odległość Levenshtein'a](https://en.wikipedia.org/wiki/Levenshtein_distance);
|
|
|
* zrób to w dwóch plikach - w jednym niech będzie wczytywanie i wypisywanie, a w drugim cała logika
|
|
|
związana z wyliczaniem odległości;
|
|
|
* napisz skrypt, który kompiluje program - powinien najpierw skompilować oba pliki do *object files*
|
|
|
a potem je skonsolidować. Skrypt powinien się nazywać `build.sh`, a wynikowy plik wykonywalny:
|
|
|
`ldist.e`.
|
|
|
|
|
|
Jeśli musisz, możesz przyjąć jakieś ograniczenie na długość słów wejściowych. Jeśli to robisz,
|
|
|
to zaimplementuj sprawdzanie długości i w przypadku przekroczenia - wypisz sensowny komunikat
|
|
|
o błędzie. Koniecznie zaimplementuj to w kolejnym (trzecim już) pliku źródłowym.
|
|
|
|
|
|
Zadanie 2.
|
|
|
---
|
|
|
To zadanie składa się wielu punktów i polega na wywoływaniu błędów kompilacji/linkowania:
|
|
|
|
|
|
1. spróbuj napisać program, w którym dwa różne pliki definiują tą samą zmienną. Skompiluj go na dwa
|
|
|
sposoby (tzn. tworząc oraz pomijając *object files*). Komunikaty o błędzie wraz z zaznaczeniem
|
|
|
etapu kompilacji (parsowanie/kompilacja/asemblacja/linkowanie) zapisz do pliku `1.txt`.
|
|
|
1. to samo, co w punkcie 1, tylko dwie funkcje. W pliku `2.txt` zawrzyj komunikaty o błędzie.
|
|
|
1. spróbuj zlinkować ze sobą niekompatybilne *object files*, np. jeden z nich skompiluj z flagą
|
|
|
`-m32`. Komunikat o błędzie trafia do pliku `3.txt`.
|
|
|
1. napisz program, który próbuje wywołać funkcję, której nie ma, ale tak udolnie, że błąd
|
|
|
pojawia się dopiero na etapie konsolidacji. Program ma być w pliku `4.cc` a błąd w `4.txt`.
|
|
|
|
|
|
Programy z punktów 1 - 3 także powinny się znaleźć w rozwiązaniu tego zadania, ale z dowolnymi
|
|
|
nazwami.
|
|
|
|
|
|
*Wskazówka do punktu 4: https://stackoverflow.com/questions/1410563/what-is-the-difference-between-a-definition-and-a-declaration*
|
|
|
|
|
|
|
|
|
Zadanie 3.
|
|
|
---
|
|
|
Plik binarny `a.o` zawiera funkcję `magic`, która ma następujący prototyp: `bool magic(long)`.
|
|
|
Stwórz plik `a.cc`, który będzie implementował funkcję `bool notmagic(long)`, która będzie zwracała
|
|
|
dokładnie to samo, co funkcja `magic`. Twoja implementacja nie może wywoływać funkcji `magic`, ani
|
|
|
zawierać wstawek assemblerowych.
|
|
|
|
|
|
|
|
|
Zadanie 4.
|
|
|
---
|
|
|
Pewna drużyna na sesji próbnej pewnego konkursu w programowaniu zespołowym się nudziła. Nudziła
|
|
|
się tak bardzo, że postanowiła jedno z zadań rozwiązać w assemblerze. Zadanie brzmiało tak: *Niech
|
|
|
`d(x)` oznacza liczbę dzielników liczby `x`. Wczytaj `n` i wypisz sumę `d(1) + d(2) + ... + d(n)`.
|
|
|
Liczba `n` spełnia warunki: `1 ≤ n ≤ 10^12`.* Pójdź w ślady tej drużyny i napisz program
|
|
|
w assemblerze, który rozwiąże to zadanie. Do oceny możesz przedstawić:
|
|
|
|
|
|
* plik `sol.asm`, który można zasemblować używając polecenia `nasm -felf64 sol.asm`, a później
|
|
|
zlinkować poleceniem `ld sol.o`, lub
|
|
|
* plik `sol.s`, który można zasemblować i zlinkować używając polecenia `gcc -no-pie sol.s`, lub
|
|
|
* plik `sol.cc`, który można skompilować używając polecenia `g++ sol.cc`.
|
|
|
|
|
|
Jeśli wybierzesz opcję trzecią, oczekuję że program będzie jedną wielką wstawką assemblerową. Jeśli
|
|
|
zrobisz opcję pierwszą, zyskasz mój szacunek.
|
|
|
|
|
|
*Wskazówka: https://www.felixcloutier.com/x86/, a tak konkretniej instrukcje `MOV`, `ADD`, `SUB`,
|
|
|
`MUL`, `DIV`, `CMP`, `Jcc`, `CALL` i pewnie kilka innych.*
|
|
|
|
|
|
*PS: Ta drużyna rozwiązała to zadanie wysyłając zgłoszenie w ostatniej minucie sesji próbnej.
|
|
|
Co ciekawe, program uruchomiony na komputerze, na którym drużyna pisała program, kończył się błędem
|
|
|
`Segmentation fault`, a mimo to sprawdzarka uznała zgłoszenie za poprawne. Czy potrafisz zgadnąć,
|
|
|
dlaczego?*
|
|
|
|