本文轉載自:http://blog.csdn.net/junzhang1122/article/details/46674569
1 GPS HAL層代碼在目錄trunk/Android/hardware/xxx/gps/skytraqskytraq_gsp.c,向下與硬件驅動通訊,向上提供接口 2 GPS JNI層層代碼在目錄trunk/Android/frameworks/base/services/jni/com_android_server_location_GpsLocationProvider.cpp C與java轉換,給java層提供接口 3 GPS framework層代碼目錄Android/frameworks/base/services/java/com/android/server下,主要文件是location服務對內部的封裝並提供provider服務 4 Android/frameworks/base/location/java/com/android/internal/location這個是framework對location服務內部的實現 5 6 啟動GPS服務代碼流程如下 7 public static void main(String[] args) 8 -->ServerThread thr = new ServerThread(); 9 -->location = new LocationManagerService(context); 10 -->ServiceManager.addService(Context.LOCATION_SERVICE, location); 11 -->locationF.systemRunning() 12 -->systemRunning() 13 -->loadProvidersLocked(); 14 -->GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this, mLocationHandler.getLooper()); 15 -->class_init_native(); 16 -->android_location_GpsLocationProvider_class_init_native(JNIEnv* env, jclass clazz) 17 -->err = module->methods->open(module, GPS_HARDWARE_MODULE_ID, &device); 18 -->pen_gps(const struct hw_module_t *module, char const *name, struct hw_device_t **device) 19 -->sGpsInterface = gps_device->get_gps_interface(gps_device); 20 -->const GpsInterface *gps__get_gps_interface(struct gps_device_t *dev) 21 -->return &skytraqGpsInterface; 22 -->GpsLocationProvider.isSupported() 23 -->native_is_supported() 24 -->android_location_GpsLocationProvider_is_supported(JNIEnv* env, jclass clazz) 25 -->return (sGpsInterface != NULL); 26 -->updateProvidersLocked 27 --> updateProviderListenersLocked 28 --> applyRequirementsLocked(provider); 29 --> p.setRequest(providerRequest, worksource); 30 --> public void setRequest(ProviderRequest request, WorkSource source) 31 --> sendMessage(SET_REQUEST, 0, new GpsRequest(request, source)); 32 -->public void handleMessage(Message msg) 33 -->handleSetRequest(gpsRequest.request, gpsRequest.source); 34 -->startNavigating(singleShot); 35 -->native_set_position_mode(mPositionMode, GPS_POSITION_RECURRENCE_PERIODIC,interval, 0, 0) 36 -->native_start() 37 38 Android系統運行的第一個進程就是init進程,在該進程中創建的第一個虛擬機就是zygote,zygote孵化的第一個虛擬機就是Dalvik,該進程就是SystemServer, 39 對於的SystemServer代碼是framework\base\services\java\com\android\server\SystemServer.java 40 該SystemServer對於的第一個運行函數就是main 41 42 public static void main(String[] args) //SystemServer運行的第一個函數 43 ServerThread thr = new ServerThread(); //初始化一個server線程 44 class ServerThread 45 { 46 public void initAndLoop() 47 { 48 if (!disableLocation) //開始的時候這里的 disableLocation = false 49 { 50 try{ 51 Slog.i(TAG, "Location Manager"); 52 <1> location = new LocationManagerService(context); //實例化一個LocationManagerService服務,該服務主要用來管理GPS地理位置的變化 53 ServiceManager.addService(Context.LOCATION_SERVICE, location); //將這個service添加到SystemManager中 54 } 55 catch (Throwable e) 56 { 57 reportWtf("starting Location Manager", e); 58 } 59 60 try { 61 Slog.i(TAG, "Country Detector"); 62 countryDetector = new CountryDetectorService(context);//實例化一個CountryDetectorService服務,用來探測不同國家,也就是不同地區和時區 63 ServiceManager.addService(Context.COUNTRY_DETECTOR, countryDetector); 64 } catch (Throwable e) { 65 reportWtf("starting Country Detector", e); 66 } 67 } 68 69 ActivityManagerService.self().systemReady(new Runnable() 70 { 71 public void run() 72 { 73 try 74 { 75 <2> if (locationF != null) locationF.systemRunning();//在<1>的位置已給locationF賦值,在這里調用LocationManagerService的systemRunning()函數 76 } 77 catch(Throwable e) 78 { 79 reportWtf("Notifying Location Service running", e); 80 } 81 } 82 } 83 84 } 85 } 86 87 接下來分析LocationManagerService(context) 88 /**framework\base\services\java\com\android\server\LocationManagerService.java**/ 89 public class LocationManagerService extends ILocationManager.Stub 90 { 91 public void systemRunning() //該函數有<2>處調用 92 { 93 synchronized (mLock) 94 { 95 /*GPS啟動到運行及監聽都在這兩個函數里*/ 96 <3> loadProvidersLocked(); //在這里加載各種provider 97 <4> updateProvidersLocked(); //加載后更新 98 } 99 } 100 } 101 102 /**framework\base\services\java\com\android\server\LocationManagerService.java**/ 103 private void loadProvidersLocked() 104 { 105 // create a passive location provider, which is always enabled 106 PassiveProvider passiveProvider = new PassiveProvider(this); 107 addProviderLocked(passiveProvider); 108 mEnabledProviders.add(passiveProvider.getName()); 109 mPassiveProvider = passiveProvider; 110 // Create a gps location provider 111 <5> GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this, 112 mLocationHandler.getLooper()); 113 114 <6> if (GpsLocationProvider.isSupported()) //這里調用JNI的函數接口 115 { 116 mGpsStatusProvider = gpsProvider.getGpsStatusProvider(); //獲取gps狀態provider 117 mNetInitiatedListener = gpsProvider.getNetInitiatedListener(); //初始網絡監聽 118 addProviderLocked(gpsProvider); //將gpsProvider添加到mProviders中 119 mRealProviders.put(LocationManager.GPS_PROVIDER, gpsProvider); 120 } 121 } 122 123 /**分析 <5> ***/ 124 public class GpsLocationProvider implements LocationProviderInterface 125 { 126 static { class_init_native(); } //在這里調用JNI的android_location_GpsLocationProvider_class_init_native函數 127 } 128 129 static void android_location_GpsLocationProvider_class_init_native(JNIEnv* env, jclass clazz) 130 { 131 err = module->methods->open(module, GPS_HARDWARE_MODULE_ID, &device);//打開GPS設備文件,對應trunk/Android/hardware/xxx/gps/skytraq/skytraq_gps.c 132 -->static int open_gps(const struct hw_module_t *module, char const *name, struct hw_device_t **device) 133 134 //獲取gpsInterface接口,該函數接口在trunk/Android/hardware/xxx/gps/skytraq/skytraq_gps.c中,對應的函數是gps__get_gps_interface 135 sGpsInterface = gps_device->get_gps_interface(gps_device); 136 } 137 138 const GpsInterface *gps__get_gps_interface(struct gps_device_t *dev) 139 { 140 return &skytraqGpsInterface; 141 } 142 143 /**分析 <6> **/ 144 public static boolean GpsLocationProvider.isSupported() 145 { 146 return native_is_supported(); //該函數對應JNI的函數如下 147 } 148 149 static jboolean android_location_GpsLocationProvider_is_supported(JNIEnv* env, jclass clazz) 150 { 151 return (sGpsInterface != NULL); 152 } 153 GpsLocationProvider.isSupported()返回true,所以會走if{}里面的。在網上查閱資料,都是基於2.3的系統,2.3的系統里是直接在isSupported()函數里來獲取接口,沒有在GpsLocationProvider類中實現調用class_init_native()來獲取接口 154 155 /**分析 <4> **/ 156 /**framework\base\services\java\com\android\server\LocationManagerService.java**/ 157 private void updateProvidersLocked() 158 { 159 for (int i = mProviders.size() - 1; i >= 0; i--) 160 { 161 boolean isEnabled = p.isEnabled(); //開始的時候返回false 162 boolean shouldBeEnabled = isAllowedByCurrentUserSettingsLocked(name); //在loadProvidersLocked()函數就說了,一直是enabled 163 所以會走else 164 else if (!isEnabled && shouldBeEnabled) 165 { 166 <7> updateProviderListenersLocked(name, true, mCurrentUserId); 167 changesMade = true; 168 } 169 } 170 /*發送廣播,app和framework都可以接受該廣播*/ 171 if (changesMade) { 172 mContext.sendBroadcastAsUser(new Intent(LocationManager.PROVIDERS_CHANGED_ACTION), 173 UserHandle.ALL); 174 mContext.sendBroadcastAsUser(new Intent(LocationManager.MODE_CHANGED_ACTION), 175 UserHandle.ALL); 176 } 177 } 178 179 /**分析 <7> framework\base\services\java\com\android\server\locationManagerService.java **/ 180 private void updateProviderListenersLocked(String provider, boolean enabled, int userId) 181 { 182 if (records != null) 183 { 184 //這里主要是從UserHandle里解析UserId 是否等於 mCurrentUserId,如果是則發送notification給receiver 185 } 186 if (enabled) //這里的 enabled == true 187 { 188 <8> p.enable(); 189 if (listeners > 0) 190 { 191 <9> applyRequirementsLocked(provider); 192 } 193 } 194 else 195 { 196 p.disable(); 197 } 198 199 } 200 201 /**分析 <8> framework\base\services\java\com\android\server\location\gpsLocationProvider.java**/ 202 public void enable() 203 { 204 synchronized (mLock) 205 { 206 if (mEnabled) return;//開始的時候這里是false 207 mEnabled = true; 208 } 209 <10> sendMessage(ENABLE, 1, null);//發送消息 210 } 211 /**分析 <10> base\services\java\com\android\server\location\gpsLocationProvider.java**/ 212 private void sendMessage(int message, int arg, Object obj) 213 { 214 // hold a wake lock until this message is delivered 215 // note that this assumes the message will not be removed from the queue before 216 // it is handled (otherwise the wake lock would be leaked). 217 mWakeLock.acquire(); 218 <11> mHandler.obtainMessage(message, arg, 1, obj).sendToTarget(); //通過handler機制來發送消息 219 } 220 221 /**分析 <11> base\services\java\com\android\server\location\gpsLocationProvider.java**/ 222 private final class ProviderHandler extends Handler 223 { 224 public void handleMessage(Message msg) 225 { 226 switch (message) 227 { 228 case ENABLE: //有<10>可知,message == ENABLE , msg.arg1 == 1 229 if (msg.arg1 == 1) { 230 <12> handleEnable(); //所以會調用這個函數 231 } else { 232 handleDisable(); 233 } 234 break; 235 ..... 236 } 237 } 238 } 239 240 /**分析 <12> framework\base\services\java\com\android\server\location\gpsLocationProvider.java**/ 241 private void handleEnable() 242 { 243 <13> boolean enabled = native_init(); //調用JNI中的 static jboolean android_location_GpsLocationProvider_init(JNIEnv* env, jobject obj) 244 if (enabled) 245 { 246 mSupportsXtra = native_supports_xtra(); //native_supports_xtra()直接返回true,在class_init_native()已經賦值 247 248 if (mSuplServerHost != null) 249 { 250 /*這里沒做任何事,因為sAGpsInterface為空,代碼流程如下*/ 251 native_set_agps_server(AGPS_TYPE_SUPL, mSuplServerHost, mSuplServerPort); 252 -->static void android_location_GpsLocationProvider_set_agps_server(JNIEnv* env, jobject obj, jint type, jstring hostname, jint port) 253 -->if (!sAGpsInterface) return; 254 -->sAGpsInterface = (const AGpsInterface*)sGpsInterface->get_extension(AGPS_INTERFACE); 255 -->static const void *skytraq_gps_get_extension(const char* name) 256 { 257 ALOGD("%s: called", __FUNCTION__); 258 return NULL; 259 } 260 261 } 262 if (mC2KServerHost != null) { //同理這里也直接返回了 263 native_set_agps_server(AGPS_TYPE_C2K, mC2KServerHost, mC2KServerPort); 264 } 265 }else{ 266 synchronized (mLock) { 267 mEnabled = false; 268 } 269 Log.w(TAG, "Failed to enable location provider"); 270 } 271 272 } 273 274 /**分析 <13> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp **/ 275 static jboolean android_location_GpsLocationProvider_init(JNIEnv* env, jobject obj) 276 { 277 <14> if (!sGpsInterface || sGpsInterface->init(&sGpsCallbacks) != 0)//sGpsInterface不為null,在一開始的就已賦值,所以會調用init函數 278 return false; 279 ..... 280 } 281 282 /**分析 <14> hardware\xxx\gps\skytraq\Skytraq_gps.c **/ 283 static int skytraq_gps_init(GpsCallbacks* callbacks) //callbacks回調函數時有JNI傳下來的,在JNI中實現的 284 { 285 GpsState* s = &_gps_state; //該結構圖數組初始化的時候都為0 286 if (!s->init) 287 <15> gps_state_init(s, callbacks); 288 } 289 290 /**分析 <15> hardware\xxx\gps\skytraq\Skytraq_gps.c **/ 291 static void gps_state_init( GpsState* state, GpsCallbacks* callbacks ) 292 { 293 state->fd = gps_channel_open(GPS_CHANNEL_NAME); 294 --> fd = open("/dev/skytraq_gps_ipc", O_RDWR | O_SYNC); //打開串口 295 int ret = ioctl(state->fd, GPS_IPC_SET, &gps_connect_info); //調用驅動函數ioctl設置gps 296 state->thread = callbacks->create_thread_cb( "gps_state_thread", gps_state_thread, state );//創建線程,用來監聽發送的命令和監聽數據上報, 297 } 298 299 300 /**分析<9> frwmework\base\services\java\com\android\server\LocationManagerService.java 301 private void applyRequirementsLocked(String provider) 302 { 303 //設置worksource和providerRequest 304 ..... 305 <16> p.setRequest(providerRequest, worksource); //location provider 發送請求 306 } 307 308 309 /**分析<16> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/ 310 public void setRequest(ProviderRequest request, WorkSource source) 311 { 312 <17> sendMessage(SET_REQUEST, 0, new GpsRequest(request, source)); //發送消息,SET_REQUEST == 3 313 } 314 315 /**分析<17> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/ 316 public void handleMessage(Message msg) 317 { 318 ... 319 case SET_REQUEST: 320 GpsRequest gpsRequest = (GpsRequest) msg.obj; 321 <18> handleSetRequest(gpsRequest.request, gpsRequest.source); 322 break; 323 } 324 325 /**分析<18> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/ 326 private void handleSetRequest(ProviderRequest request, WorkSource source) 327 { 328 ... 329 <19> startNavigating(singleShot);//開始導航 330 } 331 332 /**分析<19> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/ 333 private void startNavigating(boolean singleShot) 334 { 335 <20> native_set_position_mode(mPositionMode, GPS_POSITION_RECURRENCE_PERIODIC, interval, 0, 0)//該函數在HAL層直接返回了,沒做任何事 336 <21> native_start() 337 } 338 339 /**分析<20> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp**/ 340 static jboolean android_location_GpsLocationProvider_set_position_mode(JNIEnv* env, jobject obj, 341 jint mode, jint recurrence, jint min_interval, jint preferred_accuracy, jint preferred_time) 342 { 343 if (sGpsInterface) 344 <22> return (sGpsInterface->set_position_mode(mode, recurrence, min_interval, preferred_accuracy, 345 preferred_time) == 0); //調用HAL層接口 346 } 347 348 /**分析<22> xxx\gps\skytraq\skytraq.gps.c**/ 349 static int skytraq_gps_set_position_mode(GpsPositionMode mode, 350 GpsPositionRecurrence recurrence, 351 uint32_t min_interval, 352 uint32_t preferred_accuracy, 353 uint32_t preferred_time) 354 { 355 ALOGD("%s: called", __FUNCTION__); 356 return 0; 357 } 358 /**分析<21> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp**/ 359 static jboolean android_location_GpsLocationProvider_start(JNIEnv* env, jobject obj) 360 { 361 if (sGpsInterface) 362 <23> return (sGpsInterface->start() == 0); //調用HAL 層的static int skytraq_gps_start() 363 } 364 365 /**分析<23> xxx\gps\skytraq\skytraq.gps.c**/ 366 static int skytraq_gps_start() 367 { 368 gps_state_start(s); 369 -->s->status = CMD_START; 370 /*在<15>線程函數gps_state_thread()中while(1)中等該命令,進入獲取數據*/ 371 } 372 此時GPS就已運行
- GPS HAL層代碼在目錄trunk/Android/hardware/xxx/gps/skytraqskytraq_gsp.c,向下與硬件驅動通訊,向上提供接口
- GPS JNI層層代碼在目錄trunk/Android/frameworks/base/services/jni/com_android_server_location_GpsLocationProvider.cpp C與java轉換,給java層提供接口
- GPS framework層代碼目錄Android/frameworks/base/services/java/com/android/server下,主要文件是location服務對內部的封裝並提供provider服務
- Android/frameworks/base/location/java/com/android/internal/location這個是framework對location服務內部的實現
- 啟動GPS服務代碼流程如下
- public static void main(String[] args)
- -->ServerThread thr = new ServerThread();
- -->location = new LocationManagerService(context);
- -->ServiceManager.addService(Context.LOCATION_SERVICE, location);
- -->locationF.systemRunning()
- -->systemRunning()
- -->loadProvidersLocked();
- -->GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this, mLocationHandler.getLooper());
- -->class_init_native();
- -->android_location_GpsLocationProvider_class_init_native(JNIEnv* env, jclass clazz)
- -->err = module->methods->open(module, GPS_HARDWARE_MODULE_ID, &device);
- -->pen_gps(const struct hw_module_t *module, char const *name, struct hw_device_t **device)
- -->sGpsInterface = gps_device->get_gps_interface(gps_device);
- -->const GpsInterface *gps__get_gps_interface(struct gps_device_t *dev)
- -->return &skytraqGpsInterface;
- -->GpsLocationProvider.isSupported()
- -->native_is_supported()
- -->android_location_GpsLocationProvider_is_supported(JNIEnv* env, jclass clazz)
- -->return (sGpsInterface != NULL);
- -->updateProvidersLocked
- --> updateProviderListenersLocked
- --> applyRequirementsLocked(provider);
- --> p.setRequest(providerRequest, worksource);
- --> public void setRequest(ProviderRequest request, WorkSource source)
- --> sendMessage(SET_REQUEST, 0, new GpsRequest(request, source));
- -->public void handleMessage(Message msg)
- -->handleSetRequest(gpsRequest.request, gpsRequest.source);
- -->startNavigating(singleShot);
- -->native_set_position_mode(mPositionMode, GPS_POSITION_RECURRENCE_PERIODIC,interval, 0, 0)
- -->native_start()
- Android系統運行的第一個進程就是init進程,在該進程中創建的第一個虛擬機就是zygote,zygote孵化的第一個虛擬機就是Dalvik,該進程就是SystemServer,
- 對於的SystemServer代碼是framework\base\services\java\com\android\server\SystemServer.java
- 該SystemServer對於的第一個運行函數就是main
- public static void main(String[] args) //SystemServer運行的第一個函數
- ServerThread thr = new ServerThread(); //初始化一個server線程
- class ServerThread
- {
- public void initAndLoop()
- {
- if (!disableLocation) //開始的時候這里的 disableLocation = false
- {
- try{
- Slog.i(TAG, "Location Manager");
- <1> location = new LocationManagerService(context); //實例化一個LocationManagerService服務,該服務主要用來管理GPS地理位置的變化
- ServiceManager.addService(Context.LOCATION_SERVICE, location); //將這個service添加到SystemManager中
- }
- catch (Throwable e)
- {
- reportWtf("starting Location Manager", e);
- }
- try {
- Slog.i(TAG, "Country Detector");
- countryDetector = new CountryDetectorService(context);//實例化一個CountryDetectorService服務,用來探測不同國家,也就是不同地區和時區
- ServiceManager.addService(Context.COUNTRY_DETECTOR, countryDetector);
- } catch (Throwable e) {
- reportWtf("starting Country Detector", e);
- }
- }
- ActivityManagerService.self().systemReady(new Runnable()
- {
- public void run()
- {
- try
- {
- <2> if (locationF != null) locationF.systemRunning();//在<1>的位置已給locationF賦值,在這里調用LocationManagerService的systemRunning()函數
- }
- catch(Throwable e)
- {
- reportWtf("Notifying Location Service running", e);
- }
- }
- }
- }
- }
- 接下來分析LocationManagerService(context)
- /**framework\base\services\java\com\android\server\LocationManagerService.java**/
- public class LocationManagerService extends ILocationManager.Stub
- {
- public void systemRunning() //該函數有<2>處調用
- {
- synchronized (mLock)
- {
- /*GPS啟動到運行及監聽都在這兩個函數里*/
- <3> loadProvidersLocked(); //在這里加載各種provider
- <4> updateProvidersLocked(); //加載后更新
- }
- }
- }
- /**framework\base\services\java\com\android\server\LocationManagerService.java**/
- private void loadProvidersLocked()
- {
- // create a passive location provider, which is always enabled
- PassiveProvider passiveProvider = new PassiveProvider(this);
- addProviderLocked(passiveProvider);
- mEnabledProviders.add(passiveProvider.getName());
- mPassiveProvider = passiveProvider;
- // Create a gps location provider
- <5> GpsLocationProvider gpsProvider = new GpsLocationProvider(mContext, this,
- mLocationHandler.getLooper());
- <6> if (GpsLocationProvider.isSupported()) //這里調用JNI的函數接口
- {
- mGpsStatusProvider = gpsProvider.getGpsStatusProvider(); //獲取gps狀態provider
- mNetInitiatedListener = gpsProvider.getNetInitiatedListener(); //初始網絡監聽
- addProviderLocked(gpsProvider); //將gpsProvider添加到mProviders中
- mRealProviders.put(LocationManager.GPS_PROVIDER, gpsProvider);
- }
- }
- /**分析 <5> ***/
- public class GpsLocationProvider implements LocationProviderInterface
- {
- static { class_init_native(); } //在這里調用JNI的android_location_GpsLocationProvider_class_init_native函數
- }
- static void android_location_GpsLocationProvider_class_init_native(JNIEnv* env, jclass clazz)
- {
- err = module->methods->open(module, GPS_HARDWARE_MODULE_ID, &device);//打開GPS設備文件,對應trunk/Android/hardware/xxx/gps/skytraq/skytraq_gps.c
- -->static int open_gps(const struct hw_module_t *module, char const *name, struct hw_device_t **device)
- //獲取gpsInterface接口,該函數接口在trunk/Android/hardware/xxx/gps/skytraq/skytraq_gps.c中,對應的函數是gps__get_gps_interface
- sGpsInterface = gps_device->get_gps_interface(gps_device);
- }
- const GpsInterface *gps__get_gps_interface(struct gps_device_t *dev)
- {
- return &skytraqGpsInterface;
- }
- /**分析 <6> **/
- public static boolean GpsLocationProvider.isSupported()
- {
- return native_is_supported(); //該函數對應JNI的函數如下
- }
- static jboolean android_location_GpsLocationProvider_is_supported(JNIEnv* env, jclass clazz)
- {
- return (sGpsInterface != NULL);
- }
- GpsLocationProvider.isSupported()返回true,所以會走if{}里面的。在網上查閱資料,都是基於2.3的系統,2.3的系統里是直接在isSupported()函數里來獲取接口,沒有在GpsLocationProvider類中實現調用class_init_native()來獲取接口
- /**分析 <4> **/
- /**framework\base\services\java\com\android\server\LocationManagerService.java**/
- private void updateProvidersLocked()
- {
- for (int i = mProviders.size() - 1; i >= 0; i--)
- {
- boolean isEnabled = p.isEnabled(); //開始的時候返回false
- boolean shouldBeEnabled = isAllowedByCurrentUserSettingsLocked(name); //在loadProvidersLocked()函數就說了,一直是enabled
- 所以會走else
- else if (!isEnabled && shouldBeEnabled)
- {
- <7> updateProviderListenersLocked(name, true, mCurrentUserId);
- changesMade = true;
- }
- }
- /*發送廣播,app和framework都可以接受該廣播*/
- if (changesMade) {
- mContext.sendBroadcastAsUser(new Intent(LocationManager.PROVIDERS_CHANGED_ACTION),
- UserHandle.ALL);
- mContext.sendBroadcastAsUser(new Intent(LocationManager.MODE_CHANGED_ACTION),
- UserHandle.ALL);
- }
- }
- /**分析 <7> framework\base\services\java\com\android\server\locationManagerService.java **/
- private void updateProviderListenersLocked(String provider, boolean enabled, int userId)
- {
- if (records != null)
- {
- //這里主要是從UserHandle里解析UserId 是否等於 mCurrentUserId,如果是則發送notification給receiver
- }
- if (enabled) //這里的 enabled == true
- {
- <8> p.enable();
- if (listeners > 0)
- {
- <9> applyRequirementsLocked(provider);
- }
- }
- else
- {
- p.disable();
- }
- }
- /**分析 <8> framework\base\services\java\com\android\server\location\gpsLocationProvider.java**/
- public void enable()
- {
- synchronized (mLock)
- {
- if (mEnabled) return;//開始的時候這里是false
- mEnabled = true;
- }
- <10> sendMessage(ENABLE, 1, null);//發送消息
- }
- /**分析 <10> base\services\java\com\android\server\location\gpsLocationProvider.java**/
- private void sendMessage(int message, int arg, Object obj)
- {
- // hold a wake lock until this message is delivered
- // note that this assumes the message will not be removed from the queue before
- // it is handled (otherwise the wake lock would be leaked).
- mWakeLock.acquire();
- <11> mHandler.obtainMessage(message, arg, 1, obj).sendToTarget(); //通過handler機制來發送消息
- }
- /**分析 <11> base\services\java\com\android\server\location\gpsLocationProvider.java**/
- private final class ProviderHandler extends Handler
- {
- public void handleMessage(Message msg)
- {
- switch (message)
- {
- case ENABLE: //有<10>可知,message == ENABLE , msg.arg1 == 1
- if (msg.arg1 == 1) {
- <12> handleEnable(); //所以會調用這個函數
- } else {
- handleDisable();
- }
- break;
- .....
- }
- }
- }
- /**分析 <12> framework\base\services\java\com\android\server\location\gpsLocationProvider.java**/
- private void handleEnable()
- {
- <13> boolean enabled = native_init(); //調用JNI中的 static jboolean android_location_GpsLocationProvider_init(JNIEnv* env, jobject obj)
- if (enabled)
- {
- mSupportsXtra = native_supports_xtra(); //native_supports_xtra()直接返回true,在class_init_native()已經賦值
- if (mSuplServerHost != null)
- {
- /*這里沒做任何事,因為sAGpsInterface為空,代碼流程如下*/
- native_set_agps_server(AGPS_TYPE_SUPL, mSuplServerHost, mSuplServerPort);
- -->static void android_location_GpsLocationProvider_set_agps_server(JNIEnv* env, jobject obj, jint type, jstring hostname, jint port)
- -->if (!sAGpsInterface) return;
- -->sAGpsInterface = (const AGpsInterface*)sGpsInterface->get_extension(AGPS_INTERFACE);
- -->static const void *skytraq_gps_get_extension(const char* name)
- {
- ALOGD("%s: called", __FUNCTION__);
- return NULL;
- }
- }
- if (mC2KServerHost != null) { //同理這里也直接返回了
- native_set_agps_server(AGPS_TYPE_C2K, mC2KServerHost, mC2KServerPort);
- }
- }else{
- synchronized (mLock) {
- mEnabled = false;
- }
- Log.w(TAG, "Failed to enable location provider");
- }
- }
- /**分析 <13> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp **/
- static jboolean android_location_GpsLocationProvider_init(JNIEnv* env, jobject obj)
- {
- <14> if (!sGpsInterface || sGpsInterface->init(&sGpsCallbacks) != 0)//sGpsInterface不為null,在一開始的就已賦值,所以會調用init函數
- return false;
- .....
- }
- /**分析 <14> hardware\xxx\gps\skytraq\Skytraq_gps.c **/
- static int skytraq_gps_init(GpsCallbacks* callbacks) //callbacks回調函數時有JNI傳下來的,在JNI中實現的
- {
- GpsState* s = &_gps_state; //該結構圖數組初始化的時候都為0
- if (!s->init)
- <15> gps_state_init(s, callbacks);
- }
- /**分析 <15> hardware\xxx\gps\skytraq\Skytraq_gps.c **/
- static void gps_state_init( GpsState* state, GpsCallbacks* callbacks )
- {
- state->fd = gps_channel_open(GPS_CHANNEL_NAME);
- --> fd = open("/dev/skytraq_gps_ipc", O_RDWR | O_SYNC); //打開串口
- int ret = ioctl(state->fd, GPS_IPC_SET, &gps_connect_info); //調用驅動函數ioctl設置gps
- state->thread = callbacks->create_thread_cb( "gps_state_thread", gps_state_thread, state );//創建線程,用來監聽發送的命令和監聽數據上報,
- }
- /**分析<9> frwmework\base\services\java\com\android\server\LocationManagerService.java
- private void applyRequirementsLocked(String provider)
- {
- //設置worksource和providerRequest
- .....
- <16> p.setRequest(providerRequest, worksource); //location provider 發送請求
- }
- /**分析<16> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/
- public void setRequest(ProviderRequest request, WorkSource source)
- {
- <17> sendMessage(SET_REQUEST, 0, new GpsRequest(request, source)); //發送消息,SET_REQUEST == 3
- }
- /**分析<17> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/
- public void handleMessage(Message msg)
- {
- ...
- case SET_REQUEST:
- GpsRequest gpsRequest = (GpsRequest) msg.obj;
- <18> handleSetRequest(gpsRequest.request, gpsRequest.source);
- break;
- }
- /**分析<18> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/
- private void handleSetRequest(ProviderRequest request, WorkSource source)
- {
- ...
- <19> startNavigating(singleShot);//開始導航
- }
- /**分析<19> frwmework\base\services\java\com\android\server\location\GpsLocationProvider.java**/
- private void startNavigating(boolean singleShot)
- {
- <20> native_set_position_mode(mPositionMode, GPS_POSITION_RECURRENCE_PERIODIC, interval, 0, 0)//該函數在HAL層直接返回了,沒做任何事
- <21> native_start()
- }
- /**分析<20> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp**/
- static jboolean android_location_GpsLocationProvider_set_position_mode(JNIEnv* env, jobject obj,
- jint mode, jint recurrence, jint min_interval, jint preferred_accuracy, jint preferred_time)
- {
- if (sGpsInterface)
- <22> return (sGpsInterface->set_position_mode(mode, recurrence, min_interval, preferred_accuracy,
- preferred_time) == 0); //調用HAL層接口
- }
- /**分析<22> xxx\gps\skytraq\skytraq.gps.c**/
- static int skytraq_gps_set_position_mode(GpsPositionMode mode,
- GpsPositionRecurrence recurrence,
- uint32_t min_interval,
- uint32_t preferred_accuracy,
- uint32_t preferred_time)
- {
- ALOGD("%s: called", __FUNCTION__);
- return 0;
- }
- /**分析<21> framework\base\services\jni\com_android_server_location_GpsLocationProvider.cpp**/
- static jboolean android_location_GpsLocationProvider_start(JNIEnv* env, jobject obj)
- {
- if (sGpsInterface)
- <23> return (sGpsInterface->start() == 0); //調用HAL 層的static int skytraq_gps_start()
- }
- /**分析<23> xxx\gps\skytraq\skytraq.gps.c**/
- static int skytraq_gps_start()
- {
- gps_state_start(s);
- -->s->status = CMD_START;
- /*在<15>線程函數gps_state_thread()中while(1)中等該命令,進入獲取數據*/
- }
- 此時GPS就已運行