Skocz do zawartości

Elvis

Użytkownicy
  • Zawartość

    2596
  • Rejestracja

  • Ostatnio

  • Wygrane dni

    189

Wszystko napisane przez Elvis

  1. Właśnie ten warunek raczej nigdy nie będzie prawdziwy... i dlatego program wchodzi do pętli for od nowa. Powinno być if (t==7), albo i zupełnie bez tego if-a.
  2. Tak, stos musi być zawsze wyrównany do 4, czyli dwa najniższe bity mają wartość zero. Czasem musi być też wyrównywany do 8.
  3. Może po prostu przetestuj, wtedy będziesz wiedział czy poprawnie wyrównuje, czy nie. Z tego co piszą o cortex-m powinno działać, ale może faktycznie ktoś, czegoś nie dopilnował i jest błąd - w sumie nie pierwszy i nie ostatni w bibliotekach.
  4. Nie wnikałem tak bardzo w wyrównywanie stosu na stm32, bo jak chodzi o tak niskopoziomowe programowanie zajmuję się cortex-a, a nie cortex-m. W każdym razie bardzo wątpię, żeby to co próbujesz zrobić było problemem. Przeczytaj sobie chociażby programming manual od stm32f10x: https://www.st.com/resource/en/programming_manual/cd00228163-stm32f10xxx20xxx21xxxl1xxxx-cortexm3-programming-manual-stmicroelectronics.pdf "Unless stack alignment is disabled, the stack frame is aligned to a double-word address. If the STKALIGN bit of the Configuration Control Register (CCR) is set to 1, stack align adjustment is performed during stacking." Czyli jeśli nie wyłączyłeś wyrównywania to działa - a jak nie to zgłoś do ST że mają błąd. Wyrównywanie stosu oczywiście ma sens. Sprzętowo odkładane są rejestry, stos jest wyrównywany do 4, rejestry mają po 4 bajty, więc wszystko jest ok. Problemem jest dopiero kompilator. W przypadku cortex-a procedura obsługi przerwania jest pisana w asemblerze i wtedy wyrównanie do 4 jest wystarczające. Natomiast w przypadku cortex-m, procedury obsługiwania najczęściej pisze się w C, a kompilator zakłada że stos podczas wywołania jest wyrównany do 8. Jeśli nie jest to wygenerowany kod może działać niepoprawnie. Nie znajdziesz raczej opisów kiedy taki kod powstaje bo to zależy od wszystkiego - wersji kompilatora, bibliotek, ustawień itd. Najmniejsza zmiana i możesz dostać odrobinę inny kod wynikowy, który już będzie działał. Ale żeby wyjaśnić na czym polega problem, wyobraźmy sobie następujący zupełnie sztuczny przykład. Mamy dwie zmienne lokalne, czyli jak wiemy zapisane na stosie, powiedzmy: uint32_t x,y; Teraz kompilator generuje kod odczytu powiedzmy x ldr r0, =<adr_x> Teraz można sobie do tego x pisać, czytać itd. wykorzystując adres zmiennej zapisany w rejestrze r0. Ale jak kod będzie chciał odwołać się do y, to musi obliczyć adres. Pewnie zrobiłby to inaczej, ale załóżmy że na danym systemie najszybciej działają proste operacje bitowe. Skoro kompilator zakłada, że stos jest wyrównywany do 8, więc adres zmiennej x ma najniższe bity równe 0. Mógłby więc wygenerować taki kod: orr r1, r0, #4 Czyli do r1 wpisać (r0 or 4) - to zadziałą poprawnie jeśli x będzie miał adres wyrównany do 8, a po nim będzie y. Ale jeśli stos będzie wyrównany do 4, ten sam kod już zadziała źle. To oczywiście absolutnie sztuczny przykład, ale chodziło mi o pokazanie na czym polega problem - kompilator, albo raczej optymalizator zakłada że stos jest wyrównany do 8. Może więc wygenerować dziwny, ale optymalny kod, który działa tylko wtedy. A jeśli nie będzie wyrównywania to wszystko się posypie.
  5. Znalazłem hat grove z którym mi się pomyliło: https://www.seeedstudio.com/GrovePi.html Nazwa podobna, a na nim wszystkie moduły są podpinane do atmegi, więc właściwie wychodzi z tego arduino podłączone do raspberry. Ale ten moduł z zestawy jest tańszy i prostszy, więc pozwala trochę lepiej poznać samą malinkę. Tylko trzeba pamiętać że pracuje tylko z 3.3V, a niektóre moduły grove wymagają 5V. Edit: Zestaw do nauki elektroniki to chyba faktycznie najlepszy pomysł - proponowałbym nawet więcej, na razie zamówić tylko ten zestaw, przerobić kurs, porobić trochę własnych eksperymentów. Będziesz wtedy wiedział lepiej co Cię interesuje i na co wydać resztę pieniędzy.
  6. Edit: Wcześniej nie miałem czasu dokładnie przejrzeć informacji akurat o tym shieldzie, a widziałem podobne z atmegą na pokładzie, gdzie wszystko było sterowane przez mikrokontroler. Tutaj wydaje się że jest lepiej, na pokładzie jest stm32f030, który służy głównie jako konwerter analogowo-cyfrowy, natomiast sporo pinów jest podpiętych bezpośrednio do malinki. Taki układ wygląda dużo ciekawiej, przepraszam jeśli wcześniej zbytnio namieszałem.
  7. Niby tak, chociaż to bardzo górnolotne określenie w przypadku większości z tych czujników. Przykładowo moduł z diodą, to pod względem elektrycznym po prostu dioda i rezystor - można to podłączyć na płytce stykowej samemu. Oczywiście grove daje do tego płytkę pcb, gniazdko, wtyczkę i kabelek - więc jest znacznie solidniejsze niż stykówka. Ale to nadal tylko dioda i rezystor... Natomiast fizycznie ta dioda nie jest połączona z Raspberry, po drodze masz na shieldzie dodatkowy mikrokontroler, który faktycznie steruje tą diodą - więc właściwie raspberry jest niepotrzebne. Program na raspberry nie ma nic wspólnego ze sterowaniem pinami jak pokazywaliśmy podczas kursu, on po prostu przesyła do mikrokontrolera polecenie, co tamten ma wykonać. To jak z arduino - możesz je podłączyć do PC, arduino będzie sterowało diodą, a nie PC. Więc takie przykłady oczywiście będą fajne, ale nauczą Cię tylko jak korzystać z biblioteki Groove, nie dowiesz się z nich nic o tym jak działa Raspberry, ani jak sterować samemu nawet diodą. Jeśli jesteś miłośnikiem gotowych bibliotek, czy "warstw abstrakcji" to pewnie takie rozwiązanie będzie całkiem sensowne. Ale jeśli chciałeś dowiedzieć się czegoś o Raspberry, to obawiam się że mało przydatne.
  8. Może mi się pomyliło, w każdym razie na stronie gcc jest: "On ARMv7-M the interrupt type is ignored, and the attribute means the function may be called with a word-aligned stack pointer." https://gcc.gnu.org/onlinedocs/gcc/ARM-Function-Attributes.html A na ARM muszę poszukać, bo tam było chyba więcej sprzeczności (raz że potrzebny, innym razem że nie) Na stronie ARM: http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0774g/vvi1465810473505.html "In ARMv6-M, ARMv7-M, and ARMv8-M, the architectural exception handling mechanism preserves all processor registers, and a standard function return can cause an exception return. Therefore, specifying the interrupt attribute does not affect the behavior of the compiled output. However, ARM recommends using the interrupt attribute on exception handlers for clarity and easier software porting." Chociaż z tym gcc to chyba zły fragment - nie da się na szybko odpowiadać W każdym razie wpisanie w google attribute interrupt zwraca dość rozbieżne wyniki. Natomiast zgodnie z opisem np. w programming manual, na cortex-m3 sprzęt powinien obsługiwać wyrównywanie do 8.
  9. Jak nie wyrówna to mogą być błędy, bo kompilator zakłada zgodnie ze standardem że stos przy wywołaniu funkcji jest wyrównany do 8. Więc jeśli nie jest to może (ale nie musi) się coś popsuć. Nie wiem na której rewizji bazuje f103, trzeba sprawdzić, ale wątpię żeby to wyrównywanie było potrzebne - nawet na stronach ARM-a piszą że nie jest i atrybut nie ma znaczenia.
  10. Wyrównywanie oznacza, że wszystkie dane mają adresy podzielne przez pewną liczbę np. przez 4, albo przez 8. Dlaczego w AAPCS wybrano 8 tego nie wiem, bo dla 32-bitowego układu teoretycznie powinno wystarczyć 4. Możliwe że chodzi o to że niektóre instrukcje działają szybciej jeśli adres jest podzielny przez 8, a może o zgodność z 64-bitowymi układami? Nie znam dokładnego wyjaśnienia, ale ze standardami jest tak, że trzeba przestrzegać, nawet jeśli nie wszystko się o nich wie. Co do tego kodu generowanego przez kompilator to prawdopodobnie jest niepotrzebny, bo już sam sprzęt zapewni odpowiednie wyrównywanie - ale wyrównanie już wyrównanego stosu nic nie popsuje, chociaż zmarnuje trochę czasu i pamięci. W sumie nawet ciekawe co ten kod robi, możesz go przeanalizować i opisać, zawsze się czegoś nowego dowiemy.
  11. Nie wiem, czy wybrany zestaw groove to akurat najlepszy pomysł - w przypadku kursu na Forbocie, chcieliśmy pokazać jak za pomocą samej Malinki można komunikować się z (prostymi) peryferiami. Więc np. miganie diodą odbywa się bezpośrednio z poziomu Linux-a (i stąd te problemy z bibliotekami). Takie podejście wydawało nam się sensowne, bo pozwala poznać jak działa Linux na systemach wbudowanych. Natomiast zestaw groove posiada shield z mikrokontrolerem... czyli jest to po prostu Arduino podłączone do Raspberry. Oczywiście można się nim świetnie bawić i mieć dużo radości, ale to nie nauczy praktycznie niczego związanego z Raspberry, prawdopodobnie wygodniej byłoby kupić Arduino i podłączyć do PC.
  12. W starszych mikrokontrolerach (oraz nowszych mikroprocesorach) opartych o rdzeń projektowany przez ARM, procedura obsługi przerwań wymagała na początku i końcu specjalnego kodu. Można go było pisać ręcznie w asemblerze, albo pozwolić wygenerować odpowiedni kod kompilatorowi - i do tego służyło dodawanie atrybutu interrupt. Architektura ARMv7-M, na której opartych jest sporo współczesnych mikrokontrolerów w tym STM32F103 wprowadziła znaczne ułatwienie dla programistów, kosztem skomplikowania sprzętu (ale widocznie krzem jest teraz tańszy niż kiedyś). Obecnie sam sprzęt zajmuje się wszystkimi niezbędnymi operacjami na początku i końcu przerwania - czyli zachowaniem stanu rejestrów oraz wyrównaniem stosu. Bit STKALIGN pozwala na wyłączenie wyrównywania stosu, wówczas kod obsługi przerwania musiałby to wykonać albo być tak skompilowany, żeby działał poprawnie bez wyrównywania. Ogólnie stos w przypadku ARM i to nie tylko ARMv7M, jest zawsze wyrównywany do wielokrotności 4 bajtów. Natomiast standard AAPCS wymaga dodatkowo, żeby podczas wywoływania procedury stos był wyrównany do wielokrotności 8 bajtów. Jeśli bit STKALIGN jest wyzerowany, sprzęt sam zajmie się wyrównaniem stosu do wielokrotności 8 i przywracaniem jego stanu po zakończeniu obsługi przerwania. W przypadku ARMv7-M atrybut interrupt jest ignorowany przez kompilator, ale może być potrzebny jeśli użyjemy mikrokontrolera lub mikroprocesora opartego o innej architekturze. Gcc potrafi kompilować kod na bardzo różne układy, stąd pewnie informacja że atrybut jest wymagany (bo czasem jest )
  13. A tak z ciekawości zapytam - w czy napisany został Linux? Czy jego złożoność nie jest aby większa niż wielu aplikacji w pythonie? Bo jeśli przypadkiem napisany jest w C, działa całkiem wydajnie, ma ponad 20 lat, a pracowało nad nim więcej niż kilka osób to o czym cała ta dyskusja? Są banalne projekty w C i całkiem zaawansowane w pythonie, ale są i o wiele bardziej zaawansowane w C, czy asemblerze. Leczenie własnych kompleksów na forach internetowych chyba nie ma chyba sensu - niech każdy pisze mega fajne programy w jęzku, który zna i lubi oraz pozwoli innym wybierać inne rozwiązania.
  14. Proponuję zacząć od początku, czyli jaki mikrokontroler, która wersja CubeMX. Wbrew pozorom różne błędy pojawiają się w oprogramowaniu dla różnych modeli z rodziny STM32, w każdej wersji Cube niektóre są poprawiane, a pojawiają się nowe. Więc może zamiast zgadywać warto ustalić o czym piszemy. Druga sprawa to "wygląda to tak że program wychodzi z funkcji HAL_I2C_Master_Transmit ( zwraca HAL_BUSY lub HAL_ERROR ) i dopiero potem następuje zwis i nie wiem co w tym momencie procesor robi." - możesz to nieco rozwinąć? Piszesz że używasz debuggera, a później nie wiesz co procesor robi - czyli nie możesz zatrzymać wykonywania, nastąpił reset, program jest w miejscu gdzie się nie spodziewałeś czy o co chodzi? Przy okazji warto sprawdzić czy nie jest winne to co pojawia się w programie po wywołaniu HAL_I2C_Master_Transmit - może wstaw tam nieskończoną pętlę i zobacz czy wtedy wszystko działa. Bo może błąd jest w zupełnie innym miejscu kodu? Edit: pisaliśmy w tej samej chwili - w każdym razie warto ustalić o którym modelu mikrokontrolera piszemy. Natomiast odnośnie zawieszenia - wygląda jakby wykonywany był reset, stąd następne pytania: czy używasz watchdoga, z jakiej płytki korzystasz?
  15. EEPROM jest adresowany bajtowo, czyli można zarówno zapisywać, jak i odczytywać pojedyncze bajty. W jednym bajcie nie można zapisać "dużej" wartości, do tego wykorzystuje się po prostu kilka bajtów. Działa to dokładnie jak w przypadku pamięci RAM - przykładowo zmienna typu uint32_t zajmuje 4 bajty i dzięki temu może przechowywać wartości większe niż 255. Można ją zapisać w pamięci eeprom również wykorzystując 4 bajty, ale w jednym się po prostu nie zmieści.
  16. Może kurs stm32 pomoże? https://forbot.pl/blog/kurs-stm32-f1-hal-komunikacja-z-komputerem-uart-id22896
  17. @kuba15 Przeczytałeś dokumentację metody read() ? Wklejanie może słabo wygląda, więc podam jeszcze link: https://www.arduino.cc/reference/en/language/functions/communication/serial/read Jeszcze na wszelki wypadek wytłumaczę, bo pogrubienie w tekście chyba nie wystarczyło - read() zwraca jeden bajt, nie napis. Więc to co napisałeś i tak nie zadziała, nawet jak napięcia będą idealne, piny poprawne itd. itp.
  18. Zaawansowany projekt... ambitnie W każdym razie proponuję powrót do początków i podstaw, przykładowo do metody read:
  19. Spodziewałem się czegoś w rodzaju tego ostrzeżenia. Ale nie wiem jakich ustawień kompilatora używa autor wątku, w sumie nawet nie wiem jakiego kompilatora używa.
  20. Prawdę mówiąc spodziewałbym się wtedy innego komunikatu o błędzie. Moim zdaniem autor pokazał nam tylko fragment programu i to nie ten, który jest używany podczas kompilacji. Ale jak wyjaśnimy o co chodzi i z tymi nazwami, to będzie pewnie łatwiej coś doradzić.
  21. Funkcję nazwałeś throwOut, a wywołujesz throwOut2.
  22. Ja nie twierdzę, że takich ofert nie ma - po prostu zainteresowało mnie jak duże jest zapotrzebowanie rynku oraz jakie są stawki. Szkoda, że nie podali chociaż widełek przy tej ofercie
  23. Ok, czyli arduino, albo lepiej raspberry jako sposób na naukę, a później w pracy niska pensja oraz nuda - to brzmi sensownie. A może ktoś znalazł pracę, albo chociaż słyszał o pracy gdzie faktycznie Arduino albo Raspberry Pi się używa? Nie tylko doświadczenie przy tym zdobyte, ale same platformy - albo chociaż podobne?
  24. A tak wracając do pierwotnego tematu: "Co myślicie o zmianie zawodu po mimo wszystko tak krótkim czasie pracy? Jak najszybciej złapać pracę w zawodzie? Raspberry, adruino?" No właśnie bardzo ciekawe jak wygląda sytuacja ze znalezieniem pierwszej pracy przy takich założeniach - czyli znając trochę Raspberry lub Arduino? Ktoś ma jakieś doświadczenia, którymi może się podzielić? Czy dużo jest ofert pracy, ewentualnie jakie są wymagania, gdzie warto pracy szukać, na jakie stawki można liczyć? Jak chodzi o pracę front-end developera, to google zwraca np. takie informacje o zarobkach: "Wśród technologii frontendowych, zdecydowanie najbardziej dochodowy jest Angular. Mediana widełek oferowanego wynagrodzenia, w przypadku osób specjalizujących się w tym frameworku wynosi od 9 000 do 15 000 zł na umowie o pracę oraz od 11 000 zł do 15 000 zł na B2B*. W przypadku technologii React mediana oferowanych płac – zarówno na UoP, jak i B2B kształtuje się na poziomie od 9000 do 14000 zł*. Specjaliści aplikujący na stanowisko JavaScript Developera mogą liczyć na zarobki, których mediana wynosi od 9000 do 14000 zł na B2B oraz od 8000 do 13000 zł na umowę o pracę*." (źródło: https://nofluffjobs.com/blog/czym-sie-zajmuje-i-ile-zarabia-frontend-developer/)
  25. Nie do końca się zgodzę z ostatnim punktem, czyli podłączaniem modułów dla Arduino do Raspberry i odwrotnie. Trzeba pamiętać, że Arduino używa najczęściej zasilania oraz sterowania 5V, co jest zabójcze dla Raspberry Pi, które pracuje przy 3.3V. Więc niektóre moduły faktycznie będą działać, ale wiele może nie tylko nie działać, ale nawet uszkodzić układ.
×
×
  • Utwórz nowe...