Następna strona Poprzednia strona Spis treści

4. METAPROGRAMOWANIE/MAKROPRZETWARZANIE

Assemblacja programów jest nudna, ale do krytycznych części programów.

Powinieneś używać właściwego narzędzia do właściwego zadania, więc nie wybieraj assemblacji kiedy nie jest stosowna; C, OCAML, perl, Scheme, mogą być lepszym wyborem dla większości twojego programowania.

Jakkolwiek, są wypadki gdy te narzędzia nie dają ci wystarczającej kontroli nad maszyną, i assemblacja jest wtedy użyteczna i konieczna. W takich wypadkach, docenisz system makroprzetwarzania i metaprogramowania które pozwolą ci wracać do raz przygotowanych wzorców z których każdy z nich jest przygotowany jako wielokrotna definicja, co pozwala bezpiecznie programować i automatycznie przechodzić modyfikację takich wzorców itd. "Goły" assembler jest często niewystarczający, nawet jeśli chcesz robić tylko małe operacje w połączeniu z C.

4.1 Co jest zintegrowane w powyższym

Tak, wiem że ta sekcja nie zawiera użytecznych informacji. Masz swobodę do prowadzenia jej, jeśli odkryjesz coś ciekawego...

GCC

GCC pozwala (i wymaga) wyspecyfikować ograniczenia rejestrów w twoim kodzie ``inline assembly'', więc optymalizer zawsze wie o tym. W ten sposób, assemblacja kodu inline jest tak naprawdę realizowana przez wzorce, a nie wymuszana.

Później możesz umieścić twój kod assemblera w makrach CPP, i funkcjach inline w C, więc każdy może użyć go jako funkcje w C lub makro.

Funcje inline są bardzo podobne do makr, ale są czasami czystsze w użyciu. Strzeż się tych wypadków, kod będzie zduplikowany, tak więc tylko lokalne etykiety (w stylu 1:) powinny być definiowane w kodzie assemblera. Jakkolwiek, makro powinno pozwolić nazwie dla nie lokalnej etykiety być przekazaną jako parametr (lub inaczej, powinienes używać dodatkowych meta-programowych metod). Zapamiętaj także, że rozejście się kodu jako inline assemblera będzie potencjalnie rozprowadzał nim błędy, więc uważaj dokładnie w kwestii ograniczeń rejestu w kodzie inline asm.

Ostatecznie, język C w sobie może być rozważany jako dobra abstrakcja programowania w assemblerze, co przyniesie ci ulgę z większością kłopotów z assemblacją.

Strzeż się pewnych optymalizacji które zawile przekazują argumenty do funkcji; przez rejestry mogą powodować niedopasowanie tych funkcji do wywołań z zewnętrznych (w szczególności ręcznie napisanego kodu assemblera) funkcji w standardowy sposób; atrybut "asmlinkage" może chronić funkcję przed kłopotami z taką flagą optymalizacyjną; obejrzyj źródła jądra linux-a dla przykładów.

GAS

GAS ma możliwość włączania pewnych makr, jak opisano w dokumentacji texinfo. Oprócz tego, podczas gdy GCC rozpoznaje pliki .s jako surowy assembler do wysłania do GAS, także rozpoznaje pliki .S jako pliki do przepuszczenia przez CPP przed wpuszczeniem ich do GAS. Znowu, znowu, zobacz źródła Linux-a dla przykładów.

GASP

Dodaje wszelkie użyteczne dodatki makroassemblacji do GAS. Obejrzyj jego dokumentację texinfo.

NASM

NASM także zawiera pewne wsparcie makr. Zobacz dokumentację. Jeśli masz jakieś dobre pomysły, możesz chcieć skontaktować się z autorami, jako, że oni aktywnie go rozwijają. W międzyczasie, zobacz poniżej zewnętrzne filtry.

AS86

On także ma trochę prostego wsparcia makrami, ale nie mogłem nigdzie znaleźć dokumentacji. Teraz źródła są bardzo przejrzyste, więc jeśli jesteś zainteresowany, łatwo powienieneś je zrozumieć. Jeśli potrzebujesz więcej niż tylko bazę, powinieneś użyć zewnętrznego filtra (zobacz poniżej).

