Skocz do zawartości

ESP8266 RTOS SDK vs NONOS SDK


atlantis86

Pomocna odpowiedź

Parę lat temu zdarzało mi się tworzyć projekty na ESP8266, przy pomocy NONOS SDK od Espressif (nie przepadam za Arduino, które w przypadku ESP8266 tak naprawdę jest jedynie nakładką na to SDK). Niestety każda dłuższa przerwa oznaczała konieczność douczania się, bo producent wprowadzał zmiany, które wymagały dodawania kolejnych definicji i funkcji do własnego kodu, często w zależności od posiadanego modułu. Jakiś czas temu utknąłem na próbie przegryzienia się przez SDK w wersji 3.0 i prawdę mówiąc do tej chwili nie miałem motywacji, żeby się za to zabrać. Głównym powodem było to, że w międzyczasie producent ogłosił, że nie będzie już dłużej rozwijał NONOS SDK, a na GitHubie co najwyżej będą się pojawiały aktualizacje związane z bezpieczeństwem. Teraz rozwijane jest RTOS SDK, mniej więcej zgodne na poziomie kodu z ESP-IDF dla ESP32.

Prę dni temu zabrałem się więc za rozgryzanie RTOS SDK i powolne przenoszenie jednego z moich starszych projektów. Udało mi się nawet odpalić częściowo działającą wersję i podłączyć ją do domowego routera. Od razu przeprowadziłem test pingiem i tutaj pojawiło się pierwsze zaskoczenie - odpowiedzi przychodzą późno, nawet po 100ms. Co jakiś czas zdarza się nawet, że pakiet ginie zupełnie. Po kilku godzinach testu okazuje się, że mam około 2% zgubionych pakietów. Aby upewnić się, że nie odpowiada za to napisany przeze mnie kawałek kodu, skompilowałem i uruchomiłem jeden z przykładów dostarczonych przez producenta (bodajże serwer HTTP). Dokładnie takie samo zachowanie. Dla pewności wyciągnąłem jeszcze jeden ze swoich starych projektów, z softem napisanym na NONOS SDK (bodajże v2) i tam wszystko działa prawidłowo - pingi wracają po około 1 ms, nic nie ginie.

I teraz kilka pytań:

  1. Czy ktoś z was używa(ł) RTOS SDK na ESP8266? Jeśli tak, to czy zaobserwowaliście podobne zachowanie?
  2. Czy istnieje szansa, że ten problem zostanie jeszcze rozwiązany i będzie można spodziewać się podobnego zachowania jak na NONOS SDK?
  3. A może jednak w chwili obecnej nie warto już zajmować się ESP8266 i przenieść swoje projekty n ESP32?

EDIT: Ok, w razie gdyby ktoś miał kiedyś podobny problem, to chyba doszedłem do tego, co powoduje długie czasy odpowiedzi na pingi. Domyślnie w przykładach od Espressif włączony jest jakiś tryb oszczędzania energii, który powoduje taki mozolne działanie WiFi. Wystarczy dodać jedną linijkę:

esp_wifi_set_ps(WIFI_PS_NONE);

 

Edytowano przez atlantis86
Link do komentarza
Share on other sites

Mam podobne problemy. Napisałem na RTOS SDK web serwer bazując na tym co jest w przykładach, czasy odpowiedzi na request pokazywane w chrome ok 80-100 ms. Sam serwer nie robi nic bardziej skomplikowanego niż "miganie" diodami. To samo napisałem na NONOS SDK, z własną bardzo uproszczoną warstwą HTTP na połączeniu TCP, bo w przykładach nie znalazłem nic gotowego do tego. Czasy przy tym samym zadaniu to 5 ms - zdecydowanie bardziej sensowne. Wszystko w lokalnej sieci, ten sam chip, router, lokalizacja względem routera. Tryb oszczędzania energii wyłączony, bez tego było jeszcze gorzej na RTOS. Próby kombinowania z priorytetem zadania FreeRTOS nic nie dały. Jestem trochę rozczarowany. Wstępne badanie tego co się dzieje wskazuje na to, że samo obsługiwanie połączeń TCP na RTOS jest tak wolne, ale to wstępne wnioski, muszę zagłębić się w kod bardziej.

Edytowano przez celi
  • Lubię! 1
