Skocz do zawartości

Kurs STM32L4 – #17 – termometry DS18B20 (1-wire, UART)


Pomocna odpowiedź

Dnia 14.12.2021 o 21:14, roz napisał:

Czemu w kodzie pojawia się często delay_us? O ile w przykładzie to nie ma większego znaczenia o tyle w większym projekcie już może sprawiać problemy. To tak, jak z delay...

Z artykułu dość jasno wynika, że delay_us nie jest dobrym podejściem i nie powinno być używane w większych projektach. Autorzy używają tego podejścia żeby zilustrować działanie protokołu 1-wire, co byłoby trudne używając rozwiązania docelowego, czyli UART. Wersja pro, czyli ta z UART, nie wymaga żadnego delay_us.

Edytowano przez adamnar
literówka
  • Pomogłeś! 1
Link to post
Share on other sites

W końcu znalazłem czas na dokończenie kursu i nie żałuje straconego czasu, bo naprawdę warto. Z niecierpliwością czekam na podsumowanie i kolejne kursy z STM32 :)

  • Lubię! 1
Link to post
Share on other sites
(edytowany)

Odnośnie DS18B20, czy tam nie wkradło się parę błędów? Przykładowo sprawdzanie poprawności wywołania RESET przez USART - funkcja sprawdza, czy odczytana wartość jest różna od 0xf0 - to za bardzo nie ma sensu. Jeśli nie ma połączenia - odczytaną wartością będzie 0x00, czyli funkcja zwróci HAL_OK, co jest moim zdaniem błędem. Nie wykryjemy niepodłączonego czujnika. W rzeczywistości DS zwraca 0xe0, czyli 0b1110000 przy poprawnej inicjacji. W razie braku pewności, można sprawdzić, czy chociażby jest to wartość różna od 0x00, albo 0x00 i 0xff, co zdarzy się kiedy na tej linii jest stały stan wysoki lub niski.

Innym błędem jest brak sprawdzania wyniku funkcji set_baudrate() (która w dodatku nic nie zwraca, a powinna zwracać status), oraz HAL_UART_Transmit() i HAL_UART_Receive(), które zwracają status, ale jest on pomijany. Jeśli USART został skonfigurowany nieprawidłowo, lub niezainicjowany, już tu może być wykryty błąd i zwrócony wcześnie, bez próby wykonania odczytu, który, jak sprawdzałem - może zwyczajnie się zawiesić czekając na timeout.

Kosztowało mnie to troszkę kombinowania w sytuacji, kiedy mój konkretny discovery board nie widział pina od TX. Reset przechodził, a nie powinien. Ba - odłączyłem mu druta od TX-a i nadal reset przechodził. Potem read i write przechodziły, chociaż też nie powinny bez podłączonego kabla.

Może nie jest błędem, ale lekkim "code smell" ten "if" w funkcji write_bit(). Nie prościej napisać "uint8_t data_out = value ? 0xff : 0x00"?

No i tak na marginesie, na koniec funkcję ds18B20_init() można usunąć, nasz timer jest już niepotrzebny jak używamy USART-a. A że reset i tak trzeba zawsze wysłać do odczytu DS-a, więc jedyny "init" jaki się wtedy robi to ustawienie taktowania USART-a, ale znów - tu też większość kodu jest niepotrzebna. Jedynie linia ustawiająca baudrate i linia wywołująca init. Przecież pozostałe parametry zostały już wcześniej ustawione i nie zmieniają one swoich wartości (co z resztą przetestowałem na kilku różnych STM-ach i USART-ach).

Tan na marginesie, wersja poprawiona: https://gist.github.com/HTD/07f8ecd36f533382cddf814d2b44b219

Edytowano przez HTD
  • Lubię! 2
Link to post
Share on other sites
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

@HTD, witam na forum i dziękuję za merytoryczny komentarz.

W związku z tym, że ta część kursu była już bardzo długa to musieliśmy tutaj pójść na pewne ustępstwa, aby jeszcze bardziej nie rozciągać przykładów. Stąd akurat w tych przykładach celowo pominęliśmy np. sprawdzanie błędów, na które zwracaliśmy uwagę w innych częściach tego kursu. To nie jest kod produkcyjny, głównym celem było tutaj pokazanie "nietypowego" wykorzystania peryferiów sprzętów. Masz jednak oczywiście rację, że należałoby ten kod rozbudować. Analogicznie, w przypadku warunku wewnątrz write_bit() - taki zapis był celowy, ponieważ z naszych materiałów korzystają często mało doświadczeni programiści, a taki zapis jest dla nich zwyczajnie łatwiejszy w zrozumieniu.

Jeśli chodzi testowanie wartości 0xF0: jeśli nie będzie czujnika to właśnie taką wartość powinien zobaczyć odbiornik. W tym przypadku RX jest spięty z TX, neutralną wartością jest logiczne "1", natomiast STM32 i DS18B20 są podłączone jako AND "po-drucie", czyli którykolwiek nie wystawi "0", stan będzie "0". W związku z tym, jeśli nie ma DS18B20, a na TX jest 0xFF to na RX też będzie 0xFF. A jeśli na TX jest 0xF0 to na RX będzie 0xF0 - i to właśnie jest sprawdzane. Bity przesyłane są od najniższego, czyli dla 0xf0 najpierw są 4 bity o wartości "0". Więc na RX zawsze będą odczytane jako "0". Natomiast wartość wyższych bitów zależy od tego, czy DS18B20 "odpowie". Jeśli nic nie zrobi, to odczytamy same "1", co daje wartość 0xF0. Program w tej postaci jak w przykładzie wykryje poprawnie brak DS18B20. Natomiast nie wykryje "zwarcia" - to zostanie wykryte później, podczas odczytu z czujnika. Nie jest to błąd, po prostu decyzja, żeby nie wnikać w czasy odpowiedzi DS18B20. Brak układu zostanie wykryty podczas resetu, ale jeśli jest zwarcie to i tak nic dalej nie zadziała.

  • Lubię! 2
Link to post
Share on other sites

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Anonim
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.

×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.