Android app recycling mechanism or how to prevent applications from being killed as much as possible

Source: Internet
Author: User

My friends collected and sorted it online. I couldn't find the source of the original article.

Refer:

Http://blog.csdn.net/windskier/article/details/6560925

Http://blog.csdn.net/zmyde2010/article/details/6756368

Http://blog.sina.com.cn/s/blog_514048cb0100wi2j.html

Method:
For applications stored in the/system/app, you need to set the persistent attribute in the manifest. xml file of the app, such as the androidmanifest. xml file of the app 'phone:

[Java]
View plaincopyprint?
  1. <Application Android: Name = "phoneapp"
  2. Android: Persistent = "true"
  3. Android: Label = "@ string/dialericonlabel"
  4. Android: icon = "@ drawable/ic_launcher_phone">
  5. ...
  6. </Application>
    <application android:name="PhoneApp"                android:persistent="true"                 android:label="@string/dialerIconLabel"                 android:icon="@drawable/ic_launcher_phone">         ...    </application>

After setting, the app is upgraded to the system core level and will not be killed in any case. The stop operation will also be blocked in settings-> applications.

The preceding log is set as follows:

[Java]
View plaincopyprint?
  1. Proc #19: adj = svc/B 4067b028 255: COM. XXX. XXX/10001 (started-services)
  2. # Cat/proc/255/oom_adj
  3. 4
    Proc #19: adj=svc  /B 4067b028 255:com.xxx.xxx/10001 (started-services)    # cat /proc/255/oom_adj    4
Configured log: [Java]
View plaincopyprint?
  1. Pers #19: adj = Core/F 406291f0 155: COM. XXX. XXX/10001 (fixed)
  2. # Cat/proc/155/oom_adj
  3. -12 # This is core_server_adj
  4. Note: The oom_adj of the init process is-16 (system_adj): CAT/proc/1/oom_adj
Pers #19: Quick Bi = Core/F 406291f0 155: COM. xxx. xxx/10001 (fixed) # Cat/proc/155/oom_adj-12 # This is core_server_adj Note: The oom_adj of the init process is-16 (system_adj): CAT/proc/1/oom_adj

The following code is available in the file frameworks/base/services/Java/COM/Android/Server/AM/activitymanagerservice. Java:[Java]
View plaincopyprint?

  1. Final processrecord addapplocked (applicationinfo info ){
  2. Processrecord APP = getprocessrecordlocked (info. processname, info. UID );
  3. If (APP = NULL ){
  4. APP = newprocessrecordlocked (null, info, null );
  5. Mprocessnames. Put (info. processname, info. uid, APP );
  6. Updatelruprocesslocked (app, true, true );
  7. }
  8. If (info. Flags & (applicationinfo. flag_system | applicationinfo. flag_persistent ))
  9. ==( Applicationinfo. flag_system | applicationinfo. flag_persistent )){
  10. App. Persistent = true;
  11. App. maxadj = core_server_adj; // This constant value is-12.
  12. }
  13. If (App. Thread = NULL & mpersistentstartingprocesses. indexof (APP) <0 ){
  14. Mpersistentstartingprocesses. Add (APP );
  15. Startprocesslocked (app, "added Application", app. processname );
  16. }
  17. Return app;
  18. }
