logo elektroda
logo elektroda
X
logo elektroda
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

ATmega - Optymalizacja kodu assembler dla obsługi UART

yanan 30 Maj 2016 20:16 957 6
  • #1 15709882
    yanan
    Poziom 10  
    Witam

    Chciałbym zoptymalizować kod pod względem zajętości pamięci konkretnie chodzi mi o obsługę UARTU. Nie wiem ile dokładnie pamięci zyskam (pewnie 2 bajty, ale chciałbym się też czegoś nowego przy okazji nauczyć)

    Generalnie mam 2 funkcje

    Kod: C / C++
    Zaloguj się, aby zobaczyć kod

    Według noty Atmel
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod

    Niestety cały czas walczę z pierwszą funkcją i wyszło mi coś takiego
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod


    Chyba zaczynam rozumieć dlaczego tak mało ludzi programuje w czystym ASM.
    Jak widać na załączonym kodzie pomoc mile widziana.
    Pozdrawiam
  • #2 15709918
    Konto nie istnieje
    Konto nie istnieje  
  • #3 15709924
    grko
    Poziom 33  
    @yanan
    Skompiluj swój kod za pomocą avr-gcc z opcją -S. Wtedy kompilator skończy na generacji kodu asemblerowego. Przykładowo:

    Kod: Bash
    Zaloguj się, aby zobaczyć kod


    Zobacz sobie jaki kompilator wygenerował kod i odpowiedz sobie szczerze czy warto się bawić w asemblera.
  • #4 15709936
    yanan
    Poziom 10  
    Rozumiem, korzystając z okazji jakie są dobre praktyki do tworzenia timeoutów? Może jakiś przykład?

    Wiele osób tak robi, więc uznałem to za rozwiązanie poprawne
    Przykład pierwszy z brzegu
    https://gist.github.com/rms95/5887356
  • #5 15709976
    Konto nie istnieje
    Konto nie istnieje  
  • #6 15710012
    tmf
    VIP Zasłużony dla elektroda
    @yanan Sposób na timeouty jaki masz jest ok, jakbym miał się czegoś przyczepić to tego, jak odróżnisz odebranie 0xff od timeouta w twojej funkcji?
    Oczywiście najogólniej robienie odbioru danych z wolnych interfejsów typu UART za pomocą poolingu to porażka na całej linii. Zdecydowanie należałoby użyć przerwań interfejsu UART, co w połączeniu z timerem niejako automatycznie daje ci timeout. Zaleta jest taka, że nie blokujesz procka na czas odbioru znaków. Robienie poolingu zażyna każdy procek, sprowadzając go wydajnościowo do pierwszych 4-bitowych mikroprocesorów...
    Nie walcz też o bajty - to nie ma sensu. Poświęcisz miesiąc na jakieś dziwne optymalizacje, zamiast skończyć w tym czasie projekt. W dodatku pisząc w C skompiluj większy program dwoma różnymi wersjami gcc - nie zdziw się, jeśli różnice długości kodu wynikowego sięgną 10 i więcej %. Skup się na pisaniu poprawnego kodu C, resztę zostaw kompilatorowi i nie staraj się go wyręczać.
  • #7 15710069
    yanan
    Poziom 10  
    Timeout jest mi potrzebny do przeskoku do początku pamięci w programie ładującym. Na ogół w "normalnym" programie używam przerwań, tutaj mikrokontroler nie ma co innego do roboty :) Przy obsłudze wyświetlaczy LED w trybie multipleksowanym taka obsługa UARTU spowodowałaby miganie wyświetlacza (jak nie gorzej). Co do kompilatora, to muszę powiedzieć, że masz rację są różnice w kodzie wynikowym w zależności od wersji, ale nie badałem jeszcze który tworzy najbardziej optymalny...
REKLAMA