gps_freerunner.c
今日は出社して mtg な一日。ゲンジツトウヒ気味にソース確認してたり。
しかし標題のソースファイルなんですが、きちんと公開/非公開がソースで明示されていて気持ち良い。公開されている i/f としては以前のエントリでも引用した以下な手続き。
const GpsInterface* gps_get_hardware_interface() { return &freerunnerGpsInterface; }
戻している freerunnerGpsInterface の定義は直上で以下。
static const GpsInterface freerunnerGpsInterface = { freerunner_gps_init, freerunner_gps_start, freerunner_gps_stop, freerunner_gps_set_fix_frequency, freerunner_gps_cleanup, freerunner_gps_inject_time, freerunner_gps_delete_aiding_data, freerunner_gps_set_position_mode, freerunner_gps_get_extension, };
gps_get_hardware 手続きを呼び出すことで、そこから戻ってくる上記にて羅列されている手続きも公開される、という形になりますな。
で、この gps_get_hardware_interface 手続きを呼び出すのは hardware/libhardware_legacy/gps/gps.cpp にて定義されている gps_find_hardware 手続きで、この手続きを呼び出しているのが jni 側との i/f になっている gps_get_interface 手続きになります。
ちなみに gps_get_interface 手続きを呼び出しているのは jni 側の android_location_GpsLocationProvider.cpp からとなってますが、掘削は一旦停止。
GpsInterface 構造体
メンバは関数ポインタのみになってて、定義は hardware/libhardware_lebacy/include/hardware_legacy/gps.h にて以下。
/** Represents the standard GPS interface. */ typedef struct { /** * Opens the interface and provides the callback routines * to the implemenation of this interface. */ int (*init)( GpsCallbacks* callbacks ); /** Starts navigating. */ int (*start)( void ); /** Stops navigating. */ int (*stop)( void ); /** Closes the interface. */ void (*cleanup)( void ); /** Injects the current time. */ int (*inject_time)(GpsUtcTime time, int64_t timeReference, int uncertainty); /** Injects current location from another location provider * (typically cell ID). * latitude and longitude are measured in degrees * expected accuracy is measured in meters */ int (*inject_location)(double latitude, double longitude, float accuracy); /** * Specifies that the next call to start will not use the * information defined in the flags. GPS_DELETE_ALL is passed for * a cold start. */ void (*delete_aiding_data)(GpsAidingData flags); /** * fix_frequency represents the time between fixes in seconds. * Set fix_frequency to zero for a single-shot fix. */ int (*set_position_mode)(GpsPositionMode mode, int fix_frequency); /** Get a pointer to extension information. */ const void* (*get_extension)(const char* name); } GpsInterface;
こっちの名前は基本的には android_location_GpsLocationProvider.cpp 側で使われているはずなので、別途掘削予定という事にしとく。
call graph
とりあえず gps_freerunner.c 内での call graph 作ってみる事に。以下です。
freerunner_gps_init gps_state_init sem_init property_get socketpair pthread_create freerunner_gps_start gps_state_start freerunner_gps_stop gps_state_stop freerunner_gps_set_fix_frequency freerunner_gps_cleanup gps_state_done pthread_join sem_destroy freerunner_gps_inject_time freerunner_gps_delete_aiding_data freerunner_gps_set_position_mode freerunner_gps_get_extension
ええと、usbserial からの吸い出しになるので、thread を kick して処理する形になっているのかな。以下のコメントの通り、gps_state_thread が主処理になっている模様。
/* this is the main thread, it waits for commands from gps_state_start/stop and, * when started, messages from the QEMU GPS daemon. these are simple NMEA sentences * that must be parsed to be converted into GPS fixes sent to the framework */ static void* gps_state_thread( void* arg )
どっちかっつーとこっちをきちんと確認する必要があるみたい。今日はスデに終わってるカンジなので、gps_state_thread 手続きについては別途確認ってコトにさせて下さひ。
おまけ
Android のソースツリーにある LocationManager 関連のソースなパスを以下に控え。