Link do komentarza
Share on other sites

Hmm... Zrobiłem test n jednym z przykładów dodanych do RTOS SDK. Czas załadowania prostej strony w stylu "Hello World" to jakieś 50ms. Nie jest idealnie, ale chyba też nie tragedia na prostym MCU. Może po prostu napisany przez Ciebie serwer był uproszczony dużo bardziej od tego, czego używa RTOS SDK? Tm chyba pod spodem siedzi serwer z lwIP?
Pamiętam, że w czasach NONOS używałem bardziej zaawansowanego serwera, który pozwalał na załadowanie kompletnych stron do pamięci flash ESP8266 i użycia w plikach html/js/json tokenów, które były podmieniane na określone wartości podczas wysyłania strony. Miałem napisany na tym kompletny interfejs konfiguracyjny, ale niestety ten serwer już od paru lat nie jest wspierany i kod na GitHubie nie miał od dawna aktualizacji. Zresztą z RTOS i tak chyb nie byłby kompatybilny... Tam opóźnienia w ładowaniu stron były widoczne. Nie tylko w stosunku do "normalnych" stron WWW, ale także w porównaniu do podobnego serwer, który miałem odpalony na PIC32 z Ethernetem.

Link do komentarza
Share on other sites

50 ms wg mnie to dużo na hello world, chociaż u mnie minimalnie to 60 ms, cześciej 80 ms, a nawet 100 ms 🙂

Zgoda, że mój soft jest mega uproszczony, ale coś mi tu nie pasuje mimo wszystko. LwIP to stos TCP/IP, nie obsluguje HTTP sam w sobie, to się dzieje warstwę wyżej. Jeszcze raz wgrałem kawałek softu na NONOS  i czas obsługi najprostszego GETa to nawet 3 ms! Nie chce mi się wierzyć, że parsowanie requestu i alokowanie do tego potrzebnej pamięci tyle zajmuje.

 

 

 

 

3ms.png

Edytowano przez celi
Link do komentarza
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

2 godziny temu, celi napisał:

50 ms wg mnie to dużo na hello world, chociaż u mnie minimalnie to 60 ms, cześciej 80 ms, a nawet 100 ms 🙂

A usunąłeś niepotrzebny kod z przykładowych funkcji? Bo trochę tego tam było: odczytywanie treści nagłówków, logowanie poszczególnych operacji na monitor (to narzędzie do debugowania) itp. Odchudziłem do maksimum funkcję obsługującą jeden URI i teraz nie robi ona właściwie nic poza zwróceniem odpowiedniego tekstu. Teraz czas załadowania kompletnej strony w Chrome spadł do około 18 ms.

2 godziny temu, celi napisał:

LwIP to stos TCP/IP, nie obsluguje HTTP sam w sobie, to się dzieje warstwę wyżej.

Nic nie stoi na przeszkodzie, żeby biblioteka TCP/IP udostępniała także funkcje do obsługi wyższych warstw. Tak było chociażby w przypadku biblioteki TCP/IP od Microchipa, która posiadała m.in. całkiem rozbudowany serwer HTTP z obsługą kompletnych stron przechowywanych we flashu na skompresowanym systemie plików tylko do odczytu. Na pewno w lwIP jest obsługa SNTP oraz MQTT. Wydaje mi się jednak, że było też parę innych protokołów, m.in. HTTP. Ale może się mylę?

2 godziny temu, celi napisał:

Jeszcze raz wgrałem kawałek softu na NONOS  i czas obsługi najprostszego GETa to nawet 3 ms! Nie chce mi się wierzyć, że parsowanie requestu i alokowanie do tego potrzebnej pamięci tyle zajmuje.

No cóż, może to wynika z filozofii działania RTOS? Pamiętaj, że w NONOS musiałeś wyrobić się ze wszystkimi operacjami wykonywanymi w pętlach tasków, żeby zwolnić zasoby potrzebne do obsługi systemu i WiFi. Jeśli nie zrobiłeś tego na czas, watchdog resetował układ. Tutaj masz scheduler. Zakładam, że operacje wykonywane w tle przez system mają najwyższy priorytet i jeśli mają się wykonać, to po prostu się wykonują. W NONOS musiały poczekać.

No i schedular też zajmuje trochę cykli procesora...

