Czujniki HAL 1.0

Interfejs HAL Sensors zadeklarowany w sensors.h reprezentuje interfejs między platformą Androida a konkretnego oprogramowania. Implementacja HAL musi zdefiniować każdą funkcję zadeklarowaną w pliku sensors.h. Główne funkcje to:

  • get_sensors_list – zwraca listę wszystkich czujników.
  • activate – uruchamia lub zatrzymuje czujnik.
  • batch – ustawia parametry czujnika, takie jak częstotliwość próbkowania i maksymalne opóźnienie raportowania.
  • setDelay – używany tylko w wersji 1.0 interfejsu HAL. Ustawia częstotliwość próbkowania dla danego czujnika.
  • flush – opróżnia FIFO określonego czujnika i zgłasza zakończenie czyszczenia. .
  • poll – zwraca dostępne zdarzenia z czujnika.

Implementacja musi być bezpieczna w zasobie wątków i umożliwiać wywoływanie tych funkcji z różnych wątków.

Interfejs definiuje też kilka typów używanych przez te funkcje. Główne typy to:

  • sensors_module_t
  • sensors_poll_device_t
  • sensor_t
  • sensors_event_t

Więcej informacji o tych typach znajdziesz w pliku sensors.h, a nie tylko w sekcjach poniżej.

get_sensors_list(list)

int (*get_sensors_list)(struct sensors_module_t* module, struct sensor_t
  const** list);

Udostępnia listę czujników wdrożonych przez HAL. Szczegółowe informacje o definiowaniu czujników znajdziesz w sekcji sensor_t.

Czujniki na liście pojawiają się w kolejności, w jakiej będą przesyłane do aplikacji. Zwykle najpierw pojawiają się czujniki podstawowe, a potem złożone.

Jeśli kilka czujników ma ten sam typ i właściwości wybudzania, pierwszy czujnik na liście jest nazywany „domyślnym”. To ten zwrócony przez getDefaultSensor(int sensorType, bool wakeUp)

Ta funkcja zwraca liczbę czujników na liście.

aktywuj(czujnik, prawda/fałsz)

int (*activate)(struct sensors_poll_device_t *dev, int sensor_handle, int
  enabled);

Aktywuje lub dezaktywuje czujnik.

sensor_handle to uchwyt czujnika do aktywacji/dezaktywacji. Uchwyt czujnika jest zdefiniowany przez pole handle w strukturze sensor_t.

Wartość enabled 1 włącza czujnik, a 0 – wyłącza.

Jednorazowe czujniki wyłączają się automatycznie po otrzymaniu zdarzenia. Aby je wyłączyć, należy je aktywować, wykonując połączenie do activate(..., enabled=0).

Czujniki wybudzania nigdy nie zapobiegają przechodzeniu układu SOC w tryb zawieszenia. które jest, HAL nie może stosować częściowej blokady uśpienia w imieniu aplikacji.

Czujniki wybudzania podczas ciągłego dostarczania zdarzeń mogą uniemożliwić układowi SOC przechodzi w tryb zawieszenia, ale jeśli nie trzeba dostarczyć żadnego zdarzenia, blokada wybudzania musi być zdjęta.

Jeśli enabled = 1, a czujnik jest już aktywny, ta funkcja nie wykonuje żadnej operacji i kończy się sukcesem.

Jeśli enabled = 0 i czujnik jest już dezaktywowany, ta funkcja nie wykonuje żadnej operacji i kończy się sukcesem.

Ta funkcja zwraca 0 w przypadku powodzenia i ujemną liczbę błędu w przeciwnym przypadku.

wsad(czujnik, flagi, okres próbkowania, maksymalny czas oczekiwania na raport)

int (*batch)(
     struct sensors_poll_device_1* dev,
     int sensor_handle,
     int flags,
     int64_t sampling_period_ns,
     int64_t max_report_latency_ns);

Ustawia parametry czujnika, w tym częstotliwość próbkowania oraz Raport o maksymalnej liczbie wyświetleń Funkcję tę można wywołać podczas aktywacji czujnika. W tym przypadku nie może ona spowodować utraty pomiarów czujnika. Przejście z jednego współczynnika próbkowania na inny nie może spowodować utraty zdarzeń. Nie może też nastąpić przejście z wysokiej maksymalnej latencji raportu na niską maksymalną latencję raportu.

sensor_handle to uchwyt czujnika do skonfigurowania.

Konto flags nie jest obecnie używane.

sampling_period_ns to okres próbkowania, w którym powinien działać czujnik (w nanosekundach). Zobacz sampling_period_ns dla .

max_report_latency_ns to maksymalny czas, do którego mogą być rejestrowane zdarzenia jest opóźniony przed zgłoszeniem przez HAL, w nanosekundach. Zobacz max_report_latency_ns .

