-
Zawartość
2694 -
Rejestracja
-
Ostatnio
-
Wygrane dni
198
Posty napisane przez Elvis
-
-
W każdym razie:
10 minut temu, ethanak napisał:Zauważ: zakładając, że PB5 to stała a PINB to odwołanie się do zawartości rejestru - 1 << PB5 obliczany jest w czasie kompilacji. PINB >> PB5 w czasie wykonania.
Ergo: jeśli moje założenia są słuszne, nie jest optymalny niezależnie od mikrokontrolera
to nieprawda. Są takie architektury gdzie oba kody mogą być tak samo wydajne.
-
Przy okazji warto jeszcze wyjaśnić jak ten pin jest skonfigurowany i jak niby miało działać - bo najpierw używany jest rejestr PORTB, czyli wygląda jakby to miał być pin w trybie wyjścia, ale chwilę później następuje odczyt z rejestru PINB, więc jednak wejście. Jestem bardzo ciekaw jak autor rozumie działanie takiego programu.
@ethanak zostawmy te optymalizacje w spokoju, może warto zacząć od poprawności programu. Może nie być różnicy, czy przesunięcie jest wykonywane podczas kompilacji, czy wykonywania.
-
Niestety nie znam metody na użycie GPS w małym robocie, dlatego zapytałem. Dokładność 2m to bardzo optymistyczne założenie. Filtr Kalmana to dobry pomysł, sprawdza się w nawigacji samochodowej - ale znowu, przy rozmiarze i szybkości reakcji robota raczej nie zadziała poprawnie.
Można uzyskać wysoką dokładność w przypadku GPS, taki sprzęt używany jest np. w geodezji - ale ceny są zupełnie inne niż w przypadku opisywanych modułów, czas pomiaru jest dość długi no i konieczny jest abonament na dane dla DGPS.
-
Robiłeś może jakąś analizę dokładności danych z GPS? Pytam bo to dość mały robot i kilka metrów to dla niego spory dystans, a z moich doświadczeń z odbiornikami GPS otrzymywanie "szumu", który wygląda jak skoki po kilka metrów to normalne działanie. I bardzo mnie ciekawi jak sobie poradziłeś z tym problemem.
-
I2S to nie format przesyłania dźwięku tylko interfejs. W każdym razie poczytaj to sam zobaczysz, że w przypadku esp32 jednak coś ma i to więcej niż samo DMA.
-
Nie musisz zaczynać od DMA, możesz wykorzystać sam I2S na początek.
-
Dobra, z tymi timerami to był zły pomysł - jednak na esp32 jest zupełnie inaczej niż na stm32, a mi się wszystko pomieszało
W każdym razie jak chodzi o gotowca to proponuję popatrzeć na kod biblioteki FabGL: https://github.com/fdivitto/FabGL
Jest tam kod sterownika VGA, który wykorzystuje DMA, ale zamiast jak myślałem GPIO używane jest I2S - pozostaje przeanalizować kod, a może i przetestować.
Tak jako ciekawostka, że ESP32 może faktycznie generować obraz VGA:
-
Ja bym proponował zostawić DMA na moment i zacząć od czegoś prostszego, czyli timera. Niezależnie, czy używając DMA, czy CPU i tak konieczne jest ustalenie prędkości transmisji do wyświetlacza - podejście z liczeniem cykli maszynowych się nie sprawdzi, więc proponuję uruchomić timer i na początek programowo go używać. Czyli to co może zrobić DMA najpierw niech robi drugi rdzeń - jest nawet szansa, że to zadziała i DMA nie będzie niezbędne (chociaż zawsze warto czegoś nowego się nauczyć).
-
Oczywiście, że taki sposób istnieje. Możesz po prostu wyrzucić FreeRTOS, przejąć pełną kontrolę i wszystko sam zrobić. Będzie to dość trudne, ale jak najbardziej możliwe.
Wydaje mi się jednak, że po prostu źle do tego podchodzisz. W przypadku AVR takie sterowanie pinami mając policzone takty zegara działało - w nowszych układach będzie bardzo skomplikowane. O wiele łatwiej i dokładniej byłoby użyć do tego odpowiednich modułów peryferyjnych. Do odmierzania czasu - timer, a do transmisji DMA.
-
Też mnie to zainteresowało, ale chwilowo trochę brak czasu
Jeśli coś przetestujesz to chętnie się dowiem jak to z tym FreeRTOS-em na esp32 jest
-
1
-
-
Zakładałem że scheduler na ESP32 używa dwóch rdzeni i sam uruchomi zadanie na drugim. Ale możliwe, że to było zbyt optymistyczne założenie. Wydawało mi się, że użycie priorytetów jest mniej "inwazyjne" niż wskazywanie rdzenia, ale oczywiście użycie xTaskCreatePinnedToCore zadziała na pewno, a z priorytetami trzeba byłoby przetestować.
-
Nie testowałem implementacji FreeRTOS-a na ESP32, ale ogólnie jeśli jest zadanie o wyższym priorytecie to powinno być zawsze wykonywane jako pierwsze. Więc na jednym rdzeniu nic poza nim nie powinno działać. Ale muszę to sprawdzić, bo w sumie ciekawe jak to faktycznie działa na esp.
-
Moim zdaniem przypisywanie zadania do rdzenia wcale nie jest potrzebne - wystarczy do zadania, które steruje LCD przypisać wyższy priorytet.
-
Rozdzielczość jest ustawiona na maksymalną wartość, można próbować ją zmienić używając plików /sys, ale chwilowo nie mam podłączonego czujnika żeby to przetestować i napisać jak dokładnie.
Natomiast pytanie jest inne - po co zmieniać rozdzielczość?
-
1
-
-
Może skoro nauka Arduino to nic przyjemnego oraz strata czasu, to warto poszukać gotowego rozwiązania? Nie jestem fanem modelarstwa, ale jakoś mi się nie chce wierzyć, że nie ma gotowych sterowników do makiet - wystarczy poszukać i zamówić z dostawą do domu.
-
- Popularny post
- Popularny post
@atMegaTona prosiłem, żebyś powtórzył podstawy języka C (chociaż akurat tutaj jest mój błąd, bo pownniśmy pisać o C++). Ale niezależnie czy to C, czy C++ wskaźniki i tablice to co innego i nie chodzi tutaj tylko o możliwość zmiany wskaźnika.
Wszystkich początkujących bardzo proszę o czytanie wypowiedzi kolegi @atMegaTona z zamkniętymi oczami - tablice i wskaźniki to nie to samo, a takie wpisy są tylko przykrym dowodem na to że w internecie znajdziemy mnóstwo bzdur i to jeszcze pisanych jako prawdy objawione
A jak już uda się powtórzyć podstawy C oraz C++ to może będzie warto wyjaśnić, czym tablice i wskaźniki się różnią.
PS. dla ustalenia uwagi: piszemy o tablicach statycznych, zostawiamy alokowane dynamicznie w spokoju.
-
3
-
Nie mieszajmy innym w głowie, czasem lepiej nic nie pisać niż pisać nieprawdziwe rzeczy. Wskaźnik i tablica to co innego w języku C, więc zapis
const char *napis = "jakis napis";
oraz:
const char napis[] = "jakis napis";
nie są równoważne, chociaż podobne. Zachęcam do poczytania podstaw języka C oraz sprawdzenia czym się różnią.
-
Prawdopodobnie całe nieporozumienie wzięło się z warunku w pętli:
for(t=0;t<=6;t++){
Jak słusznie zauważył kolega @Hudyvolt, taka pętla wykona się 7 razy, za pierwszym razem t=0, a za ostatnim t=6, czyli t=0,1,2,3,4,5,6 daje razem 7. Powodem tego zamieszania jest użycie warunku <= (mniejszy-równy), popularniejsze jest używanie ostrej nierówności, czyli kodu:
for(t=0;t<6;t++){
Domyślam się, że o to chodziło autorowi tematu i taka postać jest używana znacznie częściej. Pętla chyba miała się wykonać 6 razy, czyli t=0,1,2,3,4,5 i wówczas po wyjściu z pętli wartość t wynosiłaby 6, a więc oryginalny warunek byłby spełniony.
-
18 minut temu, Hudyvolt napisał:
Twoja pętla wykonuje się 7 razy. Warunek if(t==6) zawsze będzie prawdziwy, ponieważ z taką wartością pętla kończy pracę.
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.
-
1
-
-
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.
-
1
-
-
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.
-
1
-
1
-
-
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.
-
1
-
-
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.
Odczyt stanu pinu AVR
w Mikrokontrolery
Napisałeś że niezależnie od mikrokontrolera - i tylko dlatego napisałem że to nieprawda. Są takie i to dość popularne, sam na takie piszesz programy