Układ scalony BME680 to jakby kilka układów w jednym: czujnik ciśnienia i temperatury (jak w układzie BMP280) z rozszerzeniem o czujnik wilgotności (jak w układzie BME280) i z dodatkowym czujnikiem gazu [S34]. Czujnik wilgotności względnej jest wykonany w technologii MEMS z zastosowaniem pomiaru zmian pojemności kondensatora z polimerową folią [S32]. Czujnik ciśnienia barometrycznego jest wykonany w technologii MEMS z zastosowaniem pomiaru rezystancji cienkiej membrany. Pomiar temperatury jest wykonywany poprzez pomiar zmian napięcia diody krzemowej. Każda struktura scalona zastosowana w układzie scalonym BM680 zawiera czujnik temperatury.
Układ scalony BME680 został użyty w najnowszym zestawie Thingy:91 firmy Nordic Semiconductor przeznaczonym dla mobilnego Internetu Rzeczy [S31]. Dokładny opis dołączania procesora komunikacyjnego CC1352R1 firmy Texas Instruments do układu BME680 z zastosowaniem komunikacji I2C został zamieszczony w poprzednim odcinku kursu [S36]. Jest tam również dokładnie omówiony indeks jakości powietrza IAQ. W tym artykule, w celu zapewnienia kompletności opisu zostały częściowo powtórzone niektóre informacje. Jest to konieczne ze względu na niepełny opis układu BME680 w dokumentacji firmowej.
Indeks jakości powietrza IAQ
IAQ (Indoor Air Quality) jest liczbą, która informuje o jakości powietrza w pomieszczeniach. Obecnie nie ma globalnego standardu definiującego IAQ [3]. Niektóre kraje mają lokalne podejście i opublikowały badania, które podają wskaźniki czystego powietrza i jego implikacje. Niestety, nie ma zgodności w zastosowaniu skali, liczby poziomów, nazw ani kolorów.
Praca układu BME680
Układ scalony BME680 pracuje w dwóch stanach: uśpienia (sleep) oraz pracy (forced mode). Tryb pracy jest ustawiany na bitach 1:0 rejestru Config (pod adresem 0x75). Wpis 00b oznacza ustawienie stanu uśpienia a wpis 01b ustawienie stanu pracy. Układ po włączeniu zasilania automatycznie ustawia tryb uśpienia. W tym stanie nie jest wykonywany pomiar i pobierana jest minimalna moc zasilania.
W stanie pracy wykonywany jest pojedynczy pomiar w sekwencji: temperatura, ciśnienie, wilgotność, rozpoczęcie podgrzewania czujnika gazu, wykonanie pomiaru gazu i zakończenie grzania. Można ustawić w rejestrach układu scalonego 10 konfiguracji pracy, co opisano w poprzedniej części artykułu.
Odczyt danych pomiarowych trzeba rozpocząć od odczytu rejestru stanu Eas_status_0 (0x1D) z polami bitowymi:
- 7 – new data: dane nowego pomiaru są zapisane w rejestrach,
- 6 – gas measuring: zmiana stanu na zero sygnalizuje zakończenie pomiaru gazu.
- 5 – measuring: zmiana stanu na zero sygnalizuje zakończenie wszystkich pomiarów,
- 3:0 – gas meas index: numer konfiguracji pracy czujnika gazu.
Następnie trzeba sprawdzić stan bitów gas_valid oraz heat_stab rejestru gas_valid_r (0x2B), aby ustalić, czy dane pomiarowe są poprawne oraz czy grzejnik pracował stabilnie.
Następnie odczytane dane z rejestrów danych układu należy przeliczyć z uwzględnieniem danych z rejestrów kalibracyjnych układu.
W przypadku wykonywania przez układ BME680 pomiaru gazu włączany jest wewnętrzny grzejnik czujnika gazu. W stabilnych warunkach długiej sekwencji pomiarów powoduje to wystąpienie stałego podwyższenia mierzonej temperatury oraz obniżonego odczytu wilgotności. Można to zjawisko skompensować poprzez uwzględnienie stałej poprawki lub odczytu z dodatkowych czujników zewnętrznych.
Rejestry wewnętrzne
Układ zawiera wiele 8-bitowych rejestrów: kalibracji, sterowania, danych, statusu oraz rejestry zarezerwowane. Dostępna jest przestrzeń adresowa z zakresu 0x00 do 0xFF. Rejestry mają inny adres przy dostępie poprzez interfejs I2C oraz SPI:
- Podczas pracy z interfejsem I2C stosowany jest adres 8-bitowy z dostępem do całej przestrzeni adresowej.
- Podczas pracy z interfejsem SPI stosowany jest adres 7-bitowy z dostępem do dwóch stron wybieranych przez ustawienia rejestru spi_mem_page. Po włączeniu zasilania wybrana jest strona zerowa (0x80 do 0xFF). Wpisanie do rejestru spi_mem_page wartości 1 powoduje wybranie strony 1 (0x00 do 0x7F).
Mapa i opis rejestrów jest zamieszczony w dokumencie BME680 Datasheet [2]. Mapa nie zawiera wszystkich rejestrów a opis nie zawiera omówienia niektórych istotnych rejestrów układu.
Interfejs komunikacyjny
Interfejs komunikacyjny układu BME680 ma osobne wyprowadzenie zasilania VDDIO. Poziom wysoki sygnałów wejściowych interfejsu cyfrowego odnosi się do poziomu napięcia na wyprowadzeniu VDDIO [2]. Układ może pracować w trzech konfiguracjach wyprowadzeń – przy pracy w standardzie: I2C, SPI (4 linie) lub SPI (3 linie).
Wyprowadzenie SCK pracuje zawsze jako wejście. Wyprowadzenie SDI pracuje jako wejście (SPI 4 linie), wejście/wyjście SPI (3 linie) lub jako linia dwukierunkowa danych (I2C). Wyprowadzenie SDO pracuje jako wyjście (SPI 4 linie) lub jako wejście wyboru adresu (I2C). Wyprowadzenie CSB pracuje zawsze jako wejście. Pełni funkcję wejścia wyboru (chip select) dla pracy SPI.
Wybór standardu komunikacyjnego jest wykonywany na podstawie stanu wejścia CSB. Jeśli podczas włączenia zasilania układu wyprowadzenie CSB jest dołączone do napięcia, to wybierany jest standard I2C. Poziom niższy niż VDDIO spowoduje trwałą pracę ze standardem SPI. Po podaniu w trakcie pracy układu na wejście CSB poziomu niskiego (nawet jeden impuls) aktywowany jest na stałe interfejs SPI.
Układ obsługuje cyfrową komunikację w standardzie SPI oraz I2C jako układ „slave”. Komunikacja z układem jest wykonywana poprzez odczyt lub wpis do rejestrów.
Interfejs SPI
Układ BME680 obsługuje komunikację w standardzie SPI w dwóch konfiguracjach wyprowadzeń: SPI (4 linie) lub SPI (3 linie) (rysunek 1). Maksymalna częstotliwość zegara wynosi 10 MHz [2].
Układ BME680 obsługuje dwa tryby pracy SPI:
- w trybie ‘00’ (CPOL = CPHA = ‘0’),
- w trybie ‘11’ (CPOL = CPHA = ‘1’).
Automatyczny wybór trybu jest określany poprzez stan wejścia SCK po zboczu opadającym wejścia CSB (rysunek 2).
Protokół obsługi obu trybów pracy SPI (4 linie) oraz SPI (3 linie) jest taki sam. Tryb SPI (3 linie) jest wybierany poprzez wpis ‘1’ do rejestru spi3w_en.
Podczas pracy układu BME680 w standardzie SPI do komunikacji używane są cztery wyprowadzenia (rysunki 1a, 2b):
- CSB – wejście chip select, aktywny poziomem niskim,
- SCK – jako wejście zegara,
- SDI – jako wejściowa linia danych – SPI (4 linie) lub dwukierunkowa linia danych – SPI (3 linie),
- SDO – jako wyjście danych – SPI (4 linie) lub wysoka impedancja – ASPI (3 linie).
Interfejs SPI używa adresowania 7-bitowego i obsługuje dwa rodzaje transferu:
- odczyt pojedynczego bajtu (bit R/W = 0 + 7b add + 8b data),
- wpis pojedynczy lub wielokrotny bajtów – sekwencja (bit R/W = 1 + 7b add + 8b data).
Przestrzeń adresowa jest podzielona na dwie strony. Po włączeniu zasilania rejestr spi_mem_page (adr 0x73) jest wyzerowany i wybrana jest strona 0 z adresami rejestrów 0x80 do 0xFF. Po wpisie 1 do rejestru spi_mem_page wybrana jest strona 1 z adresami rejestrów 0x00 do 0x7F.
Wpis bajtu danych do rejestru układu
Schemat transmisji podczas wpisu bajtów pokazano na rysunku 3. Pokazany jest stan wejścia SDI, gdyż stan wyjścia SDO jest nieistotny. Obserwacje pokazują, że układ na wyjściu SDO ustawia trzeci stan. Transmisja następuje zawsze jako dwa bajty, gdzie pierwszy bajt zawiera adres rejestru, a drugi daną do wpisania.
Podczas wpisu danych do rejestrów układu transmisja rozpoczyna się od:
- wystawienia przez układ master niskiego stanu na linii CSB i 7-bitowego adresu rejestru poprzedzonego bitem RW=0 (write),
- następnie master wysyła bajt z daną do wpisu,
- master może jednak wysyłać kolejne pary bajów do wpisu danych pod inne adresy rejestrów,
- zdjęcie przez układ master niskiego poziomu na linii CSB kończy wpis bajtów.
Nie jest stosowana autoikrementacja adresów. Przykład zapisu bajtu jest pokazany dalej na rysunku 11.
Odczyt bajtu danych z rejestru układu
Schemat transmisji podczas odczytu bajów pokazano na rysunku 4.
Podczas odczytu danych z rejestrów układu transmisja rozpoczyna się od:
- wystawienia przez układ master niskiego stanu na linii CSB i 7-bitowego adresu rejestru poprzedzonego bitem RW=1 (read),
- następnie układ BME680 wysyła na wyjście SDO bajt z odczytaną z rejestru daną. Stan wyjścia SDO podczas bajtu adresowego jest nieistotny. Obserwacje pokazują, że układ na wyjściu SDO ustawia trzeci stan,
- master może wysyłać kolejne bajty sygnałów zegarowych do odczytu danych z rejestrów spod kolejnych adresów (autoikrementacja adresów),
- zdjęcie przez układ master niskiego poziomu na linii CSB kończy wpis bajtów.
Przykład odczytu pojedynczego bajtu danych jest pokazany dalej na rysunku 10, a odczytu sekwencji bajtów na rysunku 12.
Biblioteka Bosch Sensortec drivers
Firmowe sterowniki dla układu BME680 są dostępne na stronie Bosch Sensortec drivers [10].
Repozytorium BoschSensortec Github udostępnia dwa komplety sterowników:
- BME680 sensor driver/API – sterowniki z opisem i przykładami,
- BSEC-Arduino – biblioteka do Arduino do integracji biblioteki firmowej BSEC.
Pakiet programowy BME680 sensor driver/API zapewnia niskopoziomową komunikację z układem BME680 oraz kalibrację wartości odczytu z sensorów. Uwalnia to użytkownika od konieczności zajmowania się obsługą poszczególnych rejestrów układu scalonego.
Pobierany z repozytorium plik BME680_driver-master.zip zawiera trzy pliki źródłowe:
- bme680_defs.h – zawiera stałe, makra i deklaracje,
- bme680.h – zawiera deklaracje funkcji API,
- bme680.c – zawiera definicje funkcji API,
- REDAME.md – zawiera opis sposobu dołączania drajwerów do projektu użytkownika.
Dodatkowo jest pobierany folder Self test z dwoma plikami:
- bme680_selftest.h – zawiera stałe, makra i deklaracje funkcji,
- bme680_selftest.c – zawiera definicje funkcji wykonywania testu i analizy danych.
Pakiet BME680 sensor driver/API obsługuje komunikację z układem BME680 w dwóch standardach: I2C oraz SPI (4 linie). Na stronie repozytorium zamieszczony jest przykładowy kod inicjalizacji układu (dla obu standardów komunikacji), skonfigurowania układu oraz wykonania pojedynczego pomiaru i odczytania wyników.
W nocie aplikacyjnej AN-014 [3] została opisana praca układu scalonego oraz postępowanie podczas wykonywania testowania układu: weryfikacja identyfikacji struktury scalonej, weryfikacja danych kalibracyjnych, generowanie CRC, pomiar danych z czujników, weryfikacja danych pomiarowych.
Biblioteka pomiarowa BSEC
Biblioteka Bosch Sensortec Environmental Cluster (BSEC) [11] jest przeznaczona do obsługi pracy z czujnikiem BME680. Komunikację oraz kompensację danych zapewnia sterownik firmowy [10]. Algorytmy biblioteki zapewniają również dodatkową kompensację pomiarów czujnika gazu z uwzględnieniem wilgotności oraz dryftu. Kod biblioteki jest zamknięty.
Moduł czujnikowy BME680 Environmental Sensor
Kilka firm oferuje moduły czujnikowe z układem scalonym BME680. Typowo zawierają one układ scalony BME680 oraz dodatkowo (opcjonalnie) układy interfejsu cyfrowego oraz regulator napięcia zasilania. Typowym przykładem jest moduł czujnikowy BME680 Environmental Sensor (DFRobot SEN0248) [6] oferowany również przez Kamami [7]. Widok płytki drukowanej modułu czujnikowego BME680 Environmental Sensor został pokazany na fotografiach 5 i 6. Dokładniejszy opis modułu znajduje się w poprzedniej części artykułu.
Zestaw startowy CC1352R1 LaunchPad (Texas Instruments)
Zestaw startowy SimpleLink Multi-Band CC1352R Wireless MCU LaunchPad Development Kit (LAUNCHXL-CC1352R1) jest wyposażony w układ scalony CC1352R1F3 [S15]. Zestaw jest przeznaczony do pracy w pasmach 868 MHz/915 MHz oraz 2,4 GHz. Cała elektronika zestawu CC1352R1 LaunchPad jest umieszczona na jednej wielowarstwowej płytce drukowanej. Płytka jest podzielona na dwie części: u góry płytki jest emulator sprzętowy standardu XDS110 oraz układ monitora zasilania a na dole układ scalony CC1352R.
Na złączach J1, J2, umieszczonych po obu bokach płytki drukowanej, jest udostępnionych 26 wyprowadzeń wejścia-wyjścia (GPIO) układu scalonego CC1352R oznaczanych jako „DIOxx”, gdzie xx – numery od 01 do 31. Dodatkowo na dole płytki są umieszczone dwa potrójne złącza z wyprowadzoną masą „GND” oraz zasilaniem „3V3”.
Połączenia sprzętowe
Na płytce modułu BME680 Environmental Sensor jest umieszczone złącze P2 typu IDC do obsługi komunikacji SPI. Dołączanie sygnałów SPI modułu do zestawu startowego CC1352R LaunchPad [S15]:
- GND (P2.5) → GND (P1.3) płytki CC1352R1 LP
- VCC (P2.6) → 3,3 V (J1.1) płytki CC1352R1 LP
- MOSI (P2.6) → DIO9 (J2.12, MOSI) płytki CC1352R1 LP
- CS (P2.6) → DIO11 (J2.6, CS) płytki CC1352R1 LP
- SCLK (P2.6) → DIO10 (J1.13, SCLK) płytki CC1352R1 LP
- MISO (P2.6) → DIO8 (J2.14, MISO) płytki CC1352R1 LP
Sposób podłączenia kabelków jest pokazany na rysunku tytułowym. Dodatkowo jest tam pokazany zestaw uruchomieniowy SHT31 Smart Gadget firmy Sensirion zastosowany do referencyjnego pomiaru temperatury i wilgotności [S32].
Aktualizowanie oprogramowania firmowego
Debugger sprzętowy typu XDS110 wymaga okresowej aktualizacji oprogramowania firmowego. Obecnie razem z wersją CCS stosowana jest aktualizacja FW do wersji 3.0.0.11 z pakietu emulacyjnego 9.1.0.00001 (2020-02-13). Numer aktualnej wersji oprogramowania firmowego w środowisku CCS można sprawdzić z menu Help → About Code Composer Studio → Instalation Detiles. Teraz w górnym oknie należy przewinąć do linii TI Emulators i kliknąć na nią. W dolnym oknie wyświetlane są dokładne informacje o pakiecie.
W obecnej wersji został zmieniony sposób aktualizacji FW. Jest on wykonywany w jednym kroku (zamiast w dwóch osobnych), co obejmuje: przełączenie debuggera XDS110 w tryb programowania, dołączanie do debuggera pracującego w trybie programowania, przesyłania nowego oprogramowania firmowego, kończenie aktualizacji oprogramowania oraz ponowne bootowanie debuggera w celu powrotu do trybu pracy normalnej. W trakcie aktualizacji oprogramowania porty wirtualne COM widoczne w systemie Windows są kasowane. Po zakończeniu aktualizacji porty pojawiają się ponownie. Jednak do portu Application/User UART nie można się już dołączyć programem PuTTy. Wymaga to odłączenia XD110 od komputera i ponownego dołączenia lub ponownego uruchomienia systemu Windows. Ze sterownikami dla XDS110 jest ogólnie spory problem, ponieważ odłączenie debuggera podczas działania programu PuTTy dołączonego do jego portu również blokuje dostęp do tego portu i wymaga ponownego uruchomienia systemu Windows.
Pakiet programowy SimpleLink Sensor and Actuator Plugin (Texas Instruments)
Do obsługi układu BME280 z zastosowaniem różnych procesorów służy darmowy pakiet programowy SimpleLink Sensor and Actuator Plugin firmy Texas Instruments [13]. Trochę zamieszania wprowadza stosowanie w opisach pakietu zamiennie nowej nazwy SimpleLink Sensor and Actuator Plugin oraz starej nazwy Sensor Actuator Interface Layer (SAIL). Na przykład, tak nazywa się folder z zainstalowanym pakietem na dysku. Pakiet zawiera przykładowy projekt i2cbme280, który korzysta z firmowego pakietu BME280 sensor driver/API firmy Bosch kompatybilnego z pakietem BME680 sensor driver/API.
Pakiet SimpleLink Sensor and Actuator Plugin (1.50.00.00) ma następujące wymagania [13]:
- Windows 7, Windows 8, Windows 10, Ubuntu 14.04, Mac OS X El Capitan,
- Code Composer Studio 9.2, lepiej zastosować najnowszą wersję CCS,
- simplelink_cc13x2_26x2_sdk_3_40_00_02 SDK lub nowsza wersja [12].
Tworzenie projektu obsługi czujnika BME680
Poniżej zostanie opisany sposób dołączenia czujnika BME680 do procesora CC1352R1. Czujnik jest zamontowany na płytce drukowanej modułu BME680 Environmental Sensor [6] a procesor na płytce drukowanej zestawu startowego CC1352R1 LaunchPad [S15].
Jako środowisko programowe zostanie zastosowany Code Composer Studio (9.3 lub nowszy). Można go darmowo pobrać ze strony producenta Texas Instruments. Po zainstalowaniu CCS trzeba doinstalować pakiet SimpleLink Sensor and Actuator Plugin (1.50.00.00) [13] oraz pakiet SimpleLink cc13x2 26x2 SDK (3.40.00.02 lub nowszy) [12].
Pracę rozpoczynamy od użycia projektu i2cbme280_CC1352R1_LAUNCHXL_tirtos_ccs z pakietu SimpleLink Sensor and Actuator Plugin. Projekt jest przeznaczony do obsługi komunikacji w standardzie I2C czujnika BME280. Ma on taki sam interfejs programowy jak czujnik BME680. Różni się trochę zawartością mapy adresowej rejestrów oraz dodaniem pomiaru gazu. Program wysyła napisy poprzez łącze UART do portu wirtualnego COM komputera dołączonego do zestawu startowego CC1352R1 LaunchPad. Umożliwia to oglądanie na bieżąco aktualnych danych pobranych z czujnika. Opis projektu i parametrów jest zamieszczony w pliku REDAME.html w folderze projektu.
1. Dołącz zestaw startowy CC1352R1 LaunchPad kablem USB do komputera.
2. Wystartuj środowisko CCS.
3. Utwórz folder roboczy o nazwie work_BME680_SPI w ścieżce C:\home_dir.
Taki sposób nazywania i umieszczania foldera roboczego ułatwia potem orientację wśród wielu folderów o podobnych nazwach. Umożliwia też przenoszenie foldera roboczego projektu pomiędzy komputerami o tej samej strukturze folderów.
4. Zaimportuj projekt i2cbme280_CC1352R1_LAUNCHXL_tirtos_ccs z pakietu SimpleLink Sensor and Actuator Plugin.
5. Zmień nazwę projektu na spibme680_CC1352R1_LAUNCHXL_tirtos_ccs. W oknie Project Explorer kliknij prawym klawiszem na linię projektu, z podręcznego menu wybierz Rename i zmień nazwę.
6. Pobierz pliki sterownika firmowego Bosch Sensortec drivers z repozytorium Github [10].
Na stronie repozytorium kliknij przycisk [Clone or download] a następnie [Download ZIP]. Rozpakuj archiwum w eksploratorze plików.
7. Dodaj pliki do projektu. Po kolei zaznacz pliki źródłowe i przeciągnij (drag and drop) na linię projektu i2cbme680_ CC1352R1_LAUNCHXL_tirtos_ccs w oknie Project Explorer. Pozostaw wybraną opcję Copy files.
8. Zmień nazwę pliku i2cbme280.c na spibme680.c.
Zmodyfikuj kod źródłowy pliku spibme680.c według opisu w pliku REDAME pakietu drajwera firmowego Bosch Sensortec drivers.
- Zastąp linię kodu #include <ti/sail/bme280/bme280.h> na #include “bme680.h”.
- Zastąp linię kodu #include <ti/drivers/I2C.h> na #include <ti/drivers/SPI.h>.
- Pod definicjami zmiennych globalnych należy umieścić kod funkcji służących do obsługi komunikacji szyną SPI: user_delay_ms, user_spi_read oraz user_spi_write. Są to funkcje realizowane przez użytkownika specjalnie dla zastosowanego procesora.
- Poniżej należy umieścić funkcję getIAQ obliczającą IAQ.
- Należy zmodyfikować funkcję główną aplikacji.
Tych modyfikacji jest sporo. Dlatego najprościej jest wymienić plik i2cbme680.c na plik spibme680.c pobrany ze strony FTP.
9. Otwórz plik i2cbme280.syscfg.
10. W nowym oknie edycyjnym, w lewym panelu znajdź I2C i kliknij na niego.
11. W prawym panelu kliknij na ikonkę kosza, usuń definicję I2C.
12. W lewym paneli kliknij na SPI.
13. W prawym panelu kliknij na przycisk ADD (rysunek 4).
14. Zmień tryb (Mode) na Four Pin SS Active Low.
15. Ustaw Default TX Buffer Value na 0xFF.
16. Rozwiń listę PinMUX (Peripheral and Pin Configuration).
17. Wybierz: SCLK Pin: DIO10, MISO Pin: DIO8, MOSI Pin: DIO9, SS Pin: DIO11.
Pojawiają się informacje Connected to hardware. Te linie są dołączone do pamięci SPI Flash zamontowanej na płytce zestawu startowego CC1352R LaunchPad. Nie ma to znaczenia, ponieważ szyna SPI jest współdzielona z zastosowaniem osobnych sygnałów wyboru (CS, SS). Nazwa CONFIG_SPI_0 jest używana jako odwołanie do uchwytu dla pracy z układem SPI.
Funkcja mainThread() w pliku i2cbme680.c została poważnie zmodyfikowana w stosunku do wersji w pliku readme. Zostało dodanych sporo wydruków opisujących błędy występujące podczas pracy. Bardzo ułatwia to uruchamianie programu oraz umożliwia lepsze orientowanie się w działaniu czujnika.
Pierwszy fragment kodu funkcji wykonuje inicjalizację modułu peryferyjnego SPI procesora CC1352R1. Następnie wykonywana jest inicjalizacja czujnika BME680. Dane potrzebne do konfigurowania czujnika BME680 są przechowywane w strukturze gas_sensor typu bme680_dev (zdefiniowanej w pliku bme680_defs.h). Po ustawieniu w strukturze parametrów czujnika wykonywana jest funkcja bme680_init, która wysyła do czujnika polecenie resetu programowego oraz odczytuje identyfikator układu scalonego (rysunek 11) a następnie dane kalibracyjne (zaczynając od adresu 0x89, brak opisu rejestrów) oraz inne współczynniki. Następnie konfigurowane są rejestry sterujące czujnika BME680. Ustawiane są parametry pomiaru wilgotności, ciśnienia, temperatury i gazu (w tej kolejności). Dla czujnika gazu ustawiana jest temperatura pracy na 320°C oraz czas podgrzewania na 150 ms (typowe warunki pracy).
Teraz wysyłana jest komenda (rysunek 9, linia 348) wystartowania pomiaru (rysunek 12). Następnie w funkcji bme680_get_profile_dur (linia 357) jest obliczany i ustawiany dokładny czas podgrzewania (profil). Dla powyższych ustawień wynosi on typowo 183 ms. Jego wartość jest bardzo ważna, ponieważ co najmniej tyle czasu trzeba po wystartowaniu pomiaru czekać na dostęp do zwalidowanych i stabilnych danych.
Praca układu jest zorganizowana w pętli nieskończonej (linia 368). Teraz już można odczytać (linia 372) skalibrowane dane pomiarowe (rysunek 13). Są one wysyłane do portu UART (linia 382). Następnie wysyłana jest komenda wykonania kolejnego pomiaru (linia 392) i procesor jest wprowadzany w uśpienie na czas 1 sekundy (linia 396). Po wybudzeniu procesora program powraca do wykonywania pętli nieskończonej i wysyła do portu UART dane ostatniego pomiaru. W ten sposób unika się czekania 183 ms na dostęp do danych oraz oszczędza energię zasilania.
Uruchamianie projektu obsługi czujnika BME680
18. Zbuduj projekt przyciskiem Build. Nie powinny być zasygnalizowane żadne błędy kompilacji i powinien być wygenerowany plik spibme680_CC1352R1_LAUNCHXL_tirtos_ccs.out. Projekt zawiera już gotową definicję modułu sprzętowego (w folderze targetConfigs).
19. Zaprogramuj przyciskiem Debug pamięć Flash procesora wygenerowanym kodem.
Projekt jest zorganizowany z zastosowaniem systemu operacyjnego TIRTOS. Po załadowaniu kodu wykonywany jest reset procesora i program jest uruchamiany do pierwszej linii kodu funkcji main() w pliku main_tirtos.c.
W funkcji main wykonywana jest inicjalizacja procesora i tworzone jest zadanie (wątek) mainThread (z kodem w pliku spibme680.c). Na koniec działania funkcji main() rozpoczyna działać system operacyjny i zostaje uruchamiane wykonanie jedynego zadania (task) mainThread.
Sprawdź w Menedżerze Urządzeń systemu Windows, jaki numer portu COM został przypisany do kanału XDS110 Class Application/User UART.
Do tego portu dołącz terminal znakowy, na przykład PuTTy. Wymagane ustawienia 115200/8/1/N.
Rozpocznij wykonywanie programu przyciskiem Resume.
Przykładowy wydruk podczas pracy projektu obsługi czujnika BME680 jest pokazany na listingu 1.
Starting the spibme680 sensor example...
SPI Initialized!
Chip ID: 0x61, Chip Addr: 0x0
BME680 Initialization OK!
BME680 sensor configuration OK!
BME680 Trigger the measurement OK!
Heater temperature: 320 Celcius degree, Heater duration: 150 ms
Ambient temperature: 25
Measurement duration: 183 ms
Pressure: 1011.7399 hPa, Temp: 21.9899 DegC, Humidity: 48.8310 %RH
Gas_res: 171971 Ohms, Gas_res_min: 161213 Ohms, Gas_res_max: 173936 Ohms, Gas_res_%: 84.5555 %
Hum_IAQ: 18.3982, Gas_IAQ: 316.5969, IAQ: 334
Air quality is: Hazardous
Pressure: 1011.7399 hPa, Temp: 21.9899 DegC, Humidity: 48.8240 %RH
Gas_res: 172503 Ohms, Gas_res_min: 161213 Ohms, Gas_res_max: 173936 Ohms, Gas_res_%: 88.7369 %
Hum_IAQ: 18.3836, Gas_IAQ: 316.4051, IAQ: 334
Air quality is: Hazardous...
Wysoki poziom indeksu IAQ został uzyskany niedługo po pierwszym włączeniu układu BME680 i wynika z zastosowania wysokiego progu górnego wartości rezystancji czujnika, oszacowanego w poprzednim eksperymencie [S36]. Dodatkowo zapisywana jest największa i najmniejsza wartość rezystancji czujnika oraz obliczane jest, jaki procent wartości pomiędzy nimi stanowi aktualna wartość rezystancji. Daje to pewny wgląd w dynamikę zmian poziomu (typowo wzrost) wartości rezystancji czujnika w dłuższym okresie (kilku dni) eksploatacji.
Wartości temperatury, ciśnienia i wilgotności są pokazywane (nadmiarowo) z czterema miejscami po przecinku, ponieważ wystąpiły kłopoty z obsługą formatowania wydruku liczb ułamkowych przez bibliotekę firmową.
Uruchamianie obsługi czujnika BME680
Projekt jest bardzo łatwy do debugowania w środowisku CCS. Po uruchomieniu działania programu można go zatrzymać w każdej chwili przyciskiem Suspend. Teraz powrót do stanu bezpośrednio po załadowaniu kodu programu (przyciskiem Debug) jest prosty. Trzeba kliknąć na ikonkę System Reset a następnie ikonkę Restat.
Po wykonaniu restartu działanie programu jest ponownie zatrzymywane w pierwszej linii kodu funkcji main(). W każdej linii kodu (nie komentarza) w plikach ic2bme60.c oraz bme680.c można ustawiać pułapki (sprzętowe). Wystarczy dwa razy klinąć na pasku z numeracją linii kodu źródłowego. Dostępna jest też praca krokowa z wchodzeniem do wywoływanych w linii kodu funkcji lub bez. Najechanie kursorem na nazwę funkcji z przyciśniętym klawiszem CTRL pozwala, po kliknięciu na nią, na przeniesienie się do miejsca definicji tej funkcji. Tak samo jest z deklaracjami zmiennych i stałych.
Uruchamianie pracy czujnika BME680 okazało się dosyć trudne. Bardzo w tym pomógł oscyloskop z analizą protokołu SPI. Odczyt rejestru identyfikatora układu scalonego 0x61 spod adresu 0x50 jest pokazany na rysunku 10.
Najpierw na szynie SPI (linia MOSI, wejście SDI układu BME680) jest wysłany bajt adresowy z ustawionym bitem odczytu (0xD0 = 0x50 + 0x80). Układ BME680 na linii MISO (wyjście SDO) utrzymuje trzeci stan. Następnie układ BME680 wystawia na niej zawartość rejestru (0x61).
Wystartowanie pomiaru jest bardziej złożone (rysunek 11). Najpierw odczytywany jest stan rejestru Ctrl_meas (adr. 0x74 + 0x80 = 0xF4). Pole bitowe mode1:0 tego rejestru musi mieć wartość 0x00, co oznacza, że nie jest wykonywany pomiar. Odczytana wartość 0x8C oznacza zerową zawartość pola mode. Dopiero teraz można w pole mode wpisać wartość 0x01, bez zmiany stanu pozostałych bitów (0x8C + 0x01 = 0x8D). Jest to wykonane w następnej parze bajtów.
Sekwencja odczytu danych pomiarowych trwa ok. 1,27 ms, a odstęp powtarzania ok. 1019,8 ms (rysunek 12). Najpierw odczytywany jest stan rejestru Eas_status_0 (adr. 0x1D + 0x80 = 0x8D). Odczytana zawartość 0x80 oznacza, że są gotowe nowe dane. W kolejnym rejestrze (adr. 0x1E) są następne znaczniki, ale już nie ma ich opisu w dokumentacji fabrycznej. O ich znaczeniu można wnioskować z kodu biblioteki firmowej. Zawartość kolejnych rejestrów danych jest już w dokumentacji lepiej opisana.
Szyna SPI pracuje z dosyć niską częstotliwością zegara 100 kHz (rysunek 10). Próby ze zwiększeniem częstotliwości wykazały kłopoty układu SPI (SSI) procesora CC1252R1 z obsługą ramki (rysunek 13). Losowo zdejmował on sygnał CS po pierwszym bajcie adresowym na czas ok. 33 ns. Powodowało to brak odpowiedzi układu BME680.
Eksperymenty z obsługą czujnika BME680
Zrealizowany zestaw został eksploatowany przez dłuższy czas. Do referencyjnego pomiaru temperatury i wilgotności został zastosowany zestaw uruchomieniowy SHT31 Smart Gadget firmy Sensirion [S32]. Wartości odczytane z czujnika BME680 były porównywane z pomiarami wykonywanymi przez czujnik SHT31 firmy Sensirion. Typowo temperatura odczytywana przez czujnik jest wyższa od temperatury otoczenia o ok. 1,2°C, a odczytywana wilgotność niższa o ok. 2,3%. Są to wyniki porównywalne z uzyskanymi dla transmisji I2C [S36].
Drugi zastosowany do porównania moduł czujnikowy to Thingy:52 firmy Nordic Semicoductor [S21]. W nim jest zastosowany czujnik ciśnienia LPS22HB firmy ST Microelectronics, czujnik wilgotności względnej i temperatury HTS221 firmy ST Microelectronics oraz jakości powietrza CCS811 firmy AMS. Układ CCS811 pozwala na wykrywanie w powietrzu bardzo niskiego stężenia dwutlenku węgla (CO2) oraz lotnych związków organicznych VOC. Na podstawie rezystancji czujnika MOX obliczany jest pomiar przez wewnętrzny mikroprocesor:
- eCO2 – równoważny (equivalent) poziom dwutlenku węgla, w zakresie od 400 ppm do 32768 ppm.
- eTVOC – równoważny całkowity (equivalent Total) poziom lotnych związków organicznych w zakresie od 0 ppb do 32768 ppb.
Odczyty ciśnienia obu czujników były prawie identyczne. Czujnik SHT31 pokazywał najniższą temperaturę. Ma on największą dokładność i jest zamontowany na „wysepce” płytki drukowanej. Thingy:52 pokazywał najwyższą wilgotność, o ok. 3% wyższą niż czujnik SHT31. Dotyczyło to także innych egzemplarzy tego modułu czujnikowego.
Układ CCS811 pokazywał bardzo niski poziom eTVOC. Kierunek zmian tego poziomu był skorelowany ze zmianami rezystancji czujnika BME680. Jednak w trakcie prób wystąpił problem z określeniem górnego i dolnego zakresu pomiaru rezystancji czujnika gazu układu BME680. Nie udało się znaleźć takiej informacji w dokumentacji firmowej. W sieci podawana jest wartość górna ok. 50 kΩ. Próby pokazały, że po pierwszym włączeniu układu wartość rezystancji czujnika jest dosyć niska ok. 100 kΩ. Rośnie ona stopniowo w ciągu kilku dni. Badania pokazały wartości sięgające 950 kΩ, a nawet ponad 1,4 MΩ. Ustalenie górnej wartości jest istotne dla określenia skali do obliczeń indeksu IAQ.
Po włączeniu zasilania i rozpoczęciu wykonywania pomiarów w regularnych odstępach (tutaj ok. 1 s) odczytywana wartość rezystancji czujnika gazu zaczyna rosnąć i stabilizuje się po pewnym czasie. W opisach podawana jest nawet konieczność odczekania 30 minut [9]. Wydaje się, że dopiero zastosowanie firmowej biblioteki BSEC i obliczanie estymowanego poziom VOC może pozwolić na porównanie działania obu czujników jakości powietrza. Jednorazowa próba w niekontrolowanych warunkach nie może być podstawą do wyciągania zbyt daleko idących wniosków.
Podsumowanie
Pierwsza próba podłączenia układu BME680 do procesora CC1352R1 z zastosowaniem transmisji SPI została podjęta w ramach projektów studenckich przedmiotu Systemy dla Internetu Rzeczy na Wydziale Elektroniki i Technik Informacyjnych Politechniki Warszawskiej. Pozwoliła ona na opracowanie sposobu użycia firmowych sterowników dla modułu SPI procesora. Integracja tego kodu z biblioteką Bosch Sensortec drivers znowu wymagała zaglądania do kodu źródłowego. Spowodowane jest to brakiem opisu biblioteki. Na szczęście kod źródłowy jest dosyć dobrze skomentowany. Dodatkową trudność sprawia brak w dokumentacji firmowej pełnego opisu wszystkich rejestrów układu BME680. O działaniu niektórych rejestrów sterujących można się dowiedzieć tylko na podstawie zachowania programu.
Próby z zastosowaniem kodu funkcji selftest dołączonej do biblioteki Bosch Sensortec drivers dalej nie bardzo się powiodły. Zostaną one ponowione później. Nie została, na razie, podjęta próba wykorzystania firmowej biblioteki BSEC.
Tak jak się można było spodziewać, problemy z zastosowaniem czujnika gazu dotyczyły kalibracji. Procedury postępowania kalibracyjnego takich czujników są dosyć skomplikowane. Typowo wymagają one wystawienia czujnika na czyste powietrze. Wtedy taki minimalny poziom jest traktowany jako poziom referencyjny. Potrzebne jest do tego odpowiednie oprogramowanie i możliwość przechowywania/zapisu danych kalibracyjnych. A i tak procedurę należy okresowo powtarzać.
Zaskakująco dobrze wygląda debugowanie działania programu. Kod biblioteki Bosch Sensortec drivers jest tak przejrzyście zorganizowany, że bardzo łatwo można śledzić działanie programu, nawet na poziomie pracy krokowej.
Dłuższy okres ciągłego działania układu BME680 dołączonego do procesora pokazuje stabilną pracę z występowaniem małych fluktuacji surowej wartości pomiaru rezystancji czujnika gazu. Ale aktualnym celem było tylko uzyskanie stabilnej pracy oprogramowania z użyciem procesora CC1352R1. Pozytywny wynik daje podstawę do wykonania prób dołączenia kolejnych czujników i rozbudowania oprogramowania.
Henryk A. Kowalski
Instytut Informatyki
Politechnika Warszawska
Zdjęcia: Piotr T. Kowalski
Wybrane artykuły kursu „Systemy dla Internetu Rzeczy” z miesięcznika „Elektronika Praktyczna”:
[S15] Zestaw CC1352R1 LaunchPad, EP 5/2018
[S21] Zestaw Nordic Thingy:52 IoT Sensor Kit, EP 12/2018
[S31] Nordic Thingy:91 – platforma prototypowania dla mobilnego IoT, EP 11/2019
[S32] Scalone czujniki cyfrowe wilgotności i temperatury, EP 12/2019
[S34] Cyfrowe czujniki gazu, EP 2/2020
[S36] Pomiar jakości powietrza, ciśnienia, wilgotności i temperatury czujnikiem BME680 dołączonym do zestawu startowego CC1352R1 LaunchPad z transmisją protokołem I2C, EP 3/2020
Literatura
[1] BME680 Low power gas, pressure, temperature & humidity sensor, Bosch Sensortec, http://bit.ly/2P0cyry
[2] BME680 Datasheet, rev.1.3, July 2019, BST-BME680-DS001, Bosch, http://bit.ly/2U9wiL1
[3] BME680 Self-test application note, rev.1.4, May 2018, BST-BME680-AN014, Bosch, http://bit.ly/2WfZQJK
[4] BME680 IAQ Example, David Bird, http://bit.ly/2TXVvcD
[5] Moduł czujnika BME680 – v.1.1a – Shield do Wemos D1 mini, Nettigo, http://bit.ly/2UdmTSD
[6] Gravity: I2C BME680 Environmental Sensor, SKU:SEN0248, Product Page, DFRobot, http://bit.ly/2x72Pta
[7] Gravity: I2C BME680 Environmental Sensor – czujnik środowiska 4 w 1, DFRobot SEN0248, Kamami, http://bit.ly/2wdWvAb
[8] DFRobot’s BME680 Environmental Sensor, Wiki, http://bit.ly/2w5Ly3P
[9] Adafruit BME680, Adafruit, http://bit.ly/2QpkD9M
[10] BoschSensortec, Github, BME680 sensor driver/API including example guide. Bosch Sensortec GmbH, 29 Jun 2018, http://bit.ly/3d6plDf
[11] Bosch Sensortec Environmental Cluster (BSEC) v1.4.7.4, July 3rd, 2019, http://bit.ly/2Qod2by
[12] SimpleLink CC13x2 and CC26x2 software development kit (SDK) (Ver. 3.40.00.02), Texas Instruments, http://bit.ly/38I8TXC
[13] SimpleLink Sensor and Actuator Plugin (1.50.00.00), Texas Instruments, http://bit.ly/2w1Ihm2