Ta funkcja zwraca 0 w przypadku powodzenia i ujemną liczbę błędu w przeciwnym przypadku.

setDelay(czujnik; okres próbkowania)

int (*setDelay)(
     struct sensors_poll_device_t *dev,
     int sensor_handle,
     int64_t sampling_period_ns);

Po wersji HAL 1.0 ta funkcja została wycofana i nigdy nie jest wywoływana. Zamiast tego funkcja batch jest wywoływana w celu ustawienia atrybutu sampling_period_ns.

W wersji HAL 1.0 do ustawienia parametru sampling_period_ns używana była funkcja setDelay zamiast batch.

flush(czujnik)

int (*flush)(struct sensors_poll_device_1* dev, int sensor_handle);

Dodaj zdarzenie flash complete na końcu sprzętowego FIFO określonego czujnika i usuwa FIFO. te zdarzenia są dostarczane w zwykły sposób (tj. tak, jakby maksymalny opóźnienie raportowania był możliwy stracił ważność) i został usunięty z FIFO.

Usuwanie danych odbywa się asynchronicznie (tj. ta funkcja musi wrócić natychmiast). Jeśli implementacja używa jednego kolejki FIFO dla kilku czujników, ta kolej jest opróżniana, a zdarzenie o ukończeniu opróżniania jest dodawane tylko w przypadku określonego czujnika.

Jeśli określony czujnik nie ma FIFO (brak możliwości buforowania) lub jeśli FIFO, było puste w momencie wywołania, flush musi mimo to potwierdzić i wysyła zdarzenie opróżnienia dla tego czujnika. Dotyczy to wszystkich czujników oprócz czujników jednorazowych.

Gdy wywołana zostanie funkcja flush, nawet jeśli zdarzenie czyszczenia znajduje się już w FIFO dla danego czujnika, należy utworzyć dodatkowe zdarzenie i dodać je na końcu FIFO, a także opróżnić FIFO. Liczba: flush muszą być równe liczbie utworzonych zdarzeń całkowitego usunięcia.

flush nie dotyczy one-shot czujniki; jeśli sensor_handle odnosi się do czujnika pojedynczego, Funkcja flush musi zwrócić wartość -EINVAL i nie może generować żadnych flush pełne zdarzenie metadanych.

Ta funkcja zwraca 0 w przypadku powodzenia, -EINVAL, jeśli podany czujnik jest z czujnikiem jednorazowym lub nie został włączony, a w przeciwnym razie wartość błędu była ujemna.

ankieta()

int (*poll)(struct sensors_poll_device_t *dev, sensors_event_t* data, int
  count);

Zwraca tablicę danych z czujnika, wypełniając argument data. Ta funkcja musi blokować do momentu, gdy zdarzenia będą dostępne. W przypadku powodzenia zwraca liczbę odczytanych zdarzeń, a w przypadku błędu – ujemną liczbę błędu.

Liczba zdarzeń zwracanych w funkcji data nie może być większa niż argumentu count. Ta funkcja nigdy nie zwraca 0 (brak zdarzenia).

Kolejność wywołań

Gdy urządzenie się uruchamia, wywoływana jest funkcja get_sensors_list.

Gdy czujnik zostanie aktywowany, zostanie wywołana funkcja batch z wymaganymi parametrami, a następnie activate(..., enable=1).

W wersji HAL 1_0 kolejność była odwrotna: najpierw wywoływana była funkcja activate, a potem set_delay.

Gdy podczas aktywacji czujnika zmieniają się żądane cechy czujnika, wywoływana jest funkcja batch.

flush może być wywoływany w dowolnym momencie, nawet w przypadku nieaktywnych czujników (w takim przypadku musi zwracać -EINVAL).

Gdy czujnik zostanie dezaktywowany, zostanie wywołana funkcja activate(..., enable=0).

Równolegle z tymi wywołaniami funkcja poll będzie wielokrotnie wywoływana w celu żądania danych. poll może być wywoływany nawet wtedy, gdy nie są aktywne żadne czujniki.

czujniki_moduł_t

sensors_module_t to typ używany do tworzenia modułu sprzętowego Androida dla czujników. Implementacja HAL musi definiować obiekt HAL_MODULE_INFO_SYM tego typu do udostępniania funkcji get_sensors_list. Zobacz definicja elementu sensors_module_t w pliku sensors.h i definicja obiektu hw_module_t .

czujniki_poll_device_t / czujniki_poll_device_1_t

Pole sensors_poll_device_1_t zawiera pozostałe metody zdefiniowane powyżej: activate, batch, flush i poll. Jego pole common (typu hw_device_t) określa numer wersji HAL.

