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

XMega 128A1 - Kilka działań matematycznych następujących po sobie (ASM)

ASMnauka_ 05 Sty 2017 19:12 954 12
  • #1 16175471
    ASMnauka_
    Poziom 15  
    Cześć i szczęśliwego nowego roku.
    Borykam się z kwestią uproszczenia kilku działań.
    Może najpierw przykład.
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod

    Czyli odejmowanie od siebie dwóch liczb jedno bajtowych.
    Mnożenie dwóch liczb jedno bajtowych (wynik liczba dwu bajtowa).
    Dodanie do siebie liczby dwu bajtowej i liczby jedno bajtowej.
    Czy istnieje możliwość skrócenia tych operacji ?
    Pozdrawiam
  • #2 16176045
    kamyczek
    Poziom 38  
    To jest zwykła matematyka jak potrafisz uprościć wielomian uprościsz zapis w asemblerze tylko co tu upraszczać jak tam są operacje zajmujące pojedyncze cykle zegara ?
  • #4 16176710
    Konto nie istnieje
    Konto nie istnieje  
  • #5 16176882
    jnk0le
    Poziom 18  
    Z MUL jest taki problem że wynik ląduje w R0:R1 (dla kompilatora jest to dodatkowy koszt MOVW+CLR).
    A to mnożenie dwóch liczb jednobajtowych wygląda mi na mnożenie jednej liczby przez 2.
  • #6 16176990
    Konto nie istnieje
    Konto nie istnieje  
  • #7 16177085
    kamyczek
    Poziom 38  
    jnk0le napisał:
    Z MUL jest taki problem że wynik ląduje w R0:R1


    Tak jest ale jak się dobrze zastanowisz to jaki masz problem w tym że wynik jest w r0 i r1 ? . Nie wiem jak to jest w c więcej pewnie napisze Piotruś bo to jego klepka . Ja się nie przywiązuję do rejestrów i jak zależy mi na czasie to co mi przeszkadza że wynik jest w r0 i r1 traktuje je jako zmienna i nigdzie nie przenoszę tylko robię swoje dalej o ile nie potrzebują niczego innego w międzyczasie pomnożyć . Poza tym jeśli w trakcie operacji na zmiennych odkładasz je do ramu czy na stos możesz odłożyć wynik z r0 i r1 a zdjąć do r24 i r25 i zmienna wróci na miejsce a wykonasz to w trakcie operacji którą i tak musiałeś wykonać czyli nie stracisz żadnego cyklu . Sztuczek jest wiele a tym bardziej w asemblerze ale wszędzie wszystko ma jakąś graniczę możliwości optymalizacji .
  • #8 16177996
    ASMnauka_
    Poziom 15  
    Piotrus_999 napisał:
    A dlaczego od razu nie użyłeś mnożenia?

    Ależ to jest mnożenie.
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod
    jnk0le napisał:
    A to mnożenie dwóch liczb jednobajtowych wygląda mi na mnożenie jednej liczby przez 2.
    Tak, rozkaz ROL łącznie z LSL jest wykorzystywany do mnożenia dwóch liczb przez dwa.
    Piotrus_999 napisał:
    Dlatego kompilatory dobierają sobie do potrzeb:
    Zauważ, że tak, czy owak w przykładach które podałeś trzeba załadować
    (wpisać) do rejestrów mnożną i mnożnik (R2 do R31).
    W przypadku mojego przykładu musiał bym do rejestru R19 załadować mnożnik.
    Czyli
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod
    , a następnie dopiero pomnożyć zawartość rejestru R18 przez R19
    Kod: AVR assembler
    Zaloguj się, aby zobaczyć kod

    kamyczek ma rację, bez problemu można skopiować zawartość R0+R1 do dowolnej pary rejestrów (poczynając od parzystego np. R6+R7 R2 do R31) a następnie dokonywać dowolnych działań na zawartości tej pary rejestrów.
    Co więcej:
    MOVW = 1 cykl
    PUSH = 1 cykl
    POP = 2 cykle
    Tak więc o ile tylko mamy nie wykorzystaną jakąkolwiek parę rejestrów (za wyjątkiem R0+R1) lepiej jest skopiować zawartość R0+R1 do tej pary rejestrów.
  • #9 16178101
    kamyczek
    Poziom 38  
    Ja bym się jeszcze zastanowił nad jednym czy zanim skończysz te działania ,które robisz będziesz używał gdzieś mnożenia lub koniecznie r0 i r1 , jeśli nie , to potraktuj że tam masz zmienna i rób działania na r0 i r1 a jak skończysz to wynik umieść tam gdzie chcesz go mieć nie stanowi różnicy czy dodajesz do pary r0,r1 czy do pary r19,r20 . Zasada jest prosta rób to co musisz a rejestry traktuj jak lokalizację zmiennej . Pomnożyłeś cos wynik masz w r0 i r1 chcesz do niego dodać r16 to dodaj do r0 i r1 i dalej wynik masz w r0 i r1 jaką widzisz różnice gdzie masz ten wynik , bo ja żadnej . Nie musisz deklarować ze para rejestrów jest zmienną 16 bitową o nazwie zmienna16 . i nie musisz dbać żeby ona była akurat we wskazanej parze rejestrów .
  • #11 16178265
    Konto nie istnieje
    Konto nie istnieje  
  • #12 16178267
    kamyczek
    Poziom 38  
    I o to właśnie chodziło żeby nie kopiować i nie robić zbędnych operacji , dlatego napisałem rób to co musisz wymaga to zmiany przyzwyczajeń ale w wielu przypadkach skraca znacząco długość kodu i czas jego wykonywania .
  • #13 16178317
    ASMnauka_
    Poziom 15  
    Piotrus_999 napisał:
    pytanie tylko po co.
    Ale co po co ?
    Piotrus_999, jak sam zauważysz w przykładach które podałeś kompilator użył MOVW, czy potrzebne jest to kopiowanie ?
    jnk0le napisał:
    Z MUL jest taki problem że wynik ląduje w R0:R1 (dla kompilatora jest to dodatkowy koszt MOVW+CLR).

    Otóż to :D
REKLAMA