Final processrecord addapplocked (applicationinfo info) {processrecord APP = getprocessrecordlocked (info. processname, info. UID); If (APP = NULL) {APP = newprocessrecordlocked (null, info, null); mprocessnames. put (info. processname, info. UID, APP); updatelruprocesslocked (app, true, true);} If (info. flags & (applicationinfo. flag_system | applicationinfo. flag_persistent) = (applicationinfo. flag_system | Applicationinfo. flag_persistent) {app. Persistent = true; app. maxadj = core_server_adj; // This constant value is-12. } If (App. thread = NULL & mpersistentstartingprocesses. indexof (APP) <0) {mpersistentstartingprocesses. add (APP); startprocesslocked (app, "added Application", app. processname);} return app ;}

It can be seen that you want to become a core service (that is, app. maxadj = core_server_adj (-12). The application requires flag_system and flag_persistent. flag_system indicates that the application is located under/system/app, and flag_persistent indicates the persistent attribute.

For frameworks/base/services/Java/COM/Android/Server/systemserver. Java
      Activitymanagerservice. setsystemprocess ();
Set your app. maxadj to system_adj, that is,-16.

Principle:
Processes in Android are hosted. When the system process space is insufficient, the process is automatically reclaimed based on the priority. This brings about three problems:
   1) recycling rules:When will it be recycled?
   2) avoid false positives:How can we prevent recycling?
   3) data recovery and storage:What should I do if it is recycled?
 
Android divides processes into six levels. The order of priority is from high to low:
  1. Foreground process (foreground_app)
  2. Visual Process (visible_app)
  3. Secondary service process (secondary_server)
  4. background process (hidden_app)
  5. content supply node (content_provider)
  6. Empty Process (empty_app)
 
Features:
1. If a process contains both service and visible activity, the process should be classified as a visible process rather than a service process.
2. In addition, if other processes depend on it, the level of a process can be increased. For example, if a service in process a is bound to a component in process B, process a is considered at least as important as process B.
3. The phone service in the system is divided into foreground processes rather than secondary service processes.
 
In Android, The oom_adj value of a process represents its priority. The higher the oom_adj value, the lower the priority of the process. The file/init. RC has the following attribute settings:[Java]
View plaincopyprint?

  1. Setprop Ro. foreground_app_adj 0
  2. Setprop Ro. visible_app_adj 1
  3. Setprop Ro. secondary_server_adj 2
  4. Setprop Ro. hidden_app_min_adj 7
  5. Setprop Ro. content_provider_adj 14
  6. Setprop Ro. empty_app_adj 15
    setprop ro.FOREGROUND_APP_ADJ       0    setprop ro.VISIBLE_APP_ADJ                     1    setprop ro.SECONDARY_SERVER_ADJ   2    setprop ro.HIDDEN_APP_MIN_ADJ           7    setprop ro.CONTENT_PROVIDER_ADJ  14    setprop ro.EMPTY_APP_ADJ                    15

In/init. RC, set oom_adj of the process whose PID is 1 (INIT process) to system_adj (-16 ).

View local settings:
CAT/sys/module/lowmemorykiller/parameters/adj

 
Recovery Time:
File/init. RC:[Java]
View plaincopyprint?

  1. Setprop Ro. foreground_app_mem 1536 // 6 m
  2. Setprop Ro. visible_app_mem 2048 // 8 m
  3. Setprop Ro. secondary_server_mem 4096 // 16 m
  4. Setprop Ro. hidden_app_mem 5120 // 20 m
  5. Setprop Ro. content_provider_mem 5632 // 22.4 m
  6. Setprop Ro. empty_app_mem 6144 // 24 m
   setprop ro.FOREGROUND_APP_MEM       1536      //    6M   setprop ro.VISIBLE_APP_MEM                     2048     //    8M   setprop ro.SECONDARY_SERVER_MEM   4096     //  16M   setprop ro.HIDDEN_APP_MEM                     5120     //  20M   setprop ro.CONTENT_PROVIDER_MEM    5632     //  22.4M   setprop ro.EMPTY_APP_MEM                      6144     //  24M

These numbers are the corresponding memory threshold. Once they are lower than this value, Android begins to close the process of the corresponding level in order.
Note that the unit of these numbers is page: 1 page = 4 kb. So the above six numbers correspond to (MB): 6, 8, 16, 20.
 
View the current memory threshold settings:
[Java]
View plaincopyprint?

  1. CAT/sys/module/lowmemorykiller/parameters/minfree
cat /sys/module/lowmemorykiller/parameters/minfree
To reset this value (corresponding to different requirements ): [Java]
View plaincopyprint?
  1. Echo "1536,2048, 4096,5120, 15360,23040">/sys/module/lowmemorykiller/parameters/minfree
echo   "1536,2048,4096,5120,15360,23040">/sys/module/lowmemorykiller/parameters/minfree
In this way, when the available memory is less than 90 MB, the "Empty Process" will be killed, and when the available memory is less than 60 MB, the "content supply node" process will be killed.
 
The specific recycling function trimapplications () in activitymanagerservice. Java ():
    1. First, Remove useless processes that have been uninstalled from the package;
    2. Update the oom_adj value based on the current state of the process, and then perform the following operations:
                1) Remove the processes without activity running;
                2) If the AP has saved all activity states, terminate the AP.
    3. At last, if there are still many activities running, remove the activity that has been saved.
 

