Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is Android's Wakelock a necessity for background services?

I am writing a long-running background service that collects and analyzes device data. To do this I start a service, the service spawns a thread and the thread does the data collection / analysis.

From my reading I have learned that if I want the service to do it's thing while the screen is locked / device is sleeping, that I should be using a partial wakelock to ensure that the cpu does not go to sleep while the service's thread is running. However I'm really confused about this because I am currently not using a wakelock and am able to background my app or lock the screen or kill the app via the task manager and each time I do this I am able to observe via the logcat and Log statements that the thread that I spawned in the service is still running and doing the work that I want it to.

I've even run an adb shell dumpsys power and found that I have refcount = 0 for wakelocks which indicates to me that a different app isn't holding the wakelock for me.

Am I just getting lucky that my service seems to run just fine in the background without a wakelock?

Edit: The device has exhibited this behavior when connected to USB and when detached from USB. I have am periodically uploading the data that I collect to a server and have run tests where I never plug the device in and have the screen locked the entire test and I still am seeing that my thread runs and data gets uploaded.

like image 372
neonDion Avatar asked May 04 '15 05:05

neonDion


1 Answers

You were not "lucky" that your service is fine without a wakelock. Your device never slept.

If you have USB connected and supplying power, then your device will not sleep. After all, what is the point of saving power if you have a ready supply of it to use?

You need to connect to your device using adb over IP (adb connect ) and then do logcat from there to see if you still observe your expected logs.

EDIT: Forgot to actually answer the question.

If you want your service to do things constantly, then you need to keep a wakelock. Keep in mind that permanently keeping a wakelock is basically sin #1 in mobile programming. You should NEVER EVER KEEP A PERMANENT WAKELOCK.

Since your service is tracking data usage, then there is no need for a wakelock since, if the device is sleeping, then there is no data to be logged.

EDIT 2: Let's experiment!

Hmmm. Sleep is hard to force, so let's go straight to the nuclear option.

  1. Modify your code so that instead of actually uploading data, you instead store some meta-data to tell you that you would have stored data at a specific timestamp. Also, modify your code so that you can keep track of power events and also timestamp them. If you can, keep all of this data in memory so that we don't have too much system code running.

  2. Put your phone into airplane mode. That's right, turn off all external connections. Also, don't use ADB or logcat or anything like that.

  3. Kill all non-essential apps. Uninstall is best.

  4. Run your service as a user would using the UI. DO NOT USE A TEST OF ANY SORT; TESTS MAY PREVENT SLEEP (it's hard to know anything for certain on Android since sleepiness is an OEM thing).

  5. Wait a while.

  6. Dump out your in-memory logs with timestamps. You probably won't get accurate data on when the sleep occurred, if it will even tell you that you slept. But you should be able to infer it from odd power event orderings as you transition back to the state that you were just in.

like image 185
justhecuke Avatar answered Sep 20 '22 14:09

justhecuke