Usuwanie nieużywanych funkcji z programu
W trakcie tworzenia biblioteki do obsługi wyświetlacza 7 segmentowego (7 segmentów+kropka) doszedłem do wniosku, że najbardziej eleganckie rozwiązanie to stworzenie osobnego pliku C dla tej biblioteki, wraz z nagłówkami z prototypami funkcji jak i z konfiguracją. Niestety napisanie kilku funkcji ustawiających liczbę na wyświetlaczu spowodowało znaczny rozrost programu - nieużywane funkcje, często bardzo obszerne, trafiły do pliku *.o a następnie do wygenerowanego HEXa zajmując miejsce, pomimo iż nie wszystkie były używane.
Po przetrząśnięciu kawałka internetu znalazłem rozwiązanie, którego efekty są naprawdę znaczące (usunięcie zbędnych funkcji potrafi zaoszczędzić dużo miejsca gdy korzystamy z bibliotek zawierających funkcje na każdą okazję), i w związku z tym warte powtórzenia w wielu innych programach - pozwoli to uniknąć ręcznego usuwania nieużywanego kodu z "biblioteki".
Ustawienie kompilatora
Aby móc usuwać nieużywane funkcje, muszą one w pliku wynikowym kompilatora być odrębnymi częściami. Zachowanie takie wymusza dodatkowy argument w poleceniu kompilatora:
-ffunction-sections
Dodanie takiej komendy w projekcie przy użyciu Makefile:
CFLAGS += -ffunction-sectionsPrzy korzystaniu z Środowiska Eclipse dla AVR należy z kolei polecenie dodać w ustawieniach projektu.
Z menu Eclipse wybieramy Project -> Properties,
następnie odnajdujemy C/C++ build -> Settings.
I przy wybranym configu Release, w zakładce Tool Settings wybieramy Optimizations z zakładki AVR Compiler. W polu Other Optimizations flag dopisujemy nasze "-ffunction-sections"Ustawienia linkera
Poprzednio dodane polecenie umieści każdą funkcję w osobnej części pamięci - sekcji. Teraz pozostaje poinformowanie linkera, iż sekcje nie używane mają zostać usunięte - umożliwia to polecenie przekazane do linkera -gc-sections (gc od garbage collector). Tego również można dokonać poprzez plik Makefile lub ustawienia projektu.
Dla Makefile wystarczająca modyfikacja to
-Wl,-gc-sectionsZ kolei w Eclipse będąc już w Project -> Properties-> C/C++ build -> Settings ->(Release) Wchodzimy w zakładkę AVR C Linker->General, i dodajemy polecenie "-Wl,-gc-sections"
U mnie taka modyfikacja ustawień pozwoliła na przykład usunąć jedyną funkcję używającą arytmetyki zmiennoprzecinkowej, zamieniając 2,5kB programu w 600bajtów.


Wrzesień 22nd, 2009 - 07:31
Dokładnie tak samo można zrobić z danymi, które nigdzie nie są używane – „-fdata-sections”
4\/3!!