Update oom_adj value:
In the computeoomadjlocked () file of the activitymanagerservice. Java file, calculate the oom_adj of the process, for example:
[Java]
View plaincopyprint?

  1. If (APP = top_app ){
  2. // The Last app on the list is the foreground app.
  3. Adj = foreground_app_adj;
  4. App. adjtype = "Top-activity ";
  5. }
     if (app == TOP_APP) {            // The last app on the list is the foreground app.            adj = FOREGROUND_APP_ADJ;            app.adjType = "top-activity";        }
 
Low memory killer in Android Kernel
Android low memory killer kills the process to release its memory as needed (when the system memory is insufficient). The source code is in kernel/Drivers/MISC/lowmemorykiller. C. Simply put, it is to find the most suitable process to kill and release the memory it occupies.
The most suitable process is:
    ? More oom_adj
    ? The more physical memory occupied
 
Once a process is selected, the kernel sends a sigkill signal to kill it:
[Java]
View plaincopyprint?
  1. For_each_process (p ){
  2. ......
  3. If (selected = NULL | p-> oomkilladj> selected-> oomkilladj |
  4. (P-> oomkilladj = selected-> oomkilladj & tasksize> selected_tasksize ))
  5. {
  6. Selected = P;
  7. }
  8. }
  9. If (selected! = NULL ){
  10. Force_sig (sigkill, selected );
  11. }
   for_each_process(p) {        ……        if(selected == NULL ||   p->oomkilladj > selected->oomkilladj ||              (p->oomkilladj == selected->oomkilladj && tasksize > selected_tasksize))        {             selected = p;        }   }   if(selected != NULL) {        force_sig(SIGKILL, selected);   }
 
View LRU list: ADB shell dumpsys Activity
When activitydemo is on the frontend:
Processes that contain services have a high priority. In computeoomadjlocked, they are divided into two classes:
[Java]
View plaincopyprint?
  1. Static final int max_service_inactivity = 30*60*1000;
  2. If (now <(S. lastactivity + max_service_inactivity )){
  3. If (adj> secondary_server_adj ){
  4. Adj = secondary_server_adj;
  5. App. adjtype = "started-services ";
  6. App. Hidden = false;
  7. }
  8. }
  9. If (adj> secondary_server_adj ){
  10. App. adjtype = "started-BG-services ";
  11. }
      static final int MAX_SERVICE_INACTIVITY = 30*60*1000;                       if (now < (s.lastActivity+MAX_SERVICE_INACTIVITY)) {               if (adj > SECONDARY_SERVER_ADJ) {                            adj = SECONDARY_SERVER_ADJ;                            app.adjType = "started-services";                            app.hidden = false;               }      }      if (adj > SECONDARY_SERVER_ADJ) {                        app.adjType = "started-bg-services";      } 

It is impossible to completely prevent the process from being killed. We can perform some operations to reduce the chance of the process being killed:
 1) process priority improvement:
       * Background operations adopt the form of service because a process running a service has a higher level than a background activity;
       * Press the back key to run the activity in the process in the background rather than destory. You need to reload the back button (no activity is killed first in the running process ).
       * Dependent on other high-priority processes;

 2) force modify process attributes:
       * In the process, set setpersistent (true) to/system/app.
       * Set (as shown above) in the manifest file to put the APK under/system/app.

From: http://blog.csdn.net/yuan1590/article/details/7775158

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.