协和影音 伦理 第8页:Android GPS架构分析
来源:百度文库 编辑:偶看新闻 时间:2024/06/03 01:25:14
我们今天就来看看gps的结构分析,下面来看看gps的定位服务(LocationManager)的启动过程。我总是喜欢追本溯源地从源头去认识事物。因为“人之初,性本善”,从事物的本性去认识事物。
LocationManager 这项服务是在SystemServer.java 中启动的,也就是系统启动之后,这个服务就已经启动了:
systemServer.java [framework\base\services\java\com\android\server]。在SystemServer.java的init2函数中启动了一个线程来注册Android的诸多服务,如:Bluetooth Service,NetworkManagement Service,Notification Manager等,当然也包括Location Service。那么我们来看看代码吧:
Java代码:
在ServerThread线程的run函数中LocationManager服务的代码段如下:
Java代码:
在run函数的后半部分,是服务对系统的反馈,就是systemReady()函数。LocationManager服务的反馈函数如下:
Java代码:
Java代码:
而在2.1版本中LocationManagerService的构造函数如下:
LocationManagerService.java [frameworks\base\services\java\com\android\server]
Java代码:
2.2版本
Java代码:
2.1是在构造函数的时候就启动一个自身服务线程。见构造函数。
2.2是在反馈机制中通过systemReady函数启动自身服务线程。如下:
Java代码:
通过线程run函数,调用initialize函数:
Java代码:
我们这一篇是继续上一篇来解析GPS构架的。我们这一篇主要就是讲initialize函数的,但我们要记住的是initialize函数其中一个是最重要的,那就是loadProviders函数,还有就是在代码中我们要特别注意下if()语句,因为这个if()语句是得到HAL层的GPS接口GpsInterface,在往下就不多说了,我们还是重点来看看代码吧:
initialize函数
LocationManagerService.java[frameworks\base\services\java\com\android\server]
Java代码:
initialize函数中最重要的就是loadProviders函数了,该函数调用loadProvidersLocked,然后loadProvidersLocked函数又调用_loadProvidersLocked函数。为什么要这么折腾呢?
先来看一部分的_loadProvidersLocked函数:
Java代码:
GpsLocationProvider.cpp
[frameworks\base\location\java\com\android\internal\location]
Java代码:
android_location_GpsLocationProvider.cpp [frameworks\base\core\jni]
Java代码:
gps.cpp [hardware\libhardware_legacy\gps]
Java代码:
然后通过gps_find_hardware函数去得到gps接口,下面只模拟器中的gpsinterface。
Java代码:
Java代码:
Java代码:
这一篇也是接着上一篇的内容继续来讲GPS架构,在底层得到gps的接口之后,
if (GpsLocationProvider.isSupported())(在文件LocationManagerService.java中调用)语句得到true,然后进行下一步操作,在这里new了一个GpsLocationProvider对象。代码如下:
Java代码:
Java代码:
在GpsLocationProvider类里面的成员变量mLocationManager是构造函数的第二个参数,就是说是LocationManagerService对象。这一点在这里先明确。
接着看_loadProvidersLocked函数。
Java代码:
在构造完GpsLocationProvider之后将其add到全局变量ArrayList mProviders中,备以后调用。
在2.2中采取了一种PassiveProvider的类,而在2.1中是通过LocationProviderProxy代理类的方式。2.1中LocationProviderProxy作为GpsLocationProvider的代理作用在LocationManagerService中,而2.2中的PassiveProvider感觉这个类是个空壳。。。。。。。。有待研究。
然后启动了nerwork location和geocoder 两个service。但是可惜的是这两个服务都无法启动,因为他们是通过配置文件conifg.xml[framework\base\core\res\res\values]得到服务的名字,然后启动服务的。但是在这个配置文件中,两个服务的名字都是null。
conifg.xml [framework\base\core\res\res\values]
Java代码:
其实这也导致了,在调用GetFromLocationName和GetFromLocation两个函数时提示“Service not Available”,这个google Android 2.2的bug。
_loadProvidersLocked函数的最后一句是调用updateProvidersLocked函数,仍然在LocationManagerServic.java文件中。
LocationManagerServic.java
Java代码:
从上面_loadProvidersLocked函数的代码来看,在mProviders这个ArrayList中有两个元素(这一点未求证),一个是gpsProvider,另一个是passiveProvider。gpsProvider是GpsLocationProvider类型的,它的isEnabled函数返回的是false,因为它并没有被enable。而passiveProvider是PassiveProvider类型,它总是enable的。所以gpsProvider会调用else语句中的updateProviderListenersLocked(name,true)函数。我们主要分析这个else语句,对于passiveProvider不做分析。
Java代码:
通过调用GpsLocationProvider类的enable和enableLocationTracking函数就把GPS的LocationManager服务启动起来了。下面对这两个函数进行分析。
首先是enable函数。
GpsLocationProvider.java
Java代码:
Java代码:
在handleMessage函数中,定义了各种message对应的处理函数。对于ENABLE消息还带有一个参数,enable函数里面带的参数值为1,所以调用handleEnable函数。
Java代码:
在handleEnable函数中中主要做了3件事,不过有一件事情没有做成。先来看看哪三件事:
1)调用了native的初始化方法对gps进行初始化,
2)试图启动agps服务,
3)并启动一个线程去监听事件。
先来说说它没有做成的第二件事,启动agps服务。其实在GpsLocationProvider类构造的时候就试图去读取agps的配置文件"/etc/gps.conf",该文件里面储存着agps的服务器地址以及端口号,但是服务器地址以及端口号都是错误的,所以它基本上无法启动agps服务,而且对模拟器来说agps基本是个鸡肋。关于agps部分可能在以后的以后会提到。下面看它做成的第一和第三件事。
1)调用native方法native_init,就是JNI层的android_location_GpsLocationProvider_init方法,在文件andoird_location_GpsLocationProvider.cpp中。
Java代码:
在初始化函数中会去确认GpsInterface是否已经得到,如果没有得到那么通过gps_get_interface()方法再次去得到,正如其实前面提到的那样该接口已经在android_location_GpsLocationProvider_is_supported函数中得到了。然后在第二个if语句中调用初始化方法sGpsInterface->init。
android_location_GpsLocationProvider_init的后半部分,试图通过GpsInterface->get_extension方法去得到gps相关的扩展接口,可是在2.2的模拟器实现中并没有实现这个函数,在gps_qume.c中明显写着return NULL。
Java代码:
分析sGpsInterface->init方法。
Java代码:
Java代码:
3)建立线程监听事件
Java代码:
Java代码:
run函数中还是需要调用native函数:JNI:android_location_GpsLocationProvider_wait_for_event函数。这个函数就是在一个while循环里面等待事件的触发(由回调函数触发),然后调用GpsLocationProvider类的数据上报函数(Location数据)。这个在后面还会讲到。
Java代码:
分析完了enable函数以后就轮到enableLocationTracking函数了。
GpsLocationProvider.java
Java代码:
Java代码:
Java代码:
android_location_GpsLocationProvider.cpp
Java代码:
Java代码:
Java代码:
Java代码:
在enableLocationTracking函数调用完成以后,基本上gps服务已经启动完成了,也就是LocationManagerService中的updateProvidersLocked函数的完成,也就是loadProviders函数的完成,也就是initialize函数的完成,也就是run函数的完成,也就是2.2中反馈机制systemReady的完成。
Java代码:
LocationManager 这项服务是在SystemServer.java 中启动的,也就是系统启动之后,这个服务就已经启动了:
systemServer.java [framework\base\services\java\com\android\server]。在SystemServer.java的init2函数中启动了一个线程来注册Android的诸多服务,如:Bluetooth Service,NetworkManagement Service,Notification Manager等,当然也包括Location Service。那么我们来看看代码吧:
Java代码:
- public static final void init2() {
- Slog.i(TAG, "Entered the Android system server!");
- Thread thr = new ServerThread();
- thr.setName("android.server.ServerThread");
- thr.start();
- }
在ServerThread线程的run函数中LocationManager服务的代码段如下:
Java代码:
- try {
- Log.i(TAG, "Location Manager");
- ServiceManager.addService(Context.LOCATION_SERVICE, new LocationManagerService(context));
- } catch (Throwable e) {
- Log.e(TAG, "Failure starting Location Manager", e);
- }
- //2.2的代码中代码段如下形式:
- try {
- Slog.i(TAG, "Location Manager");
- location = new LocationManagerService(context);
- ServiceManager.addService(Context.LOCATION_SERVICE, location);
- } catch (Throwable e) {
- Slog.e(TAG, "Failure starting Location Manager
在run函数的后半部分,是服务对系统的反馈,就是systemReady()函数。LocationManager服务的反馈函数如下:
Java代码:
- if (locationF != null) locationF.systemReady();
Java代码:
- final LocationManagerService locationF = location;
而在2.1版本中LocationManagerService的构造函数如下:
LocationManagerService.java [frameworks\base\services\java\com\android\server]
Java代码:
- public LocationManagerService(Context context) {
- super();
- mContext = context;
- Thread thread = new Thread(null, this, "LocationManagerService");
- thread.start();
- if (LOCAL_LOGV) {
- Log.v(TAG, "Constructed LocationManager Service");
- }
- }
2.2版本
Java代码:
- public LocationManagerService(Context context) {
- super();
- mContext = context;
- if (LOCAL_LOGV) {
- Slog.v(TAG, "Constructed LocationManager Service");
- }
- }
2.1是在构造函数的时候就启动一个自身服务线程。见构造函数。
2.2是在反馈机制中通过systemReady函数启动自身服务线程。如下:
Java代码:
- void systemReady() {
- Thread thread = new Thread(null, this, "LocationManagerService");
- thread.start();
- }
通过线程run函数,调用initialize函数:
Java代码:
- public void run(){
- Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
- Looper.prepare();
- mLocationHandler = new LocationWorkerHandler();
- initialize();
- Looper.loop();
- }
我们这一篇是继续上一篇来解析GPS构架的。我们这一篇主要就是讲initialize函数的,但我们要记住的是initialize函数其中一个是最重要的,那就是loadProviders函数,还有就是在代码中我们要特别注意下if()语句,因为这个if()语句是得到HAL层的GPS接口GpsInterface,在往下就不多说了,我们还是重点来看看代码吧:
initialize函数
LocationManagerService.java[frameworks\base\services\java\com\android\server]
Java代码:
- private void _loadProvidersLocked() {
- if (GpsLocationProvider.isSupported()) {
- GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this);
- mGpsStatusProvider = gpsProvider.getGpsStatusProvider();
- mNetInitiatedListener = gpsProvider.getNetInitiatedListener();
- addProvider(gpsProvider);
- mGpsLocationProvider = gpsProvider;
- }
- private void initialize() {
- PowerManager powerManager = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
- mWakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, WAKELOCK_KEY);
- loadProviders();
initialize函数中最重要的就是loadProviders函数了,该函数调用loadProvidersLocked,然后loadProvidersLocked函数又调用_loadProvidersLocked函数。为什么要这么折腾呢?
先来看一部分的_loadProvidersLocked函数:
Java代码:
- private void _loadProvidersLocked() {
- if (GpsLocationProvider.isSupported()) {
- GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this);
- mGpsStatusProvider = gpsProvider.getGpsStatusProvider();
- mNetInitiatedListener = gpsProvider.getNetInitiatedListener();
- addProvider(gpsProvider);
- mGpsLocationProvider = gpsProvider;
- }
GpsLocationProvider.cpp
[frameworks\base\location\java\com\android\internal\location]
Java代码:
- public static boolean isSupported() {
- return native_is_supported();
- }
android_location_GpsLocationProvider.cpp [frameworks\base\core\jni]
Java代码:
- static jboolean android_location_GpsLocationProvider_is_supported(JNIEnv* env, jclass clazz) {
- if (!sGpsInterface)
- sGpsInterface = gps_get_interface();
- return (sGpsInterface != NULL);
- }
gps.cpp [hardware\libhardware_legacy\gps]
Java代码:
- const GpsInterface*gps_get_interface(){
- if (sGpsInterface == NULL)
- gps_find_hardware();
- return sGpsInterface;
- }
然后通过gps_find_hardware函数去得到gps接口,下面只模拟器中的gpsinterface。
Java代码:
- static void gps_find_hardware( void ){
- #ifdef HAVE_QEMU_GPS_HARDWARE
- if (qemu_check()) {
- sGpsInterface = gps_get_qemu_interface();
- if (sGpsInterface) {
- LOGD("using QEMU GPS Hardware emulation\n");
- return;
- }
- }
- #endif
- #ifdef HAVE_GPS_HARDWARE
- sGpsInterface = gps_get_hardware_interface();
- #endif
- if (!sGpsInterface)
- LOGD("no GPS hardware on this device\n");
- }
Java代码:
- const GpsInterface* gps_get_qemu_interface(){
- return &qemuGpsInterface;
- }
Java代码:
- static const GpsInterface qemuGpsInterface = {
- qemu_gps_init,
- qemu_gps_start,
- qemu_gps_stop,
- qemu_gps_cleanup,
- qemu_gps_inject_time,
- qemu_gps_inject_location,
- qemu_gps_delete_aiding_data,
- qemu_gps_set_position_mode,
- qemu_gps_get_extension,
- };
这一篇也是接着上一篇的内容继续来讲GPS架构,在底层得到gps的接口之后,
if (GpsLocationProvider.isSupported())(在文件LocationManagerService.java中调用)语句得到true,然后进行下一步操作,在这里new了一个GpsLocationProvider对象。代码如下:
Java代码:
- GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this);
Java代码:
- public GpsLocationProvider(Context context, ILocationManager locationManager) {
- mContext = context;
- mLocationManager = locationManager;
- mNIHandler = new GpsNetInitiatedHandler(context, this);
- ...
- }
在GpsLocationProvider类里面的成员变量mLocationManager是构造函数的第二个参数,就是说是LocationManagerService对象。这一点在这里先明确。
接着看_loadProvidersLocked函数。
Java代码:
- private void _loadProvidersLocked() {
- if (GpsLocationProvider.isSupported()) {
- GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this);
- mGpsStatusProvider = gpsProvider.getGpsStatusProvider();
- mNetInitiatedListener = gpsProvider.getNetInitiatedListener();
- addProvider(gpsProvider);
- mGpsLocationProvider = gpsProvider;
- }
- PassiveProvider passiveProvider = new PassiveProvider(this);
- addProvider(passiveProvider);
- mEnabledProviders.add(passiveProvider.getName());
- Resources resources = mContext.getResources();
- String serviceName = resources.getString(
- com.android.internal.R.string.config_networkLocationProvider);
- if (serviceName != null) {
- mNetworkLocationProvider =new LocationProviderProxy(mContext, LocationManager.NETWORK_PROVIDER,serviceName, mLocationHandler);
- addProvider(mNetworkLocationProvider);
- }
- serviceName = resources.getString(com.android.internal.R.string.config_geocodeProvider);
- if (serviceName != null) {
- mGeocodeProvider = new GeocoderProxy(mContext, serviceName);
- }
- updateProvidersLocked();
- }
在构造完GpsLocationProvider之后将其add到全局变量ArrayList
在2.2中采取了一种PassiveProvider的类,而在2.1中是通过LocationProviderProxy代理类的方式。2.1中LocationProviderProxy作为GpsLocationProvider的代理作用在LocationManagerService中,而2.2中的PassiveProvider感觉这个类是个空壳。。。。。。。。有待研究。
然后启动了nerwork location和geocoder 两个service。但是可惜的是这两个服务都无法启动,因为他们是通过配置文件conifg.xml[framework\base\core\res\res\values]得到服务的名字,然后启动服务的。但是在这个配置文件中,两个服务的名字都是null。
conifg.xml [framework\base\core\res\res\values]
Java代码:
@null
@null
其实这也导致了,在调用GetFromLocationName和GetFromLocation两个函数时提示“Service not Available”,这个google Android 2.2的bug。
_loadProvidersLocked函数的最后一句是调用updateProvidersLocked函数,仍然在LocationManagerServic.java文件中。
LocationManagerServic.java
Java代码:
- private void updateProvidersLocked() {
- for (int i = mProviders.size() - 1; i >= 0; i--) {
- LocationProviderInterface p = mProviders.get(i);
- boolean isEnabled = p.isEnabled();
- String name = p.getName();
- boolean shouldBeEnabled = isAllowedBySettingsLocked(name);
- if (isEnabled && !shouldBeEnabled) {
- updateProviderListenersLocked(name, false);
- } else if (!isEnabled && shouldBeEnabled) {
- updateProviderListenersLocked(name, true);
- }
- }
- }
从上面_loadProvidersLocked函数的代码来看,在mProviders这个ArrayList中有两个元素(这一点未求证),一个是gpsProvider,另一个是passiveProvider。gpsProvider是GpsLocationProvider类型的,它的isEnabled函数返回的是false,因为它并没有被enable。而passiveProvider是PassiveProvider类型,它总是enable的。所以gpsProvider会调用else语句中的updateProviderListenersLocked(name,true)函数。我们主要分析这个else语句,对于passiveProvider不做分析。
Java代码:
- private void updateProviderListenersLocked(String provider, boolean enabled) {
- int listeners = 0;
- LocationProviderInterface p = mProvidersByName.get(provider);
- if (p == null) {
- return;
- }
- ArrayList
deadReceivers = null;
- ArrayList
records = mRecordsByProvider.get(provider);
- if (records != null) {
- final int N = records.size();
- for (int i=0; i
- UpdateRecord record = records.get(i);
- if (!record.mReceiver.callProviderEnabledLocked(provider, enabled)) {
- if (deadReceivers == null) {
- deadReceivers = new ArrayList
();
- }
- deadReceivers.add(record.mReceiver);
- }
- listeners++;
- }
- }
- if (deadReceivers != null) {
- for (int i=deadReceivers.size()-1; i>=0; i--) {
- removeUpdatesLocked(deadReceivers.get(i));
- }
- }
- if (enabled) { //enabled 的值是true
- p.enable();
- if (listeners > 0) {
- p.setMinTime(getMinTimeLocked(provider));
- p.enableLocationTracking(true);
- }
- } else {
- p.enableLocationTracking(false);
- p.disable();
- }
- }
- ArrayList
通过调用GpsLocationProvider类的enable和enableLocationTracking函数就把GPS的LocationManager服务启动起来了。下面对这两个函数进行分析。
首先是enable函数。
GpsLocationProvider.java
Java代码:
- public void enable() {
- synchronized (mHandler) {
- mHandler.removeMessages(ENABLE);
- Message m = Message.obtain(mHandler, ENABLE);
- m.arg1 = 1;
- mHandler.sendMessage(m);
- }
- }
Java代码:
- public void handleMessage(Message msg){
- switch (msg.what) {
- case ENABLE:
- if (msg.arg1 == 1) {
- handleEnable();
- } else {
- handleDisable();
- }
- break;
- case ENABLE_TRACKING:
- handleEnableLocationTracking(msg.arg1 == 1);
- break;
- }
在handleMessage函数中,定义了各种message对应的处理函数。对于ENABLE消息还带有一个参数,enable函数里面带的参数值为1,所以调用handleEnable函数。
Java代码:
- private void handleEnable() {
- if (DEBUG) Log.d(TAG, "handleEnable");
- if (mEnabled) return;
- mEnabled = native_init();
- if (mEnabled) {
- if (mSuplServerHost != null) {
- native_set_agps_server(AGPS_TYPE_SUPL, mSuplServerHost, mSuplServerPort);
- }
- if (mC2KServerHost != null) {
- native_set_agps_server(AGPS_TYPE_C2K, mC2KServerHost, mC2KServerPort);
- }
- mEventThread = new GpsEventThread();
- mEventThread.start();
- } else {
- Log.w(TAG, "Failed to enable location provider");
- }
- }
在handleEnable函数中中主要做了3件事,不过有一件事情没有做成。先来看看哪三件事:
1)调用了native的初始化方法对gps进行初始化,
2)试图启动agps服务,
3)并启动一个线程去监听事件。
先来说说它没有做成的第二件事,启动agps服务。其实在GpsLocationProvider类构造的时候就试图去读取agps的配置文件"/etc/gps.conf",该文件里面储存着agps的服务器地址以及端口号,但是服务器地址以及端口号都是错误的,所以它基本上无法启动agps服务,而且对模拟器来说agps基本是个鸡肋。关于agps部分可能在以后的以后会提到。下面看它做成的第一和第三件事。
1)调用native方法native_init,就是JNI层的android_location_GpsLocationProvider_init方法,在文件andoird_location_GpsLocationProvider.cpp中。
Java代码:
- static jboolean android_location_GpsLocationProvider_init(JNIEnv* env, jobject obj){
- if (!sGpsInterface)
- sGpsInterface = gps_get_interface();
- if (!sGpsInterface || sGpsInterface->init(&sGpsCallbacks) != 0)
- return false;
- return true;
- }
在初始化函数中会去确认GpsInterface是否已经得到,如果没有得到那么通过gps_get_interface()方法再次去得到,正如其实前面提到的那样该接口已经在android_location_GpsLocationProvider_is_supported函数中得到了。然后在第二个if语句中调用初始化方法sGpsInterface->init。
android_location_GpsLocationProvider_init的后半部分,试图通过GpsInterface->get_extension方法去得到gps相关的扩展接口,可是在2.2的模拟器实现中并没有实现这个函数,在gps_qume.c中明显写着return NULL。
Java代码:
- static const void*qemu_gps_get_extension(const char* name){
- return NULL;
- }
分析sGpsInterface->init方法。
Java代码:
- static int qemu_gps_init(GpsCallbacks* callbacks){
- GpsState* s = _gps_state;
- if (!s->init)
- gps_state_init(s);
- if (s->fd < 0)
- return -1;
- s->callbacks = *callbacks;
- return 0;
- }
Java代码:
- static void gps_state_init( GpsState* state ){
- state->init = 1;
- state->control[0] = -1;
- state->control[1] = -1;
- state->fd = -1;
- state->fd = qemu_channel_open( &state->channel,QEMU_CHANNEL_NAME,O_RDONLY );
- if (state->fd < 0) {
- D("no gps emulation detected");
- return;
- }
- D("gps emulation will read from '%s' qemud channel", QEMU_CHANNEL_NAME );
- if ( socketpair( AF_LOCAL, SOCK_STREAM, 0, state->control ) < 0 ) {
- LOGE("could not create thread control socket pair: %s", strerror(errno));
- goto Fail;
- }
- if ( pthread_create( &state->thread, NULL, gps_state_thread, state ) != 0 ) {
- LOGE("could not create gps thread: %s", strerror(errno));
- goto Fail;
- }
- D("gps state initialized");
- return;
- Fail:gps_state_done( state );
- }
3)建立线程监听事件
Java代码:
- mEventThread = new GpsEventThread();
- mEventThread.start();
Java代码:
- public void run() {
- if (DEBUG) Log.d(TAG, "GpsEventThread starting");
- while (mEnabled) {
- native_wait_for_event();
- }
- if (DEBUG) Log.d(TAG, "GpsEventThread exiting");
- }
- }
run函数中还是需要调用native函数:JNI:android_location_GpsLocationProvider_wait_for_event函数。这个函数就是在一个while循环里面等待事件的触发(由回调函数触发),然后调用GpsLocationProvider类的数据上报函数(Location数据)。这个在后面还会讲到。
Java代码:
- static void android_location_GpsLocationProvider_wait_for_event(JNIEnv* env, jobject obj){
- pthread_mutex_lock(&sEventMutex);
- while (sPendingCallbacks == 0) {
- pthread_cond_wait(&sEventCond, &sEventMutex);
- }
- ...
- }
分析完了enable函数以后就轮到enableLocationTracking函数了。
GpsLocationProvider.java
Java代码:
- public void enableLocationTracking(boolean enable) {
- synchronized (mHandler) {
- mHandler.removeMessages(ENABLE_TRACKING);
- Message m = Message.obtain(mHandler, ENABLE_TRACKING);
- m.arg1 = (enable ? 1 : 0);
- mHandler.sendMessage(m);
- }
- }
Java代码:
- private void handleEnableLocationTracking(boolean enable) {
- if (enable) {
- mTTFF = 0;
- mLastFixTime = 0;
- startNavigating();
- } else {
- mAlarmManager.cancel(mWakeupIntent);
- mAlarmManager.cancel(mTimeoutIntent);
- stopNavigating();
- }
- }
Java代码:
- private void startNavigating() {
- if (!mStarted) {
- if (DEBUG) Log.d(TAG, "startNavigating");
- mStarted = true;
- int positionMode;
- if (Settings.Secure.getInt(mContext.getContentResolver(),
- Settings.Secure.ASSISTED_GPS_ENABLED, 1) != 0) {
- positionMode = GPS_POSITION_MODE_MS_BASED;
- } else {
- positionMode = GPS_POSITION_MODE_STANDALONE;
- }
- if (!native_start(positionMode, false, 1)) {
- mStarted = false;
- Log.e(TAG, "native_start failed in startNavigating()");
- return;
- }
android_location_GpsLocationProvider.cpp
Java代码:
- static jboolean android_location_GpsLocationProvider_start(JNIEnv* env, jobject obj, jint positionMode,jboolean singleFix, jint fixFrequency){
- int result = sGpsInterface->set_position_mode(positionMode, (singleFix ? 0 : fixFrequency));
- if (result) {
- return false;
- }
- return (sGpsInterface->start() == 0);
- }
Java代码:
- static int qemu_gps_start(){
- GpsState* s = _gps_state;
- if (!s->init) {
- D("%s: called with uninitialized state !!", __FUNCTION__);
- return -1;
- }
- D("%s: called", __FUNCTION__);
- gps_state_start(s);
- return 0;
- }
Java代码:
- static void gps_state_start( GpsState* s ){
- char cmd = CMD_START;
- int ret;
- do { ret=write( s->control[0], &cmd, 1 ); }
- while (ret < 0 && errno == EINTR);
- if (ret != 1)
- D("%s: could not send CMD_START command: ret=%d: %s",__FUNCTION__, ret, strerror(errno));
- }
Java代码:
- static void*gps_state_thread( void* arg ){
- for (;;) {
- if (cmd == CMD_QUIT) {
- D("gps thread quitting on demand");
- goto Exit;
- }else
- if (cmd == CMD_START) {
- if (!started) {
- D("gps thread starting location_cb=%p", state>callbacks.location_cb);
- started = 1;
- nmea_reader_set_callback( reader, state->callbacks.location_cb );
- }
- }
- else if (cmd == CMD_STOP) {
- }
在enableLocationTracking函数调用完成以后,基本上gps服务已经启动完成了,也就是LocationManagerService中的updateProvidersLocked函数的完成,也就是loadProviders函数的完成,也就是initialize函数的完成,也就是run函数的完成,也就是2.2中反馈机制systemReady的完成。
Java代码:
- void systemReady() {
- Thread thread = new Thread(null, this, "LocationManagerService");
- thread.start();
- }