I don't mind letting the application get killed by the Android OS, I'm trying to debug why the application is restarting after being killed by low memory situations. I'm using
adb shell dumpsys activity processes
To read the "Process LRU list (sorted by oom_adj):"
My current problem is when I do the following steps and read the dumpsys after each step.
App Running
Proc #)13: adj=fore /FA trm= 0 6124:com.thisoldthing (top-activity)
App closed by back button
Proc #20: adj=bak /B trm= 0 6124:com.thisoldthing (started-bg-ui-services)
Killed after running stressrobo
Proc #13: adj=svc /B trm=15 8488:com.thisoldthing (started-services)
Now the application is not killed when putting the device into a low memory situation. More worrisome is I want to know why it restarted.
Android will try to keep your service alive as long as possible. The documentation of Context.startService() says: "If any errors happen in the service's process, it will automatically be restarted." My understanding and experience let me believe that it will happen regardless you started with startService() or bindService(), but the last one has no mention to that though.
So, if you don't want get your service restarted, you need to close bound connections before kill it. Unfortunately the application can not rely in onDestroy() being called in killing conditions so any unbindService() calls will depend on application's life-cycle. You will need to handle it by yourself.
Finally, bind connections was not designed to remain forever. They should connect, do the job and unbind. Keeping this in mind, android does the right think restarting services with bound connections.
Related
How does the apps like Swiftkey, Locker Master manages to keep process alive even after it has been removed from back stack?
They also don't use sticky notification.
Update:-
I need to keep my process alive. But in my case service is active but process gets killed.
They all have one or more unbound background service.
To kill those services you can go into Settings -> Apps -> Running.
However the services may be restarted at any time by other apps or system by sending a system wide message (intent). In most cases it is restarted by
Time events
Boot complete
Other apps
Other intents
In the Swiftkey case, it will be started by Android OS when it needs to show a keyboard.
EDIT: you can specify that a service runs in a remote process by adding this to the service definition in AndroidManifest
android:process="process_name_here"
However there is no such thing as a service that cannot be killed and can run forever. Android OS may start killing your service if it is running low on resources or the service is running for a long period of time. To overcome this, you can make a forground running service, but it needs to show a notification. It can also be killed by task managers, like you mentioned. You should instead start focusing on how to save it's state so you are able to restart it later.
I have been reading about process life-cycles after I noticed that android unexpectedly terminated my app. The app is normally running also in background but now it was terminated. The app listens gps location updates, battery state broadcasts, receives sms broadcasts, runs Bluetooth and tcp server etc. So it has quite a lot of jobs to do and until now it has succeeded pretty well.
What I found out was that android probably closed the process due to low RAM. My app was still in the 'app swap' list but when I selected it I noticed that it was actually restarted which explained the fact that I was not able to connect it earlier using tcp. Do you agree my conclusion or is there any other reason than low RAM that could cause this?
After reading a bit more I understood I should have implemented almost the whole application as a foreground service because those will be killed only after there are no normal activities to kill. However I'm not that comfortable in doing such a bit changes to the application at this point. BUT, then I found this:
http://developer.android.com/guide/components/processes-and-threads.html
There are five levels in the importance hierarchy. The following list presents the different types of processes in order of importance (the first process is most important and is killed last):
Foreground process
A process that is required for what the user is currently doing. A process is considered to be in the foreground if any of the following conditions are true:
-It hosts an Activity that the user is interacting with (the Activity's onResume() method has been called).
-It hosts a Service that's bound to the activity that the user is interacting with.
-It hosts a Service that's running "in the foreground"—the service has called startForeground().
-It hosts a Service that's executing one of its lifecycle callbacks (onCreate(), onStart(), or onDestroy()).
-It hosts a BroadcastReceiver that's executing its onReceive() method.
Please correct if I got the bolded condition wrong. Doesn't it mean that I could just make my app to host a dummy foreground service after which the process running my app and the dummy service would be considered as foreground process which again would mean that it would be very unlike that Android killed my app?? This way I wouldn't have to go through all the functions my app has and to figure out how to get them work as a service.
Thanks!
On my Galaxy Nexus with Jelly Bean 4.1.1 (official) sometimes the OS goes on a killing spree and the log has these kinds of entries:
10-02 22:24:34.992 I/ActivityManager( 306): Killing 7517:com.google.android.apps.reader/u0a77: remove task
10-02 22:24:36.484 I/ActivityManager( 306): Killing 7465:com.tf.thinkdroid.sg:writedroid/u0a50: remove task
10-02 22:24:37.273 I/ActivityManager( 306): Killing 5924:com.metago.astro/u0a73: remove task
10-02 22:24:37.296 W/ActivityManager( 306): Scheduling restart of crashed service com.metago.astro/.jobs.JobService in 5000ms
10-02 22:24:37.656 I/ActivityManager( 306): Killing 7302:org.jtb.alogcat/u0a84: remove task
10-02 22:24:38.148 I/ActivityManager( 306): Killing 7120:com.google.android.gm/u0a19: remove task
Unfortunately one of the processes being killed is my remote service that has a running app bound to it. Indeed, the service is restarted immediately afterwards but this causes inconsistent behavior in my app.
In Service Lifecycle it says:
A service can be both started and have connections bound to it. In
such a case, the system will keep the service running as long as
either it is started or there are one or more connections to it with
the Context.BIND_AUTO_CREATE flag.
My app binds to the remote service with Context.BIND_AUTO_CREATE so I was under the impression that the remote service will stay up as long as the main process is bound to it. How can I make Android not kill the remote service?
NOTE: The bounty is for explaining why the code doesn't seem to work according to the documentation.
Please, read this answer from Joel F here: How it is possible Service run indefinitely and also allow binding in android?
As mentioned, if there is really a need for resources, the only way of keeping your service unkillable is to use foreground service http://developer.android.com/guide/components/services.html#Foreground
The documentation is also written wrongly because the citation : "system will keep the service running as long as either it is started or there are one or more connections to it" is not true in 100% of cases. The Context.BIND_AUTO_CREATE flag will give a higher privilege to your service but not hight enough to keep it unkillable. The other services will be killed first and if there is still need for ressourcees, your privileged service will be also killed.
A Service is a component of an Application, which runs in a process. Though, according to the service lifecycle documentation, the process containing the service should not have been killed, but there are some other cases when Android may kill.
In case the OS has some resource shortage, it will prioritize the running processes and kill the process with lower priority. Now, if there are more than one processes running which have services which are promised not to be killed according to Service life cycle, Android will prioritize and kill the process with lower priority.
Android might decide to shut down a process at some point, when memory
is low and required by other processes that are more immediately
serving the user. Application components running in the process that's
killed are consequently destroyed. A process is started again for
those components when there's again work for them to do.
When deciding which processes to kill, the Android system weighs their
relative importance to the user. For example, it more readily shuts
down a process hosting activities that are no longer visible on
screen, compared to a process hosting visible activities. The decision
whether to terminate a process, therefore, depends on the state of the
components running in that process.
Quoted from here: http://developer.android.com/guide/components/processes-and-threads.html
When OS is running low in resouces, it is compelled to take decisions breaking fair promises :)
For setting services un-killable, please take a look on android persistant services: http://devescape.blogspot.ch/2011/02/persistent-services-in-android.html
I would like to simply stop the app, and all its activities and services. Currently, from my main activity (which had started other activities), I call finish(), and the app appears to stop, as it goes to the home screen of my device. However, when I check running apps on the device, this app is still listed. It says "one process, and one service". Is there a way to just kill everything? Or, if I have to do it individually how would I find what is running, and how do I stop it? thanks
Is there some specific reason you want to make sure the process is killed?
Android manages processes intelligently. It keeps your process around, and if the user starts your app again it can use the existing process, rather than start up a new one. And if your device start running low on memory, Android will start killing off these inactive processes to free up resources.
In short, it's a good thing that Android keeps your process around. You shouldn't want to have it killed needlessly.
Although it sounds like you may not be stopping your application's service. If you use bindService to start the service from your activity, the service will automatically be stopped when the Activity is stopped (assuming nothing else has bound to the service). Alternately, if you use startService to start the service, you need to call stopService to stop it.
Given a service that return START_STICKY from its onStartCommand:
1) The documentation mentions killing of the service, as far as I understand this, that is not done by calling Content.stopService, but done by the system if it needs resources (or my service could also crash which would be effectively the same - no clean shutdown) ?
2) How can I simulate the killing mentioned in 1) ? The killing is probably different from stopping (stoppping != killing ?) the service using the application menu in the settings, so I can't use this menu for testing purposes?
3) If my service is killed and then restarted, according to the documentation, only onStartCommand seems to be called, but not onCreate. So I conclude that variables of my service are persistet before my service gets killed? Or why does onCreate not get aclled? Or does it maybe?
My aim is to make sure that my service still works reliable when it was killed and restarted. Thanks for any hint :-)
Killing means its process being killed by the out of memory killer. You can simulate this from the adb shell -- use "ps" to find your app's process, and "kill" with the found pid to kill it. The system will after a few seconds restart the process and service.
If you are only receiving onStartCommand(), then your service and process was already running and didn't need to be re-created.
I had the same issue, and was wondering what is going on.
After reading the referenced post, I simply moved my code from onStartCommand(..) to onCreate(..) and it was working as expected.