Elektroda.pl
Elektroda.pl
X
Proszę, dodaj wyjątek www.elektroda.pl do Adblock.
Dzięki temu, że oglądasz reklamy, wspierasz portal i użytkowników.

Drgania styków, silnik krokowy (Asembler) 89C2051

Woojek 13 Cze 2005 22:57 2652 19
  • #1 13 Cze 2005 22:57
    Woojek
    Poziom 10  

    Wykonałem sterownik do silnika krokowego na uP 89C2051 i do portów wejściowych uP zamontowałem switche. Problem w tym, że trzeba zlikwidować drgania styków. Pisze w aseblerze i nie wiem jak to napisać. Jeżeli ktoś będzie wiedział prosiłbym o napisanie przykładowego programu dla jednego przycisku (naciśnięcie przycisku powoduje pojawienie sie masy na porcie)

    0 19
  • #2 13 Cze 2005 23:13
    LordBlick
    VIP Zasłużony dla elektroda

    Uniwersalny sposób postepowania dla wszystkich mikrokontrolerów (note especially for jj ;)) :
    Masz w zapasie nieużywany timer liczący w dół (do 0) ? Przy każdym wciśnięciu ustawiasz timerek na jakąś wartość opóźnienia, np. 150ms. Z chwilą gdy timer osiągnie zero, przestaje liczyć. Tak więc przed sprawdzeniem czy przycisk naciśnięto, sprawdzasz wartość timera i sprawdzasz dalej przycisk, tylko, gdy timer jest wyzerowany. Ostatecznie można zaimplementować licznik programowy w procedurze przerwania od timera, umieszczając wartość takiego licznika w RAM.
    Pozdrawiam, Light'I

    0
  • #3 14 Cze 2005 08:29
    jj
    Poziom 19  

    Woojek napisał:
    Wykonałem sterownik do silnika krokowego na uP 89C2051 (...)


    Light'I napisał:
    Masz w zapacie nieużywany timer liczący w dół (do 0) ? (...)


    A czy w 89C2051 jest jakiś timer liczący w dół (a może nie doczytałem datasheet-a :wink:)?

    Pozdrawiam, jj.

    0
  • #4 14 Cze 2005 09:06
    fantom
    Poziom 31  

    A czy musi byc liczacy w dol ? Moze byc wszystko co pozwoli odmierzyc okreslony czas.Najlepiej zrobic sobie rejestr przesuwny w ktorym na poczatek wpychasz stan danego przycisku i patrzysz czy uzyskales stabilne 0 czy stabilna 1.

    0
  • #5 14 Cze 2005 09:18
    u24
    Poziom 13  

    a zwykla petelka w petelce nie da rady? - musisz odczekac kilka ms, zalezy czy masz jakis filterek na wejsciu.

    0
  • #6 14 Cze 2005 10:19
    diag
    Spec od samochodów

    Najczęstsze rozwiazanie sprzetowe to kondensator 100nF, jeżeli korzystasz z pul-up portu.

    0
  • #7 14 Cze 2005 10:35
    u24
    Poziom 13  

    ;-) - drogi diagu a co jesli nie kozystasz z pull-up?? czy najczeszcze rozwiazanie sprzetowe to nadal 100nF... czy tylko pull-up ma wplyw na stala RC??
    Panowie pozbadzmy sie mentalnosci szewca, to sie da policzyc!

    0
  • #9 14 Cze 2005 14:19
    LordBlick
    VIP Zasłużony dla elektroda

    jj napisał:
    A czy w 89C2051 jest jakiś timer liczący w dół (a może nie doczytałem datasheet-a :wink:)?
    Moja wypowiedź jest uniwersalna, nie wnikałem w cyferki i literki na obudowie, można ją zastosować do dowolnego mikrokontrolera. Wyrwałeś z kontekstu, bo dalej dodałem, co zrobić w wypadku, gdzy takiego licznika nie ma, lub jest zajęty. Czytaj ze zrozumieniem. Poprawka dotyczy słowa "zapacie" -> "zapasie", żeby nie było niedomówień... ;)
    Co do pozostałych sposobów :
    - Wszelkie pętelki są trudniejsze do ogarnięcia czasowo, ale jak kto woli. Przy zmianie oscylatora zmieniają się czasy i żeby wszystko się zgadzało, trzeba nop-ów nawtykać kazdej procedyrze oddzielnie... Uważam, ze jedyna prawidłowa pętla to pętla główna, pozostałe to jest marnotrawienie MIPS-ów, które często się przydają do wykonania innych zadań w miedzyczasie. Teraz praktycznie każdy procesorek ma układ czasowy i to z wywołaniem przerwania.
    - Kondensator z rezystorem - owszem, ale tylko na wejściach Shmitta, w pozostałych wypadkach pewien przedział napięć jest niedopuszczalny, gdyż powoduje zwiększony pobór mocy. No i po to się używa mikrokontrolera, aby zminimalizować ilość potrzebnych elementów, w końcu od czego jest program... ;)

    0
  • #10 14 Cze 2005 16:51
    Woojek
    Poziom 10  

    Wielkie dzięki, ale jeśli chodzi o drgania to potrzebuje rozwiązania programowego, a nie sprzętowego. W programie który chce napisać będzie 5 przycisków, które będą sterować odpowiednio silnikiem krokowym. Program ma rozpoznawać który przycisk został naciśniety i będzie eliminować problem drgania styków. Problem polega na tym, że nie wiem jak to napisać w asemblerze.

    0
  • #11 14 Cze 2005 17:13
    LordBlick
    VIP Zasłużony dla elektroda

    Nie opisałeś dokładnie sposobu obsługi, więc trudno o szczegółową odpowiedź... Przyciski obsługiwane niezależnie mają oddzielne liczniki, a zależnie - wspólne. Przy takiej ilości to pozostaje obsługa liczników programowych w przerwaniu timera. Reszta procedury w petli głównej sprawdzająca po kolei stan liczników i jeśli są wyzerowane dla danego przycisku, to sprawdza ona stan tego przycisku. Jak nie jest wciśnięty żaden przycisk, to zawsze się znajdzie coś innego do roboty...

    0
  • #12 14 Cze 2005 18:07
    Woojek
    Poziom 10  

    Z załączniku umieściłem dokładny schemat układu, który wykonałem. Przyciski zamontowane są odpowiedzialne za poszczególne ruchy silnika krokowego (przycisk ma reagować na zbocze opadające). P1- prawo 1, L1 - lewo 1, P10 - prawo 10, L10 - lewo 10. Nie znam się dobrze na asemblerze dlatego wdzięczny będę o podanie przykładu jak rozpoznawać, który switch został włączony oraz odrazu programowo wyeliminować drgania styków.

    0
  • Pomocny post
    #13 14 Cze 2005 21:45
    michal10022
    Poziom 10  

    rozumiem że odczytujesz stan zera po styknięciu z masą więc ja bym zrobił tak
    wciskasz a procedurka zaczyna działać (np; port p1.6)
    jnc p1.6,czekaj
    ljmp nie_wcisnienty
    czekaj:
    mov b,#100
    ok_50_ms:
    mov a,#220
    djnz acc,$
    djnz b,ok_50_ms
    jnc p1.6,dalej
    dalej:
    -
    -
    nie_wcisnienty:


    po wciśnięciu klawisza czyli zczytaniu pierwszego zakłucenia wywołującego zero na wejściu procek czeka około 50 mili s. i sprawdza jeszcze raz

    Dodano po 6 [minuty]:

    a i ściągnołem ten twuj projekt
    sterowania silnikiem krok ,nieobraz się ale bardziej skolmplikowany to on niemoże już być
    ja sterowałem zwykłyumi tranzystorami npn w układzie inwertera lub jak kto woli (oe)
    jak by co to wal na meila hwdp-22(malpa)wp.pl

    0
  • #14 14 Cze 2005 21:49
    GienekS
    Poziom 32  

    To jest jedno z moich rozwiązań klawiatury:

    Code:
    ;Procedura obslugi klawiatury
    
    ;w R2 licznik klawisza
    ;w OLDK stara wartosc klawisza
    ; OLDK=R7
    GET_KEY:
       setb   P3.3
       acall   ACK
       acall   PIKER
       mov   C,ACC.3   ;in TxON
       mov   P3.2,C   ;out TxON
       ACALL   KEY
       MOV   A,R2
       JZ   NIE_K   ;brak klawisza
       acall   KOD_K
       CJNE   A,7,JEST_K
    NIE_K:   MOV   R7,A
       AJMP   GET_KEY
    JEST_K:   MOV   R7,A
       acall   KLIK
       push   acc
       acall   CLS
       pop   acc
       clr   STAT.7   ;bit urzytkownika
       clr   STAT.6   ;bit dla gruchy
       cjne   a,#12,JEST_1
       ret
    JEST_1:   clr   PSW.5
       RET
    ;
    KEY:   ORL   P1,#7fh
       MOV   R2,#0
       XRL   P1,#1
       ACALL   LINIA
       JC   GK   ;jest klaw. w linii
       XRL   P1,#3
       ACALL   LINIA
       JC   GK
       XRL   P1,#6
       ACALL   LINIA
       JC   GK
       MOV   R2,#0
    GK:   RET
    ;
    LINIA:   MOV   R1,#4
       MOV   A,P1
       CPL   A
       rlc   A
    L7:   INC   R2
       rlc   A
       JC   GK   ;jest klawisz
       DJNZ   R1,L7
       RET
    ;Tabela KODow Klawiatury
    KOD_K:   movc   a,@a+PC
       ret
       db   10,7,4,1,11,8,5,2,12,9,6,3
    ;dla klawiatury telefonicznej 10 zamienia sie z 12

    0
  • #15 14 Cze 2005 23:42
    jj
    Poziom 19  

    Light'I napisał:
    jj napisał:
    A czy w 89C2051 jest jakiś timer liczący w dół (a może nie doczytałem datasheet-a :wink:)?
    Moja wypowiedź jest uniwersalna, nie wnikałem w cyferki i literki na obudowie, można ją zastosować do dowolnego mikrokontrolera. Wyrwałeś z kontekstu, bo dalej dodałem, co zrobić w wypadku, gdzy takiego licznika nie ma, lub jest zajęty. Czytaj ze zrozumieniem. Poprawka dotyczy słowa "zapacie" -> "zapasie", żeby nie było niedomówień... ;)
    (...)


    Ależ czytam ze zrozumieniem. Kolega Woojek podał konkretny typ mikrokontrolera i zapewne oczekiwał pomocy w rozwiązaniu problemu właśnie dla niego. Czy wspomniałeś gdzieś, że Twoja wypowiedź jest uniwersalna? Z tekstu to nie wynika, a "moja wróżka ma dzisiaj wolne" :wink:
    A co do wyrwania z kontekstu - czy nie dodałem na końcu cytatu magicznych znaczków (...)? Myślę, że czytający ze zrozumieniem wiedzą, co one znaczą.

    0
  • #16 15 Cze 2005 03:01
    Woojek
    Poziom 10  

    michal10022 napisał:

    a i ściągnołem ten twuj projekt
    sterowania silnikiem krok ,nieobraz się ale bardziej skolmplikowany to on niemoże już być
    ja sterowałem zwykłyumi tranzystorami npn w układzie inwertera lub jak kto woli (oe)
    jak by co to wal na meila hwdp-22(malpa)wp.pl


    Wielkie dzięki, wykorzystam i po testuje ten przykład. Co do złożoności projektu, potrzebny jest uP, ponieważ w projekcje jest przywidziana łączność z komputerem. Sterownik silnika ma współpracować i wykonywać polecenia z interfejsu napisanego w Borland C++Builder .

    0
  • #17 15 Cze 2005 04:41
    shg
    Specjalista techniki cyfrowej

    Ajamamototakie ;)
    Wrzucam cały główny program + include, bo nie chce mi się go ciąć, ot leń ze mnie i tyle ;)
    Przy okazji w ramach gratisu"wieczny" kalendarz na lata 2000-2255 obliczający dzień tygodnia (procedura calc_weekday) w zdaję się mniej niż 100 cykli, a nie jakieś badziewie z AVT, które potrzebuje na to kilku sekund(!). No i jeszcze pare pierdółek - w sumie to jest część wypasionego zegara LCD z kontrolerem PLL do nadajnika.

    Tabuacja jest na 4. W ramach mojego "zboczenia" lingwistycznego wszystkie komentarze są po angielsku ;)

    Obsługa klawiatury jest mieszana: wszystko, co jest związane z odmierzaniem czasu jest w przerwaniu timera0 (zaczyna się od etykiety noclock)
    Cała "logika" jest w głównej pętli programu zaraz na początku (etykieta main)

    Najpierw do zmiennej buttons ładowane są stany odczytane z linii portu (aliasy BLEFT, BRIGHT itd. to właśnie linie portów odpowiadające poszczególnym przyciskom) Taki sposób odczytu czyni program bardzo uniwersalnym - można w tym miejscu wstawić dowolną procedurę odczytującą stany klawiszy.

    Dalej jest cała logika - na podstawie stanów przycisków i pozostałych zmiennych odnoszących się do klawiatury "składana" jest zmienna bexec, określająca, które funkcje należy wykonać (specjalnie napisałem "które", bo program radzi sobie z dowolną ilością klawiszy wciśniętych naraz). Poszczególne bity zmiennej bexec odpowiadają funkcjom przyporządkowanym do klawiszy. I tak - jeżeli klawiszowi odpowiada bit 3 w zmiennej buttons, to po jego naciśnięciu zostanie ustawiony bit 3 w zmiennej bexec.

    Na podstawie zawartości bexec wywoływane są procedury obsługi poszczególnych klawiszy.

    Algorytm jest dość zawiły, ale jakoś pokrótce postaram się opisać przynajmniej jak działa z punktu widzenia użytkownika, w rzeczywistości wygląda to nieco inaczej.

    Przede wszstkim - każdemy przyciskowi z osobna można przypisać funkcję autopowtarzania (zmienna bautorep)
    Przyciski zachowują się tak jak klawiatura komputera - jeżeli dla przycisku uaktywniona jest funkcja autopowtarzania, to po pierwszym naciśnięciu natychmiast wywoływana jest odpowiadająca mu funkcja, potem przycisk pozostaje nieaktywny przez czas określony przez stałą iclock2d (jednostką jest 10ms, ale można zmienić). Po upłynięciu tego czasu, jeżeli przycisk jest wciąż wciśnięty, funkcja wywoływana jest ponownie. Od tej pory wywoływanie powtarza cię co okres wyznaczony przez stałą iclock2r (jednostka 10ms), aż do momentu, gdy klawisz zostanie zwolniony.
    Dla klawiszy, które nie mają funkcji autopowtarzania procedura wywoływana jest tylko raz po naciśnięciu klawisza i przytrzymywanie go nie pomaga ;)
    Jeżeli aktualnie powtarzany jest jakiś klawisz (autopowtarzanie) i wciśnięty zostanie kolejny, to ten jeden raz opóżnienie autopowtarzania dla przytrzymywanego klawisza będzie równe iclock2d zamiast iclock2r. takie uproszczenie w niczym nie przeszkadza, a i program nie musi być dzięki temu niepotrzebnie rozbudowany.
    W momencie, gdy klawisz zostaje zwolniony rozpoczyna się odmierzanie czasu "martwego" (stała iclock0 jednostka 0.25ms, domyślnie 40ms), przez który przycisk nie reaguje na naciskanie.
    Wszystkie właściwości klawiatury można modyfikować "w locie", dotyczy to zarówno funkcji autopowtarzania, jak i czasów opóźnień, z tym że te ostatnie należało by w tedy zapisywać jako zmienne, a nie stałe.

    Całość jest tak zorganizowana, że praca programu nie jest przerywana, całe odmierzanie czasu odbywa się w tle.
    No i zastosowany algorytm eliminuje "za jednym zamachem" drgania powstałe zarówno przy naciskaniu, jak i zwalnianiu klawisza.
    W tej wersji obsługiwane jest maksymalnie 8 klawiszy, dodanie kolejnych sprowadza się do powtórzenia kilka razy (po jednym na każde 8 klawiszy) tego samego kodu (a właściwie tylko "logiki" i małej modyfikacji przerwania)

    Żeby wykorzystać procedurę we własnym programie trzeba wyciąć wszystko od etykiety main do komentarza "Clock and date incrementing", oraz wszystkie fragmenty, do których kod ten sie odwołuje (przerwanie!). Ważna jest też procedura inicjalizująca zmienne.

    Przerwanie wywoływane jest co 250µs, można z powodzeniem użyć innej częstotliwości, trzeba wtedy tylko dobrać odpowiednio stałe opóźnień.

    The Koniec

    0
  • #18 15 Cze 2005 17:51
    Woojek
    Poziom 10  

    Układ 89C2051 ma 2 porty (P1,p3) wejścia/wyjścia. Z projektu, który przedstawiłem wyżej switch-e załączyłem do portu p3, a diody do portu wyjściowego. Z dokumentacji układu jest podane, że obydwa porty są I/0. Czy ktoś wie jak ustawić programowo w asemblerze, alby port P3 był portem wejściowym, a port P1 wyjściowym??

    Czy ktoś zna jakiś program, ktory jest dobrym symulatorem oraz by była możliwość pisania w nim programu w asemblerze??

    0
  • #19 15 Cze 2005 18:34
    LordBlick
    VIP Zasłużony dla elektroda

    Pozostawiasz w stanie 1 (pullup) wszystkie piny, które są wejściami.

    0
  • #20 16 Cze 2005 17:13
    Woojek
    Poziom 10  

    Dzięki wszystkim za odpowiedz na temat eliminacji problemu eliminacji styków drgań.
    Przy pisaniu dalszej części programu pojawił się problem:
    Jak wiadomo silnik krokowy można sterować 3 typami pracy. Pisze teraz program, który będzie umożliwiał sterowanie falowe (A -> B -> Not A -> Not B). Układzie, który przedstawiłem wyżej są 5 przycisków (port: P3.2 – obrót 1 w prawo, P3.3 – obrót 1 w lewo, P3.4 – obrót 10 w prawo, P3.5 – obrót 10 w lewo, P3.7 – zmiana szybkości obrotu silnika 250ms, 1s). Po naciśnięciu odpowiedniego przycisku ustawiam w dowolnej komórce pamięci wartość ilości kroków jak ma wykonać silnik. Chciałbym napisać podprogram, który będzie zaczytywał wartość komórki pamięci i odpowiednio wykonywał sekwencje obrotu silnika. Nie wiem jak to napisać i jak ktoś będzie wiedział to będę wdzięczny za podpowiedzi albo przykłady.

    0