INNE ASSEMBLERY

4.2 Zewnętrzne Filtry

Jakiekolwiek jest wsparcie makr twojego assemblera, lub jakikolwiek język używasz (nawet C !), jeśli język nie jest dla ciebie wystarczająco wyrazisty, możesz chcieć przepuścić pliki przez zewnętrzny filtr z regułami w Makefile takimi jak te:


%.s:    %.S other_dependencies
        $(FILTER) $(FILTER_OPTIONS) < $< > $@

CPP

CPP nie jest bardzo wyrazisty, ale wystarczający do wielu łatwych rzeczy, jest standardem, i jest przezroczyście wywoływany przez GCC.

Dla przykładu jego ograniczeń, nie możesz deklarować obiektów, takich że destruktory wywoływane automatycznie na końcu deklarowanego bloku; nie możesz więc zmieniać kierunki widoczności, itd.

CPP przychodzi wraz z kompilatorem C. Jeśli mógłbyś robić to bez niego, nie zawracaj sobie głowy przynoszeniem CPP (chociaż myślę jakbyś mógł).

M4

M4 daje ci pełną moc makroprzetwarzania, z językiem równym Turingowi, rekursją, wyrażeniami regularnymi, itd. Możesz robić wszystko czego CPP nie.

Zobacz macro4th/This4th z ftp://ftp.forth.org/pub/Forth/ in Reviewed/ ANS/ (?), lub źródła Tunes 0.0.0.25 jako przykłady zaawansowanego makroprogramowania z użyciem m4.

Jakkolwiek, jego niefunkcjonalna semantyka cytowania i odcytowywania zmusza cię do używania jawnego ogonkowo-kontynuacyjno-przejściowego (przyp. tłum.) stylu makr jeśli chcesz robić zaawansowane makro programowanie (czego przypomnieniem jest TeX -- BTW, czy ktoś próbował używać TeX-a jako makroprocesora do czegoś innego niż typesetting ?) To NIE jest gorsze niż CPP, który nie pozwala na cytowanie i rekursję.

Właściwą wersją m4 jest GNU m4 1.4 (lub późniejsza jeśli istnieje) która zawiera większość składników i mniej błędów lub ograniczeń. m4 został pomyślany jakko wolny do czegokolwiek ale prosty w użyciu, może być więc nadal dobry dla większości programów w assemblerze (chyba nie piszesz programów z milionami linii w assemblerze?).

Makroprzetwarzanie z twoim własnym filtrem

Możesz pisać twój własny prosty filtr rozszerzający makra z użyciem zwykłych narzędzi: perl, awk, sed, itd. To jest szybki sposób i możesz wszystko kontrolować. Ale oczywiście, moc makroprzetwarzania musi coś kosztować.

Metaprogramowanie

Zamiast używania zewnętrznych filtrów które rozszerzają makra, jedną z dróg jest pisanie programów, które piszą część lub całość innych programów.

Dla przykładu, mógłbyś użyć programu produkującego kod źródłowy

Pomyśl o tym!

Część wspomagająca z dostępnych kompilatorów

Kompilatory takie jak SML/NJ, Objective CAML, MIT-Scheme, itd, mają własną część wspomagającą assembler, którą możesz ale nie musisz wykorzystywać, jeśli zamierzasz generować kod półautomatycznie z wymienionych języków.

Zestaw narzędzi Machine-Code z New-Jersey

Jest projekt, używający języka programowania Icon, do budowy podstawowych rzeczy do produkcji manipulacji na kodzie assemblera. Zobacz http://www.cs.virginia.edu/~nr/toolkit/

Tunes

Projekt Tunes OS rozwija swój własny assembler jako rozszerzenie języka Scheme i jako część procesu rozwojowego. Nie działa to jeszcze, ale pomoc jest widziana.

Assembler manipuluje symbolicznymi drzewami składni, więc możesz prawie mieć podstawę do translacji składni assemblera, disassembler, wspólną część wspomagającą assembler/kompilator, itd. Także, pełna moc języka Scheme czyni go nie do pokonania z makroprzetwarzaniem/metaprogramowaniem.

http://www.tunes.org/


Następna strona Poprzednia strona Spis treści