Ostatnio opowiadałem dlaczego moim zdaniem warto nauczyć się asemblera . Dzisiaj natomiast opiszę jak u mnie wyglądał proces nauki. Oczywiście musicie brać poprawkę, że przypadało to na okolice roku 2010 i dzisiaj mamy już nieco inne możliwości.

Niemniej jednak mam nadzieję, że lektura okaże się ciekawa i wyniesiecie coś dla siebie również w dzisiejszych realiach.

Typowe zajęcia z asemblera

Tak na poważnie zacząłem poznawać asemblera na studiach. Najpierw były zajęcia z asemblera. Takie typowe jak chyba każdy przechodził – asembler x86, pisaliśmy jakieś kalkulatory, czy printowanie choinki z gwiazdek na konsolę.

Główną trudnością nie było samo zrozumienie asemblera. Jednym z problemów było przestawienie się na sposób obsługi wypisywania danych na konsolę, odczytywania klawiatury itp. Korzystało się tam z przerwań BIOS i podawało się odpowiednie function code. Przerwanie 0x10, przerwanie 0x13 – te tematy. Kto pisał tego typu programy, ten wie. A kto nie wie – może zobaczyć w Wikipedii.

Zachowany plik z laborek – wypisywanie daty systemowej.

To jeszcze było do ogarnięcia, ale drugi problem był jeszcze gorszy. Nigdzie nie mieliśmy listy dostępnych komend asemblerowych. A wygooglowane komendy czasem działały czasem nie. Architektura x86 zawiera wiele komend asemblerowych, do tego przez lata była rozbudowywana i dochodziły kolejne instrukcje. Na pewno dało się to jakoś przedstawić, ale my nie mieliśmy dostępu do dobrej listy komend.

Dlatego modyfikowaliśmy przykłady od prowadzącego. Używaliśmy tylko komend pokazanych na zajęciach. Czasem jakaś komenda z google zadziałała i od razu wszyscy od siebie ściągali listingi. To było bez sensu. Do dzisiaj mam przez to trochę uraz do asemblera x86. A moim największym problemem jest właśnie ta lista komend. Szczególnie, że potem mieliśmy na studiach asemblera i architekturę komputerów z prawdziwego zdarzenia.

Asembler z prawdziwego zdarzenia

Dzięki temu miałem później solidne fundamenty do pracy w embedded. U nas na Politechnice Gdańskiej na Automatyce na wydziale ETI była cała seria przedmiotów w tym temacie ciągnąca się przez wiele semestrów. I prawie wszystkie prowadził dr Raczyński.

Często pojawiają się pytania czy warto iść na studia. Jaka jest różnica między osobami po studiach, a samoukami. Wydaje mi się, że właśnie przygotowanie pod względem architektury procesorów i programowania niskopoziomowego jest jedną z rzeczy, które trudno, szczególnie na początku, ogarnąć samemu.

A co to znaczy z prawdziwego zdarzenia?

Mieliśmy całą teorię wałkowaną wiele razy. Wszystkie elementy procesora, szyny danych, kontrolery przerwań, pamięci itp. A potem to wszystko powtarzane w praktyce.

Symulator asemblera

Na ćwiczeniach pamiętam projekt własnego asemblera na fikcyjną uproszczoną architekturę procesora. Musieliśmy napisać własny symulator. Dodawanie instrukcji było dosyć toporne – wyklikiwało się przyciskami. W ten sposób nie trzeba było implementować interpretowania tekstu wszystkich możliwych błędów na wejściu. Mieliśmy określoną listę dostępnych instrukcji, podglądanie stanu rejestrów i pracę stepową z podanym kodem. Super ćwiczenie i bardzo wiele rozjaśniało w głowie.

Tak wyglądała moja aplikacja symulatora

Na pewno pisanie kompilatorów interpreterów emulatorów itp nie jest najprostszym podejściem do nauki programowania, ale daje bardzo dużo głębokiej wiedzy. I nie jest to tylko moje zdanie. Oto kilka przykładów:

Też zresztą pisałem na studiach własny kompilator – mój ulubiony przedmiot. Dzięki czemu wiem jak to wszystko działa pod spodem. Owszem, bez tego również umiałbym generować kolejne strony kompilowanego tekstu w IDE. Ale… byłbym mniej świadomym programistą. Taką wiedzę warto posiadać. Bez studiów: nie posiądziesz jej (nie twierdzę że się nie da, tylko że nie znajdziesz na to chęci i czasu).

W tej książce jest opisane tworzenie własnego interpretera, własnej architektury procesora i wiele innych rzeczy. Świetna lektura, ale na pewno nie łatwa.

Asembler AVR

Mieliśmy też laborki na AVR z pisaniem programów w asemblerze. I tam odkryłem super rzecz. Jednak w asemblerze jest cywilizacja. Można mieć PDFa z listą wszystkich dostępnych instrukcji i opisem ich działania. Nie trzeba się uczyć na pamięć mnemoników, a jak nie pamiętasz – zostaje tylko metoda prób i błędów i google.

Lista instrukcji Atmegi 16 wzięta z dokumentacji

Potem też pisałem w AVR Studio 4 w symulatorze. To było jeszcze zanim AVR Studio było na Visualu. Wcześniej miało swój okienkowy IDE w stylu bardziej z 2000 roku. Ale bardzo mi się podobał podgląd graficzny stanu rejestrów i praca krokowa. Robiłem w symulatorze całkiem skomplikowane programy z kilkoma peryferiami, przechodziłem wszystko krokowo i patrzyłem co się zmienia. Po danej instrukcji można było zobaczyć np. jakie flagi się zmieniają, czy moje przewidywania były dobre. To kolejny super sposób nauki.