Link do komentarza
Share on other sites

10 godzin temu, atlantis86 napisał:

A usunąłeś niepotrzebny kod z przykładowych funkcji? Bo trochę tego tam było: odczytywanie treści nagłówków, logowanie poszczególnych operacji na monitor (to narzędzie do debugowania) itp. Odchudziłem do maksimum funkcję obsługującą jeden URI i teraz nie robi ona właściwie nic poza zwróceniem odpowiedniego tekstu. Teraz czas załadowania kompletnej strony w Chrome spadł do około 18 ms.

Tak

10 godzin temu, atlantis86 napisał:

Nic nie stoi na przeszkodzie, żeby biblioteka TCP/IP udostępniała także funkcje do obsługi wyższych warstw. Tak było chociażby w przypadku biblioteki TCP/IP od Microchipa, która posiadała m.in. całkiem rozbudowany serwer HTTP z obsługą kompletnych stron przechowywanych we flashu na skompresowanym systemie plików tylko do odczytu. Na pewno w lwIP jest obsługa SNTP oraz MQTT. Wydaje mi się jednak, że było też parę innych protokołów, m.in. HTTP. Ale może się mylę?

Jasne, ale w tym SDK mamy komponent esp_http_server, to jest warstwa HTTP na gołych gniazdach lwIp. Sam parser HTTP został napisany na podstawie kodu nginx. Jest taka informacja w kodzie. Jest to niezależne od lwIp.

10 godzin temu, atlantis86 napisał:

No cóż, może to wynika z filozofii działania RTOS? Pamiętaj, że w NONOS musiałeś wyrobić się ze wszystkimi operacjami wykonywanymi w pętlach tasków, żeby zwolnić zasoby potrzebne do obsługi systemu i WiFi. Jeśli nie zrobiłeś tego na czas, watchdog resetował układ. Tutaj masz scheduler. Zakładam, że operacje wykonywane w tle przez system mają najwyższy priorytet i jeśli mają się wykonać, to po prostu się wykonują. W NONOS musiały poczekać.

No i schedular też zajmuje trochę cykli procesora...

No właśnie dlatego to drążę, bo chce poznać i być świadomy ile "kosztuje" FreeRTOS. Z podobnych powodów jakie podałeś w pierwszym poście chciałem przejść na RTOS z NONOS. W aplikacji gdzie mam stałe zasilanie nie widzę problemu, w drugiej działającej na aku już się zastanawiam. To typowy logger danych, który większość czasu śpi i wybudza się tylko, żeby "zapostować" dane na raspberry pi. I co ciekawe klient HTTP w RTOS SDK jest jakiś niestabilny 🙂, dostaje co jakiś czas błąd opisany tutaj

https://github.com/espressif/esp-idf/issues/2684

występuje co kilkanaście/kilkadziesiąt minut. Oczywiście nie robię sterowania elektrowni atomowej i mogę z tym żyć, ale jakieś nieciekawe odczucia mam na teraz z tym SDK.

Trochę się wyjaśniło z tym czasem odpowiedzi. Zbadałem temat Wiresharkiem (analizator ruchu sieciowego). Mój serwer HTTP wysyła od razu nagłówki HTTP i dane, RTOS SDK najpierw nagłówki, w dosyć krótkim czasie (kilka/kilkanaście ms), po czym czeka na pakiet TCP ACK od przeglądarki (około 50-60 ms!) po czym dosyła ciało HTTP (też kilka/kilkanaście ms). Chrome mierzy czas TTFB - czas do pierwszego bajtu danych, nie interesuje go sam nagłówek, czyli chrome w tym przypadku w znacznej części mierzy opieszałość komputera na której jest uruchomiony w odesłaniu ACK. Niezłe jaja. Nie zmienia to faktu, że taka implementacja serwera powoduje dłuższe czekanie na zawartość, która typowo w takich aplikacjach nie jest duża i mogłaby lecieć od razu. Chyba większość potrzeb to zwrócenia jakiegoś małego jsona.

Na koniec napisałem też na RTOS SDK korzystając tylko z socketów TCP prosty server co odsyła nagłówki i content od razu i mam czasy niewiele gorsze niż na NONOS (minimalnie uzyskałem 10 ms wg chrome).

 

 

Link do komentarza
Share on other sites