czujnik_t

sensor_t reprezentuje Androida . Oto kilka ważnych pól:

name: widoczny dla użytkownika ciąg znaków reprezentujący czujnik. Ten ciąg jest często zawiera nazwę części i typ czujnika oraz czy to czujnik wybudzania. Przykłady: „LIS2HH12 Accelerometer”, „MAX21000 Uncalibrated Gyroscope”, „BMP280 Wake-up Barometer”, „MPU6515 Game Rotation Vector”.

handle:liczba całkowita używana do odwoływania się do czujnika podczas rejestracji lub i generowanie z niego zdarzeń.

type: typ czujnika. Więcej informacji o typach czujników znajdziesz w artykule Czym są czujniki Androida?, a o oficjalnych typach czujników – w artykule Typy czujników. Dla: nieoficjalne typy czujników, type musi zaczynać się od SENSOR_TYPE_DEVICE_PRIVATE_BASE

stringType: typ czujnika w postaci ciągu znaków. Gdy czujnik ma oficjalny typ ustawiony na SENSOR_STRING_TYPE_*. Kiedy czujnik ma typ konkretnego producenta, stringType musi zaczyna się od odwrotnej nazwy domeny producenta. Na przykład czujnik (np. wykrywacz jednorożców) zdefiniowany przez zespół Cool-product na stronie Fikcyjna firma może użyć stringType=”com.fictional_company.cool_product.unicorn_detector” Wartość stringType służy do jednoznacznej identyfikacji nieoficjalnych typów czujników. Więcej informacji o typach i typach ciągów znajdziesz w pliku sensors.h.

requiredPermission: ciąg znaków reprezentujący uprawnienia, które aplikacje muszą mieć, aby widzieć czujnik, zarejestrować go i otrzymywać z niego dane. Pusty ciąg znaków oznacza, że aplikacje nie wymagają żadnych uprawnień do dostępu do tego czujnika. Niektóre typy czujników, takie jak monitor tętna, mają obowiązkowe requiredPermission. Wszystkie czujniki dostarczające informacje o użytkowniku o charakterze wrażliwym (takie jak tętno) muszą być chronione przez uprawnienia.

flagi: flagi tego czujnika określające tryb raportowania i to, czy jest to czujnik aktywacji. Może to być na przykład czujnik wybudzania za jednym razem. będzie mieć flags = SENSOR_FLAG_ONE_SHOT_MODE | SENSOR_FLAG_WAKE_UP. Bity flagi, które nie są używane w bieżącej wersji HAL, muszą być równe 0.

maxRange: maksymalna wartość, jaką może podać czujnik, w tych samych jednostkach co wartości zgłoszone. Czujnik musi mieć możliwość raportowania wartości bez nasycenia w ciągu [-maxRange; maxRange]. Pamiętaj, że oznacza to całkowity zakres czujnik w ogólnym sensie to 2*maxRange. Gdy czujnik wskaże wartości przekraczające kilku osi, zakres odnosi się do każdej z nich. Na przykład akcelerometr „+/- 2g” podaje wartość maxRange = 2*9.81 = 2g.

resolution: najmniejsza różnica w wartości, jaką może mierzyć czujnik. Zwykle obliczane na podstawie maxRange i liczby bitów w pomiarach.

power: koszt energii potrzebny do włączenia czujnika w miliampach. Jest to prawie zawsze więcej niż zużycie energii podane w arkuszu danych czujnika. Więcej informacji znajdziesz w artykule Base sensors != physical sensors, a szczegółowe informacje o mierzeniu poboru mocy przez czujnik – w artykule Proces pomiaru poboru mocy. Jeśli pobór mocy czujnika zależy od tego, czy urządzenie się porusza, w polu power raportowany jest pobór mocy podczas ruchu.

minDelay: w przypadku ciągłych czujników okres próbkowania w mikrosekundach odpowiadający najszybszej częstotliwości obsługiwanej przez czujnik. Zobacz sampling_period_ns dla o sposobie wykorzystania tej wartości. Pamiętaj, że minDelay wyrażony w mikrosekundach, podczas gdy sampling_period_ns jest w nanosekund. W przypadku czujników przy zmianie oraz specjalnego trybu raportowania, chyba że w innym przypadku wartość minDelay musi wynosić 0. W przypadku czujników jednorazowych musi ona mieć wartość -1.

maxDelay: w przypadku ciągłych i zmiennych czujników okres próbkowania w mikrosekundach odpowiadający najwolniejszej częstotliwości obsługiwanej przez czujnik. Zobacz sampling_period_ns dla o sposobie wykorzystania tej wartości. Pamiętaj, że maxDelay jest wyrażona w mikrosekundach, a sampling_period_ns – w nanosekundach. W przypadku czujników specjalnych i jednorazowych wartość maxDelay musi wynosić 0.