Moim zdaniem AVR jest bardzo dobry do początkowej nauki asemblera. Szczególnie jeżeli możemy podglądać działanie naszego kodu zarówno na symulatorze jak i na gotowym sprzęcie.

Większy projekt

Po początkowych sukcesach wpadłem w euforię. Uważałem, że asembler to najlepszy możliwy język, wszystko da się w nim napisać, można podejrzeć jak wszystko działa. Od razu widać wszystkie błędy. Owszem tych instrukcji trzeba naklepać sporo, ale potem wszystko po prostu działa. Do tego jeszcze ta satysfakcja, poczucie że udało się zrobić coś trudnego i działa.

Potem oczywiście zostałem brutalnie sprowadzony na ziemię. I to szybko. Już przy kolejnym projekcie na studiach. Chciałem napisać w asemblerze projekt z Systemów Czasu Rzeczywistego. System miał sterować hodowla roślin – monitorować temperaturę, nasłonecznienie, wilgotność itp. Używał kilku peryferiów ADC, I2C, EEPROM. Co mogło pójść nie tak?

Dzisiaj wydaje mi się to śmieszne. Ale projekty na studiach to była taka piaskownica, gdzie można było realizować nawet głupie pomysły i nic złego się nie stało. Najwyżej okazywało się, że nie tędy droga i stracimy trochę czasu. Ale za to lekcja zostanie na długo. I tak było w tym przypadku.

Tak wygląda projekt za duży do asemblera. Screeny z zachowanego sprawozdania.

Próbowałem napisać większy system w ASM. Samodzielnie zaprojektować metody przekazywania argumentów, przechowywania stanów, wywoływania funkcji, podział na moduły i pliki. Czyli warstwy abstrakcji, API, biblioteki. Pamiętam, że szukałem informacji na forach. Na Forbocie (który wtedy jeszcze nazywał się Dioda) był gość, który mi mega pomógł i miał sporo postów o asemblerze. Zapamiętałem, że miał avatara z dark templarem ze Starcrafta. A jego nick to Zaquadnik czy jakoś tak.

A potem i tak co chwilę się okazywało, że trzeba coś dodać, coś zmienić, zrobić refactor i to wpływało na kilka plików. Ostatecznie się poddałem, przeszedłem na C, gdzie miałem gotowe biblioteki, projekt już trochę znałem. Z takim przygotowaniem implementacja okazała się banalna i zajęła 1-2 dni.

Lista plików w projekcie
Próby tworzenia API i dokumentacji w asemblerze

Można więc powiedzieć, że miałem przyspieszoną lekcję ewolucji języków programowania ze szczególnym naciskiem na argumenty za powstawaniem nowych języków wyższego poziomu. Wartość edukacyjna nieoceniona. Od tej pory doceniałem nie tylko zrozumienie niskopoziomowe asemblera, ale również dobrodziejstwa abstrakcji, API, interfejsów itp.

Oczywiście przez to fascynacja asemblerem mocno przygasła. W końcu okazał się zupełnie niepraktyczny.

Pragmatyzm

Później jeszcze do inżynierki potrzebowałem bootloader na Atmegę. Tam było kilka możliwych rozmiarów bootloadera. Jak dobrze pamiętam 512B 1024 i 2048. Oczywiście musiałem się zmieścić w najmniejszy. Nie żebym potrzebował całego miejsca na płytce – tutaj chodziło o ambicję.

Ale ostatecznie zwyciężył pragmatyzm. Okazało się, że jest gotowy projekt bootloadera – BLIPS i mieści się w najmniejszym rozmiarze bootloadera. Projekt był polecany na forum AVR Freaks. Kto bawił się embedded w tamtych czasach, na pewno kojarzy taką stronkę.

Projekt na inżynierkę – wtedy już wiedziałem, żeby nie pisać wszystkiego w ASM.

Jedyne co musiałem zrobić, to dodać obsługę komend z powyższej tabelki w aplikacji na PC. Ale do tego już asemblera nie potrzeba.

Czyli na bazie własnych doświadczeń doszedłem do najbardziej praktycznego użycia asemblera. Większość Projektu była napisana w C. W asemblerze potrzebowałem jakiś konkretny fragment. A ostatecznie okazało się, że nawet nie muszę go pisać samemu – sprawę załatwiłem przy pomocy gotowca.

A o swojej inżynierce kiedyś opowiadałem na live na YT:

Podsumowanie

Tak wyglądała u mnie nauka asemblera na studiach. Były wzloty i upadki. Ale na pewno doprowadziły ostatecznie do solidnego poznania tematu. Razem wiedzą o różnych wadach i zaletach. Po takiej ścieżce zdrowia na pewno nie bałem się później asemblera w komercyjnych projektach. A jednocześnie potrafiłem do niego podejść pragmatycznie.

A jak to było u Was? Jak wspominacie te przedmioty na studiach? Czy był przydatne? Czy pomogły Wam później w pracy zawodowej? Koniecznie podzielcie się swoimi opiniami w komentarzach!

A jeżeli temat asemblera Cię interesuje – pracuję właśnie nad kursem asemblera z praktycznymi przykładami na STM32. I możesz wpłynąć na treść kursu jak i materiałów na YT i blogu. Wystarczy, że wypełnisz ANKIETĘ.