Swoją drogą, znasz może jakiś prosty i wygodny sposób na konfigurowanie urządzeń na ESP8266?

Jak wspominałem, do tej pory korzystałem z "pełnego" serwer WWW, który obsługiwał pliki zapisywane w systemie plików w pamięci flash oraz tokeny, zamieniane na wartości zmiennych podczas wysyłania strony. Stworzyłem sobie w nim całkiem wygodną stronę konfiguracyjną - urządzenie startowało w trybie SoftAP, pozwalając na przeskanowanie WiFI, połączenie z określonym AP oraz skonfigurowanie kilku innych parametrów. Niestety - wspomniany serwer z GitHuba od dawna nie miał aktualizacji i prawie na pewno nie jest kompatybilny z RTOS SDK. A pełnego interfejsu WWW nie chce mi się ręcznie rzeźbić w kodzie źródłowym. 😉

Jest jakaś inna opcja, poza umieszczaniem parametrów w kodzie albo napisaniem sobie parsera komend konfiguracyjnych wysyłanych przez UART?

Link do komentarza
Share on other sites

Nie robiłem tego, ale wydaje mi się, że powinno udać się zrobić dokładnie to samo używając tylko tego co dostarcza RTOS SDK. Server HTTP jest gotowy do użycia. Zobacz jak dodać do kompilacji własne pliki i później dostać się do nich w kodzie.

https://docs.espressif.com/projects/esp8266-rtos-sdk/en/latest/api-guides/build-system.html#embedding-binary-data

Tam masz link do przykładu protocols/https_mbedtls gdzie w ten sposób podrzucają do programu potrzebny certyfikat, ale dokładnie tak samo możesz załączyć pliki html/js, czyli nie musisz pisać html w stringach języka C :) Mało tego, możesz te pliki uruchomić na jakimś serwerze HTTP na PC i dopracować wygląd strony zanim poleci na układ.

Jeśli to by było nie wystarczające masz dostępny system plików spiffs (jest przykład użycia). Tam już możesz czytać pliki, pisać do nich, zakładać nowe. Ale do tego co potrzebujesz chyba nie jest to potrzebne, bo pliki strony są niezmienne w czasie.

Reszta problemu to tylko znajdź/zamień własnych placeholderów w html/js na prawdziwą zawartość, wyliczenie prawidłowego nagłówka Content-Length po zmianie zawartości i odesłanie odpowiedzi. Chociaż jeszcze bardziej kuszące jest użycie jakiegoś bindera javascript np vue.js zamiast znajdź/zamień.

Jeśli nie robisz jednak produktu na rynek to wydaje mi się, że do własnych potrzeb konfiguracyjnych można w trybie AP wystawić tylko obsługę jednej akcji w stylu POST /settings i wkładać w ciele JSON w stylu

{
   "wifi": {
      "login": "LOGIN",
      "password": "PASSWORD"
   },
   "param1": "value1",
   "param2": "value2"
}

Operacje można wykonać np z programu Postman, a jak korzystasz z Visual Studio Code, to ma świetny dodatek REST Client.

Mi chodzi po głowie jeszcze prostszy sposób konfiguracji swoich układów (do własnego użytku). Podobnie po starcie ESP wystawia własny AP, po czym w login i hasło wkładam od razu konfigurację pełną (rozdzielanie parametrów średnikiem na przykład). ESP odrzuca logowanie po czym łączy się od razu do wskazanej sieci i używa parametrów zapisując je sobie przez fajny mechanizm NVS. Nie wiem tylko czy w sdk jest możliwość przechwycenia wprowadzonych przez użytkownika danych logowania i czy nie ma jakiegoś ograniczenia na długość. To tylko moja koncepcja, ale byłaby bardzo wygodna i pewnie to zbadam.

Nie jest to tak fajne jak zbudowanie konfiguracji w stylu routera, ale prawda jest taka, że dużo pracy w to trzeba włożyć, żeby to jeszcze wyglądało, a cieszy zazwyczaj tylko moje oko:) Póki co robię to na własny użytek jedynie.

Edytowano przez celi
Link do komentarza
Share on other sites

6 godzin temu, celi napisał:

Nie robiłem tego, ale wydaje mi się, że powinno udać się zrobić dokładnie to samo używając tylko tego co dostarcza RTOS SDK. Server HTTP jest gotowy do użycia. Zobacz jak dodać do kompilacji własne pliki i później dostać się do nich w kodzie.

Dzięki za info. To się może przydać. Jeśli to faktycznie działa tak jak mówisz, to nie ma sensu nawet modyfikować plików, podmieniając tokeny na wartości. Korzystając z gotowych serwerów na PIC32 i ESP8266 NONOS SDK korzystałem z tokenów, bo były dostępne i pozwalały pewne rzeczy osiągnąć w bardzo wygodny sposób. Jednak równie dobrze ten sam efekt można osiągnąć modyfikując DOM po stronie przeglądarki, za pomocą skryptów JS i danych pobieranych za pomocą JSON-a. Mógłbym zacząć od napisania funkcji, które pobierałyby dane przez GET i wysyłały konfigurację przez POST. Na własny użytek wystarczy, a dla osób mniej technicznych (zlecenia, projekty robione na prezent dla znajomych) mógłbym napisać WebUI oparte na HTML5 i JS.

Link do komentarza
Share on other sites

Dokładnie, prościej nawet i bardziej współcześnie. Można nawet ładować pewne zależności (np. framework js) z zewnętrznego ogólnodostępnego serwera CDN, jeśli działanie układu i tak zakłada dostęp do Internetu. Awaryjność może nieco rośnie, ale nie ogranicza nas pamięć FLASH. Jak kto woli.

Link do komentarza
Share on other sites

Dnia 23.03.2021 o 17:26, celi napisał:

czasy odpowiedzi na request pokazywane w chrome ok 80-100 ms. Sam serwer nie robi nic bardziej skomplikowanego niż "miganie" diodami. To samo napisałem na NONOS SDK, z własną bardzo uproszczoną warstwą HTTP na połączeniu TCP, bo w przykładach nie znalazłem nic gotowego do tego. Czasy przy tym samym zadaniu to 5 ms

Może warto byłoby przetestować tą uproszczoną implementację na FreeRTOS. Akurat FreeRTOS jest bardzo prostym systemem, nie ma tam chyba żadnego (na pewno nie ma ma STM32F1) sprawdzania uprawnień do pamięci (MMU, Ring0/1, etc) co mogłoby zjadać mocniej wydajność. Obstawiam że na 99% problem leżał po stronie implementacji a nie samego RTOSa.

Edytowano przez Harnas
Link do komentarza
Share on other sites

12 godzin temu, Harnas napisał:

Może warto byłoby przetestować tą uproszczoną implementację na FreeRTOS.

Zrobiłem to i pisałem tutaj

Dnia 24.03.2021 o 14:09, celi napisał:

Na koniec napisałem też na RTOS SDK korzystając tylko z socketów TCP prosty server co odsyła nagłówki i content od razu i mam czasy niewiele gorsze niż na NONOS (minimalnie uzyskałem 10 ms wg chrome).

Prawdą jest, że FreeRTOS jest prosty ale i tak czuć, że jest. Na NONOS najszybszy czas odpowiedzi HTTP to 3 ms, na RTOS wyszło 10 ms z tą prostą implementacją, analogiczną do NONOS. Na RTOS rozrzut czasu odpowiedzi, czyli jitter też jest dużo większy. To samo widać po pingach do apki bez kodu użytkownika, na NONOS mam zazwyczaj 1 ms, na RTOS minmum 2 ms, niezwykle rzadko osiągalne. Oczywiście, dla większości zastosować to bez znaczenia, ale przy zasilaniu bateryjnym warto mieć to na uwadzę.

Dodam, że próbowałem kombinować z priorytetem zadań, a nawet częstotliwością przełączania zadań FreeRTOS (parametr Tick Rate), ale bez większych rezultatów. Podejrzewam, że jakbym uruchomił wiele zadań użytkownika, które faktycznie coś robią, a nie śpią większość czasu to bym widział wpływ.

Co ciekawe w ustawieniach widać możliwość wyłączenia FreeRTOS w tym SDK. Ciekawe czy to opcja która daje jakąś realną wartość, czy bardziej doświadczalna, bo przecież bez FreeRTOS ciężko korzystać z tego całego api które jest synchroniczne i blokujące.

Link do komentarza
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.