Elektroda.pl
Elektroda.pl
X

Search our partners

Find the latest content on electronic components. Datasheets.com
Elektroda.pl
Please add exception to AdBlock for elektroda.pl.
If you watch the ads, you support portal and users.

[Solved] BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów

Elektromechanik88 22 Apr 2020 23:02 528 9
  • #1
    Elektromechanik88
    Level 3  
    Witam.
    Mam problem z dziwnym zachowaniem lcd podczas realizacji programu.
    Program pisałem już dość dawno, kiedy uczyłem się jeszcze podstawowej obsługi timerów. Ale, że problem się zaczął pojawiać również w innym moim programie, postanowiłem napisać na forum, bo nie wiem co robię źle.

    Posiadam płytkę ewaluacyjną do atmegi32 i atmegi8 oraz kilka wyświetlaczy lcd 2x16 i 4x16 i na wszystkim pojawia się ten sam problem, więc wykluczam problemy ze sprzętem.

    Program wyświetla cztery zegary, z których jeden z wybranych miga i można go zmniejszać/zwiększać przyciskami.
    Podczas zliczania czasu w przerwaniu na lcd pokazują się tzw. artefakty, zrzuty zegara pojawiające się w różnych miejscach tam nie zdefiniowanych, lub miganie/drganie jakiegoś segmentu z zegarów.
    Na lcd 4x16 zauważyłem że na 4 dolnym wierszu zrzut pokazuje się najczęściej i albo z lewej albo z prawej strony w zależności z której ustawię miganie zegara.

    Załączam film na którym widać dziwne zachowanie:
    covert.mp4 Download (21.55 MB)


    Program miał być zaczątkiem do zrobienia wielopoziomowego menu, w którym pozycja wybrana w menu miała po prostu migać.

    kod:
    Code: vbnet
    Log in, to see the code

    Podczas przerabiania tego programu zauważyłem, że kiedy z programu wyrzucę przerwanie lub procedurę migania wybranego zegara Zegar_miga na wyświetlaczu problem ustaje.


    Mam wrażenie, że nie można zrobić menu z zaznaczeniem elementu na takiej zasadzie przy takich słabych uC.
    Na forum elektroda menu wielopoziomowe było realizowane tak, że zaznaczany element miał przy sobie jakiś znaczek wskazujący

    Czy ktoś był by mi w stanie pomóc rozwiązać ten problem?
    Kamery 3D Time of Flight - zastosowania w przemyśle. Darmowe szkolenie 16.12.2021r. g. 10.00 Zarejestruj się
  • Helpful post
    #2
    bart-projects
    Level 23  
    Forum Elektroda ma swój player i możliwość takiego dodawania filmu do postu żeby się wyświetlił i nikt nie musi niczego ściągać. Takie czasy, że każdy się dwa razy zastanawia zanim coś ściągnie i uruchomi na swoim komputerze. Umieszczając film w playerze zwiększasz szansę że ktoś go obejrzy ;)

    Co do oprogramowania to całkowicie podstawową sprawą jest umieszczenie dyrektyw $hwstack, $swstack i $framesize. Bez tego to szkoda czasu na analizę oprogramowania. Lepiej naucz się je umieszczać w kodzie.
  • Helpful post
    #3
    LED5W
    Level 33  
    Sprawdź co się dzieje w symulatorze. Z filmu wynika, że objaw występuje tuż po resecie, więc powinno być łatwiej.
  • #4
    Elektromechanik88
    Level 3  
    Witam.
    Kolega bart-projects ma rację odnośnie Playera na elektroda, faktycznie jest coś takiego, i jako nowy forumowicz tego nie zauważyłem, że jest:)
    W kwestii konfiguracji początkowej stosów również.
    Sam odkryłem 4 dni temu, że jak wstawię
    Code: vbnet
    Log in, to see the code
    na początek to program działa poprawnie.

    Code: vbnet
    Log in, to see the code


    Dziwi mnie, że inne moje programy działały bez tego, widocznie domyślna konfiguracja wystarczyła.

    Tylko nie rozumiem jak obliczać wartości
    Code: vbnet
    Log in, to see the code
    by były optymalne dla działania programu i zbyt nie zżerały ramu, którego jest niewiele , czy istnieją jakieś programy do kalkukacji tego?

    Dodano po 47 [minuty]:

    Quote:
    Sprawdź co się dzieje w symulatorze. Z filmu wynika, że objaw występuje tuż po resecie, więc powinno być łatwiej.


    Co do bascomowego symulatora to działa on u mnie bardzo wolno, a Hardware simulator wyświetla jakieś bzdury

    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów

    po 5minutach
    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów
  • Helpful post
    #5
    bart-projects
    Level 23  
    To pewnie wynika z tego że powstało dużo różnych AVR`ów. Jeśli na początku ktoś korzystał tylko z jednego typu to mógł sobie w IDE ustawić konfigurację dla stosów a nawet wyświetlacza LCD czy I2C. Stąd dla wstecznej kompatybilności dalej tak można zrobić.
    Na przykład ustawienia dla stosów są tutaj tylko moje są już zmienione bo mogę szybko wkleić to do kodu ("Add to code") i mam jakiś minimalny setup w którym mogę sobie potem zmienić uC lub parametr który chcę bez musu wpisywania słów "$framesize" etc.

    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów

    Zauważ, że Twoja Mega32 lub Mega328P mają ponad 2tyś bajtów SRAM`u ...aż tak szczypać się nie musisz. To jest mało dopiero jak chcesz odpalić AVR-DOS bo potrzebujesz na obsługę kart 1500B i na program zostaje tylko 512B... Do takich zadań lepiej wziąć Mega644P, Mega2560 czy Mega1284 która już ma 16KB SRAM :D

    Co do ustawień...Bascom ma wbudowany CodeExplorer. Włącz go w View->Code Explorer. Tam jest wiele podpowiedzi takich jak minimalne zapotrzebowanie na stosy i ErrorChecker at Runtime :D czyli cos co sprawdza i pokazuje błędy jeszcze przed kompilacją.

    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów

    Normalnie do obsługi przerwania Bascom potrzebuje około 32B SRAM z $hwstack do tego skok do jakiegoś Sub potrzebuje 2B dla adresu powrotu. Jeśli w Sub wołasz inny Sub to już się robi 4B a takie procedury jak Lcd "" to tez oddzielny, wewnętrzny Sub Bascom. Dlatego CodeExplorer pokazuje po lewej $Hwstack = 6 a musisz w pamięci dodać 32 na obsługę przerwania... Jak widzisz 38 to byłoby minimum...a ja mam zapas :D
    Na bajty przekazywane do Sub jako Byval czyli ich kopie też potrzebne są bajty tylko że z $Swstack. Ty tam chyba w jednym przekazujesz trzy zmienne...
    $framesize jest jakby podręcznym RAM dla Bascoma. W tej ramce Bascom łączy różne stringi lub je wysyła na LCD i tym podobne operacje.
    Jak na przykład chcesz do napisu "lektroda" dodać "E" na poczatku to on robi najpierw kopie do $framesize "E" i dodaje "lektroda" i dopiero takim zmienionym łańcuchem zamienia "lektroda" na 'Elektroda". Z tego powodu ramka musi być przynajmniej tak duża jak największy string jaki obrabiasz w programie.
    Standardowo ramka ta ma minimum 24 a jak widzisz ja tu tez mam jakiś zapas, ale tę ramkę powiększam najczęsciej....

    Na stronie MCS (nie Forum tylko mcselec) jest zakładka "Application notes". Tam znajdziesz np opracowanie na temat stosów. Tytuł coś w stylu "reveal secrets of stacks" - nie pamietam dokładnie.
    Jest też specjalana biblioteka która wysyła na serial port wartości minimalne które używa program.
    Ogólnie to trzeba troche nabrać wprawy. Jak wiesz ile masz wolnego SRAM - a Code Explorer podpowiada (w tym programie pokazuje 95% wolne z moimi ustawieniami) - to możesz sobie ustawić coś na wyrost i się nie martwić... wyższa szkoła jazdy to oprogramować coś na Tiny13 z 64B SRAM :D

    Co do symulatora to działa dobrze - pewnie coś nie tak robisz ;) a błąd który pokazuje CodeExplorer w Twoim kodzie tyczy się tego, że składnia Config Lcd = 16 * 4" jest przestarzała i powinna brzmieć "Config Lcd = 16x4"
  • Helpful post
    #6
    LED5W
    Level 33  
    Elektromechanik88 wrote:
    Co do bascomowego symulatora to działa on u mnie bardzo wolno, a Hardware simulator wyświetla jakieś bzdury
    Symulację można przyśpieszyć dodając $sim, ale działa to przez usunięcie opóźnień, więc może zmienić zachowanie. W każdym razie polecam przyjrzeć się co się dzieje w pamięci RAM. Tutaj ładny rysunek, pokazujący jak jest podzielona. A tutaj dokładniej pokazane w symulatorze. Program uruchamiaj krokowo, przerwanie timera możesz wywołać wcześniej (jest do tego nawet przycisk).
  • #7
    Elektromechanik88
    Level 3  
    Dzisiaj troszkę posiedziałem nad tymi stosami, zapoznałem się nieco z tym opracowaniem.
    Próbowałem również rozgryźć tabelkę "SRAM" w symulatorze bascom.
    Z opracowania i zachowania symulatora wydedukowałem że obszar w sram na $hwstack jest na najwyższych dostępnych adresach pamięci sram i zwiększa się on do dołu(niższych adresów), więc na początku metodą prób i błędów wartość sprzętowego stosu ustawiłem aż zostawiłem 48 Bajtów, zauważyłem że jak dawałem mniej to stos sprzętowy zaczął nachodzić na stos programowy i program się wysypywał.
    W symulatorze tabelka SRAM, 3 najwyższe adresy miały najwięcej ruchu stąd 3 adresy po 16Bajtów każdy, wyszło 48B na stos sprzętowy (proszę się nie śmiać, te stosy to dla mnie nowość, choć trochę już bawię się bascomem w wolnym czasie :D )

    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów
    Code: vbnet
    Log in, to see the code


    Gorzej natomiast jest z obliczaniem stosu programowego i ramki
    Wiem, że stos pr. oblicza się do największego suba, funkcji tzn tego co przyjmuje najwięcej parametrów funkcji, zmiennych, wywołan lcd, print, itd.

    Stos pr. jest po stosie sp. licząc od najwyższego do niższego adresu i rusza się wolniej od tamtego :)

    Niby jest to objaśnione w “Reveal the secret of Stack” BASCOM-AVR - Part 1 "
    Ale tylko w podstawach

    Jak obliczenia się mają do tej procedury:
    Code: vbnet
    Log in, to see the code


    są tutaj 3 parametry do procedury, 2 przypisania str(x) do zmiennych Sek_maska, min_maska 2 przypisania format(x,x), warunki if...then, locate i lcd

    No i ramka $framesize (najmniej ruchliwa ;) ) jak policzyć do tej procedury co podałem.


    Co do Code Explorer to nie mam tego w bascomie 2.0.7.3 i składnia Config Lcd = 16*4 nie robi różnicy mojemu kompilatorowi
  • Helpful post
    #8
    bart-projects
    Level 23  
    Następna podpowiedź :P Na otwartym oknie Bascom wciśnij na klawiaturze F1 żeby otworzyć okno Help`a
    W zakładce Index wpisz "$DBG" i może tam znajdziesz odpowiedź na Twoje pytanie :P

    W języku C jeśli zmiennej nie zainicjujesz jakąś wartością to ona ma nieustaloną wartość, więc jeśli chcesz żeby miała zero to musisz napisać np. "char myChar = 0". W Bascom jest inaczej. Wszystkie zmienne na początku programu są inicjowane wartością 0. Dlatego niepotrzebne jest pisanie "Dim myByte As Byte" a niżej "myByte = 0" bo to już zrobił za nas kompilator.
    Jak użyjesz dyrektywy $DBG to stosy będa nadpisane innymi niż zero wartościami FFFFFFF HHHHHH i SSSSSSS :D
    Każda inna wartość tam w symulatorze oznacza, że to miejsce było potrzebne. Potem masz Stack Analyser i nawet przycisk Advise ;)
  • #9
    Elektromechanik88
    Level 3  
    Dziękuję super podpowiedź dzięki niej udało się ustalić optymalne wartości dla ramki hw i sw.
    Dyrektywa $DBG faktycznie bardzo przydatna można nią wyliczyć wartości stosów dla całego programu, albo dla jakiejś jednej funkcji/procedury.
    Po utworzeniu pliku .log można użyć stack analizera, no i super :)

    Niestety nie sprawdza się dla rozbudowanych programów mających ponad 1000 linii kodu, terminal UART w symulatorze jest ograniczony do 1000 linii i nadpisuje po przekroczeniu tej wartości a program dalej jeszcze nie zakończył cyklu, nie wiem jak to wygląda na sprzętowym uart-cie bo nie mam w kompie rs232, ale jak najbardziej można przeanalizować w ten sposób każdą funkcję po kolei w programie i wyliczyć na stack analyser.

    fff, sss, hhh można obserwować w symulacji pamięci sram, tylko proszę mi powiedzieć jak to do końca rozumieć zajętość bajtów na tych stosach, tzn.
    BASCOM, AVR, Timer0, dziwne zachowanie LCD alfanum. przy wyświetlaniu zegarów

    stan zajętego miejsca z ustawionej granicy na którymś ze stosów oznacza się hhhh, ssss, ffff czy tymi ruchomymi znaczkami na samym dole obrazka "ń%^..<"
  • #10
    Elektromechanik88
    Level 3  
    Dziękuję za pomoc, w rozwiązaniu tego problemu.
    Problemem okazało się złe ustawienie stosów w programie.

    Zamykam temat.