1
Programowanie
niskopoziomowe
dr inż. Paweł Pełczyński
ppelczynski@swspiz.pl
2
Literatura
Randall Hyde: „Asembler. Sztuka
programowania”, Helion, 2004.
Eugeniusz Wróbel: „Praktyczny kurs
asemblera”, Helion, 2004.
W prezentacji wykorzystano zdjęcia ze
stron:
http://pl.wikipedia.org
http://www.dis.uniroma1.it/~iocchi/stereo/
3
Cechy programowania
niskopoziomowego
Programowanie niskopoziomowe wymaga od
programisty znajomości sprzętu, w szczególności
architektury mikroprocesora.
Programy są pisane w języku pozwalającym na
bezpośrednie odwołania do rejestrów
mikroprocesora, portów I/O i pamięci systemu
– zazwyczaj jest to asembler.
Programowanie w języku niskiego poziomu
wymaga doświadczenia, jest czasochłonne
i narażone na błędy.
4
Uzasadnienie potrzeby
programowania
niskopoziomowego
Programowanie niskopoziomowe pozwala
na najdalej idącą optymalizację kodu
pod względem szybkości wykonania
lub objętości programu.
5
Zastosowania programowania
niskopoziomowego
Tworzenie sterowników i programów startowych
Pisanie elementów jądra systemu operacyjnego
Pisanie programów dla mikrokontrolerów o bardzo
ograniczonych zasobach
Tworzenie silnie zoptymalizowanych aplikacji dla tzw.
systemów wbudowanych
Realizacja wydajnych aplikacji dla systemów
przetwarzania sygnałów i obrazów (DSP)
Programowanie procesorów wektorowych, np. GPU
6
Zastosowania programowania
niskopoziomowego
Tworzenie sterowników i programów startowych
Przykładem takiego oprogramowania jest system BIOS
umieszczony w pamięci nieulotnej płyty głównej
komputera PC. Jego zadaniem jest:
konfiguracja i inicjalizacja pracy układów wchodzących
w skład systemu
załadowanie do pamięci i uruchomienie programu
ładującego system operacyjny
utworzenie programowej abstrakcji sprzętu,
pozwalającej na ujednolicone odwołania aplikacji
programowych do urządzeń, niezależnie od ich budowy
(funkcje i przerwania BIOSu)
7
Zastosowania programowania
niskopoziomowego
Pisanie programów dla
mikrokontrolerów o bardzo
ograniczonych zasobach
Mikrokontrolery są jednoukładowymi
komputerami, często stosowanymi do
sterowania sprzętem elektronicznym
powszechnego użytku. Ze względu na
wymaganie małego kosztu ich zasoby
są silnie ograniczone, co wymaga
tworzenia wysoce zoptymalizowanych
aplikacji programowych. Wysoki koszt
tworzenia aplikacji w języku
niskopoziomowym jest uzasadniony
produkcją wielkoseryjną sprzętu.
8
Zastosowania programowania
niskopoziomowego
Tworzenie silnie
zoptymalizowanych aplikacji
dla tzw. systemów
wbudowanych
Podobnie, jak poprzednio,
wysoki koszt tworzenia
aplikacji w języku
niskopoziomowym jest
uzasadniony produkcją
wielkoseryjną sprzętu.
9
Zastosowania programowania
niskopoziomowego
Realizacja wydajnych aplikacji
dla systemów przetwarzania
sygnałów
i obrazów (DSP)
Niektóre aplikacje wymagają
dużej mocy obliczeniowej, by
mogły realizować postawione
zadania w czasie rzeczywistym.
Osiąga się to przez
zastosowanie specjalizowanych
procesorów sygnałowych (DSP)
oprogramowanych w
asemblerze.
10
Zastosowania programowania
niskopoziomowego
Programowanie procesorów
wektorowych, np. GPU
Programowanie procesorów
wektorowych, np. procesorów
graficznych, wymaga specyficznego
podejścia, ze względu ma
możliwość przetwarzania wielu
danych w jednej instrukcji. W tym
celu zostały opracowane
specjalizowane języki niskiego
poziomu.
11
Języki programowania
niskopoziomowego
Pierwsza generacja - Język wewnętrzny
(maszynowy).
Druga generacja - Język symboliczny (asembler).
Języki symboliczne wysokiego poziomu pozwalające
na operowanie na fizycznych rejestrach, portach i
pamięci komputera, posiadają cechy języków
niskiego poziomu – pozwalają na tworzenie
programów o podobnej funkcjonalności.
12
Język wewnętrzny
Język wewnętrzny (maszynowy) jest definiowany
operacjami realizowanymi przez mikroprocesor
Lista instrukcji jest zbiorem wszystkich operacji
wykonywanych przez mikroprocesor
Odpowiednio uporządkowany ciąg instrukcji
stanowi program – kod maszynowy
13
Język wewnętrzny - wady
Reprezentacja instrukcji za pomocą kodów
liczbowych
Trudne tworzenie i poprawianie programu
Wymagana jest dobra znajomość danej platformy
sprzętowej
14
Język symboliczny - asembler
Asemblery są językami powstałymi na bazie języka
maszynowego danego mikroprocesora przez
zastąpienie kodów instrukcji nazwami
symbolicznymi – mnemonikami
Asembler jest językiem niskiego poziomu, jedno
polecenie asemblera odpowiada zazwyczaj
jednemu rozkazowi mikroprocesora
15
Asembler - cechy
Mnemoniczne nazwy operacji
Operowanie symbolicznymi nazwami adresów danych i
etykiet
Możliwość stosowania makrooperacji
Możliwość łatwiejszego modyfikowania programu
16
Asembler – składnia linii
programu
[etykieta:] [instrukcja [argument1 [, argument2...]]][; komentarz]
Etykieta jest symboliczną nazwą adresu instrukcji
Przykład:
laduj:
mov ax, $20A4 ; załaduj do rejestru ax daną szesnastkową 20A4
Program napisany w języku asemblera wymaga asemblacji –
przetłumaczenia na kod maszynowy.
Program tłumaczący jest także nazywany asemblerem.
17
Asembler – makrooperacje
Często powtarzający się ciąg instrukcji można zastąpić tzw.
makroopperacją
Makrooperację definiuje się przez umieszczenie ciągu instrukcji
między poleceniami: macro nazwa i endm
Przykład:
macro mnoz_int x, y
mov ax, x
; załaduj do rejestru ax pierwszą daną
mov bx, y
; załaduj do rejestru ax drugą daną
imul;
endm
...
mnoz_int a, b ; makro użyte w programie
...
18
Program tłumaczący - translator
Kompilator języka symbolicznego (asemblera)
tłumaczy program na kod maszynowy
Proces kompilacji jest tutaj nazywany asemblacją, a sam
kompilator – asemblerem.
19
Cechy Języka C
B.Kernighan, D. Ritchie 1971
Język C jest językiem „względnie niskopoziomowym”
wśród języków strukturalnych. Posiada następujące
cechy:
Nie sprawdza rozmiaru pamięci przydzielonej na tablice
Pozwala alokować pamięć, nie podając typu danych w niej
przechowywanych
Pozwala na manipulację portami komputera na niskim poziomie
Ze względu na te cechy został zastosowany do napisania elementów
systemu operacyjnego UNIX