fifoReservedEventCount: liczba zdarzeń zarezerwowanych dla tego czujnika w FIFO sprzętowym. Jeśli dla tego czujnika istnieje dedykowany FIFO, fifoReservedEventCount to rozmiar tego dedykowanego FIFO. Jeśli kolejka FIFO jest współdzielona z innymi czujnikami, fifoReservedEventCount to rozmiar części kolejki FIFO zarezerwowanej dla danego czujnika. W większości systemów FIFO oraz wł. w systemach bez sprzętowego FIFO ta wartość wynosi 0.

fifoMaxEventCount: maksymalna liczba zdarzeń, które mogą być przechowywane w FIFO dla tego czujnika. Zawsze jest równa lub większa od wartości fifoReservedEventCount. Ta wartość służy do oszacowania, jak szybko FIFO zapełni się podczas rejestrowania w czujniku z określoną szybkością, przy założeniu, że nie są aktywowane żadne inne czujniki. W systemach, które nie mają FIFO sprzętowego, fifoMaxEventCount ma wartość 0. Więcej informacji znajdziesz w sekcji Grupowanie wsadowe.

W przypadku czujników z oficjalnym typem niektóre pola są zastępowane przez platformę. Przykład: czujniki akcelerometru muszą korzystać z trybu ciągłego raportowania, a monitory tętna są musi być chroniona przez SENSOR_PERMISSION_BODY_SENSORS uprawnienia.

czujniki_zdarzenie_t

Zdarzenia z czujników generowane przez czujniki Androida i zgłaszane za pomocą funkcji ankiety mają wartość type sensors_event_t. Oto niektóre ważne pola w sensors_event_t:

version: musi być sizeof(struct sensors_event_t)

sensor: uchwyt czujnika, który wygenerował zdarzenie, zgodnie z definicją w sensor_t.handle.

type:typ czujnika czujnika, który wywołał zdarzenie, określony za pomocą funkcji sensor_t.type

timestamp: sygnatura czasowa zdarzenia w nanosekundach. To czas, w którym zdarzenie (zrobienie kroku lub pomiar przy użyciu akcelerometru), a nie czas zgłoszenia zdarzenia. Pole timestamp musi być zsynchronizowane z zegara elapsedRealtimeNano, a w przypadku czujników ciągłych zakłócenia. muszą być małe. Filtrowanie sygnatur czasowych jest czasami konieczne, aby spełnić wymagania dotyczące CDD, ponieważ użycie tylko czasu przerwania SoC do ustawienia sygnatur czasowych powoduje zbyt duży jitter, a użycie tylko czasu z układu scalonego czujnika do ustawienia sygnatur czasowych może spowodować brak synchronizacji z zegarem elapsedRealtimeNano, ponieważ zegar czujnika może się przesuwać.

danych i nakładających się pól: wartości mierzone przez parametr . Ich znaczenie i jednostki zależą od typu czujnika. Opis pól danych znajdziesz w pliku sensors.h oraz w definicji różnych typów czujników. W przypadku niektórych czujników podawana jest również dokładność odczytów jako część danych, za pomocą pola status. To pole jest przekazywane tylko w przypadku wybranych typów czujników i wyświetlane na poziomie SDK jako wartość dokładności. W przypadku tych czujników fakt, że pole stanu musi być ustawione jest wymienione w typie czujnika definicji.

Zdarzenia dotyczące pełnego wyczyszczania metadanych

Zdarzenia metadanych mają ten sam typ co zwykłe zdarzenia z czujnika: sensors_event_meta_data_t = sensors_event_t Zdarzenia te są zwracane razem z innymi zdarzeniami czujnika za pomocą metody poll(). Zawierają te pola:

version: musi być META_DATA_VERSION

type: musi być SENSOR_TYPE_META_DATA

sensor, zarezerwowane i timestamp: musi mieć wartość 0.

meta_data.what: zawiera typ metadanych zdarzenia. Obecnie dostępny jest tylko 1 prawidłowy typ metadanych: META_DATA_FLUSH_COMPLETE.

Zdarzenia (META_DATA_FLUSH_COMPLETE) odpowiadają zakończeniem opróżnienia czujnik FIFO. Gdy meta_data.what=META_DATA_FLUSH_COMPLETE, meta_data.sensor musi być ustawiona na uchwyt czujnika, który został opróżniony. Są one generowane tylko wtedy, gdy funkcja flush jest wywoływana w przypadku czujnika. Zapoznaj się z sekcją na temat: użyj funkcji flush.