ProcessList.java revision 9d52f791b94bbf03739bdee4ccdd3ecb514c8eeb
17d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn/*
27d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * Copyright (C) 2011 The Android Open Source Project
37d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn *
47d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * Licensed under the Apache License, Version 2.0 (the "License");
57d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * you may not use this file except in compliance with the License.
67d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * You may obtain a copy of the License at
77d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn *
87d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn *      http://www.apache.org/licenses/LICENSE-2.0
97d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn *
107d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * Unless required by applicable law or agreed to in writing, software
117d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * distributed under the License is distributed on an "AS IS" BASIS,
127d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
137d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * See the License for the specific language governing permissions and
147d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * limitations under the License.
157d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn */
167d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
177d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornpackage com.android.server.am;
187d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
197d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornimport java.io.IOException;
20bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynorimport java.io.OutputStream;
21bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynorimport java.nio.ByteBuffer;
227d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
238e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackbornimport android.app.ActivityManager;
249d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackbornimport android.os.Build;
25ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackbornimport android.os.SystemClock;
267d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornimport com.android.internal.util.MemInfoReader;
277d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornimport com.android.server.wm.WindowManagerService;
287d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
29fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Crossimport android.content.res.Resources;
307d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornimport android.graphics.Point;
3159d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Crossimport android.os.SystemProperties;
32bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynorimport android.net.LocalSocketAddress;
33bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynorimport android.net.LocalSocket;
347d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackbornimport android.util.Slog;
3559c009776dae5ccbdfb93d7151ff2065ca049dc3Craig Mautnerimport android.view.Display;
367d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
377d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn/**
387d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn * Activity manager code dealing with processes.
397d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn */
40be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackbornfinal class ProcessList {
417d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // The minimum time we allow between crashes, for us to consider this
427d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // application to be bad and stop and its services and reject broadcasts.
437d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int MIN_CRASH_INTERVAL = 60*1000;
447d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
457d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // OOM adjustments for processes in various states:
467d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
47c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    // Adjustment used in certain places where we don't know it yet.
48c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    // (Generally this is something that is going to be cached, but we
49c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    // don't know the exact value in the cached range to assign yet.)
50c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    static final int UNKNOWN_ADJ = 16;
51c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn
527d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is a process only hosting activities that are not visible,
53e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // so it can be killed without any disruption.
54be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    static final int CACHED_APP_MAX_ADJ = 15;
5520cdcee47d10986969e7e2a53a40a6ecabae3827Dianne Hackborn    static final int CACHED_APP_MIN_ADJ = 9;
56e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn
57e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // The B list of SERVICE_ADJ -- these are the old and decrepit
58e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // services that aren't as shiny and interesting as the ones in the A list.
59f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    static final int SERVICE_B_ADJ = 8;
60f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn
61f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // This is the process of the previous application that the user was in.
62f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // This process is kept above other things, because it is very common to
63f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // switch back to the previous app.  This is important both for recent
64f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // task switch (toggling between the two top recent apps) as well as normal
65f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // UI flow such as clicking on a URI in the e-mail app to view in the browser,
66f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    // and then pressing back to return to e-mail.
67f35fe23669aeeebd2db2acb6baacae503dba03a8Dianne Hackborn    static final int PREVIOUS_APP_ADJ = 7;
687d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
697d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is a process holding the home application -- we want to try
707d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // avoiding killing it, even if it would normally be in the background,
717d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // because the user interacts with it so much.
727d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int HOME_APP_ADJ = 6;
737d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
74e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // This is a process holding an application service -- killing it will not
75e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // have much of an impact as far as the user is concerned.
76e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    static final int SERVICE_ADJ = 5;
777d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
787d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is a process with a heavy-weight application.  It is in the
797d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // background, but we want to try to avoid killing it.  Value set in
807d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // system/rootdir/init.rc on startup.
81c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    static final int HEAVY_WEIGHT_APP_ADJ = 4;
82c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn
83c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    // This is a process currently hosting a backup operation.  Killing it
84c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    // is not entirely fatal but is generally a bad idea.
85c8230519728b14065effd3b7d4eca273ff86160cDianne Hackborn    static final int BACKUP_APP_ADJ = 3;
867d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
877d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is a process only hosting components that are perceptible to the
887d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // user, and we really want to avoid killing them, but they are not
89e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // immediately visible. An example is background music playback.
907d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int PERCEPTIBLE_APP_ADJ = 2;
917d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
927d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is a process only hosting activities that are visible to the
93e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // user, so we'd prefer they don't disappear.
947d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int VISIBLE_APP_ADJ = 1;
957d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
967d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // This is the process running the current foreground app.  We'd really
97e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // rather not kill it!
987d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int FOREGROUND_APP_ADJ = 0;
997d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
100e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    // This is a system persistent process, such as telephony.  Definitely
1017d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // don't want to kill it, but doing so is not completely fatal.
102e02c88af7935c72fb90a478375e61e4a94465587Dianne Hackborn    static final int PERSISTENT_PROC_ADJ = -12;
1037d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1047d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // The system process runs at the default adjustment.
1057d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int SYSTEM_ADJ = -16;
1067d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1078e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    // Special code for native processes that are not being managed by the system (so
1088e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    // don't have an oom adj assigned by the system).
1098e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    static final int NATIVE_ADJ = -17;
1108e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn
1117d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // Memory pages are 4K.
1127d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    static final int PAGE_SIZE = 4*1024;
1137d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
114be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    // The minimum number of cached apps we want to be able to keep around,
1157d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // without empty apps being able to push them out of memory.
116be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    static final int MIN_CACHED_APPS = 2;
1177d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1182286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // The maximum number of cached processes we will keep around before killing them.
1192286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // NOTE: this constant is *only* a control to not let us go too crazy with
1202286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // keeping around processes on devices with large amounts of RAM.  For devices that
1212286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // are tighter on RAM, the out of memory killer is responsible for killing background
1222286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // processes as RAM is needed, and we should *never* be relying on this limit to
1232286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // kill them.  Also note that this limit only applies to cached background processes;
1242286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // we have no limit on the number of service, visible, foreground, or other such
1252286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // processes and the number of those processes does not count against the cached
1262286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // process limit.
127be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    static final int MAX_CACHED_APPS = 24;
128b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn
129b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    // We allow empty processes to stick around for at most 30 minutes.
130b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    static final long MAX_EMPTY_TIME = 30*60*1000;
131b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn
1322286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // The maximum number of empty app processes we will let sit around.
1332286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    private static final int MAX_EMPTY_APPS = computeEmptyProcessLimit(MAX_CACHED_APPS);
134b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn
135b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    // The number of empty apps at which we don't consider it necessary to do
136b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    // memory trimming.
1372286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    static final int TRIM_EMPTY_APPS = MAX_EMPTY_APPS/2;
1382286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn
1392286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // The number of cached at which we don't consider it necessary to do
1402286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    // memory trimming.
1412610b7cb2a197a3f3f8f7c3409b6962353684159Dianne Hackborn    static final int TRIM_CACHED_APPS = ((MAX_CACHED_APPS-MAX_EMPTY_APPS)*2)/3;
142b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn
143be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    // Threshold of number of cached+empty where we consider memory critical.
144b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    static final int TRIM_CRITICAL_THRESHOLD = 3;
145b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn
146be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn    // Threshold of number of cached+empty where we consider memory critical.
147b12e1354f25f04e9c9a71da76c6fca858b7d39d0Dianne Hackborn    static final int TRIM_LOW_THRESHOLD = 5;
1487d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
149bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    // Low Memory Killer Daemon command codes.
150bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    // These must be kept in sync with the definitions in lmkd.c
151bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    //
152bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    // LMK_TARGET <minfree> <minkillprio> ... (up to 6 pairs)
153bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    // LMK_PROCPRIO <pid> <prio>
154bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    // LMK_PROCREMOVE <pid>
155bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    static final byte LMK_TARGET = 0;
156bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    static final byte LMK_PROCPRIO = 1;
157bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    static final byte LMK_PROCREMOVE = 2;
158bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
1597d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // These are the various interesting memory levels that we will give to
1607d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // the OOM killer.  Note that the OOM killer only supports 6 slots, so we
1617d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // can't give it a different value for every possible kind of process.
1627d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    private final int[] mOomAdj = new int[] {
1637d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            FOREGROUND_APP_ADJ, VISIBLE_APP_ADJ, PERCEPTIBLE_APP_ADJ,
164be4e6aaa0252dd7da28b7aa85beba982538efa46Dianne Hackborn            BACKUP_APP_ADJ, CACHED_APP_MIN_ADJ, CACHED_APP_MAX_ADJ
1657d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    };
1667d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // These are the low-end OOM level limits.  This is appropriate for an
1677d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // HVGA or smaller phone with less than 512MB.  Values are in KB.
168bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private final int[] mOomMinFreeLow = new int[] {
1697d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            8192, 12288, 16384,
1707d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            24576, 28672, 32768
1717d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    };
1727d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // These are the high-end OOM level limits.  This is appropriate for a
1737d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // 1280x800 or larger screen with around 1GB RAM.  Values are in KB.
174bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private final int[] mOomMinFreeHigh = new int[] {
175b5cda42c57bc1f965edd73f6bbe1b0d77a933256Ben Cheng            49152, 61440, 73728,
176b5cda42c57bc1f965edd73f6bbe1b0d77a933256Ben Cheng            86016, 98304, 122880
1777d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    };
1787d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    // The actual OOM killer memory levels we are using.
179bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private final int[] mOomMinFree = new int[mOomAdj.length];
1807d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1817d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    private final long mTotalMemMb;
1827d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1833bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    private long mCachedRestoreLevel;
1843bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
1857d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    private boolean mHaveDisplaySize;
1867d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
187bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private static LocalSocket sLmkdSocket;
188bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private static OutputStream sLmkdOutputStream;
189bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
1907d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    ProcessList() {
1917d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        MemInfoReader minfo = new MemInfoReader();
1927d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        minfo.readMemInfo();
1937d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        mTotalMemMb = minfo.getTotalSize()/(1024*1024);
1947d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        updateOomLevels(0, 0, false);
1957d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    }
1967d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
1977d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    void applyDisplaySize(WindowManagerService wm) {
1987d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        if (!mHaveDisplaySize) {
1997d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            Point p = new Point();
200637dbfcaf0a1f43f81d3d195461b50bfc0fd5f14Colin Cross            wm.getBaseDisplaySize(Display.DEFAULT_DISPLAY, p);
2017d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            if (p.x != 0 && p.y != 0) {
2027d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn                updateOomLevels(p.x, p.y, true);
2037d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn                mHaveDisplaySize = true;
2047d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            }
2057d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        }
2067d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    }
2077d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
2087d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    private void updateOomLevels(int displayWidth, int displayHeight, boolean write) {
2097d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        // Scale buckets from avail memory: at 300MB we use the lowest values to
2107d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        // 700MB or more for the top values.
2117d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        float scaleMem = ((float)(mTotalMemMb-300))/(700-300);
2127d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
2137d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        // Scale buckets from screen size.
214635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        int minSize = 480*800;  //  384000
2157d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        int maxSize = 1280*800; // 1024000  230400 870400  .264
2167d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        float scaleDisp = ((float)(displayWidth*displayHeight)-minSize)/(maxSize-minSize);
217635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        if (false) {
218635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn            Slog.i("XXXXXX", "scaleMem=" + scaleMem);
219635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn            Slog.i("XXXXXX", "scaleDisp=" + scaleDisp + " dw=" + displayWidth
220635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn                    + " dh=" + displayHeight);
221635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        }
2227d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
2237d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        float scale = scaleMem > scaleDisp ? scaleMem : scaleDisp;
2247d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        if (scale < 0) scale = 0;
2257d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        else if (scale > 1) scale = 1;
226635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        int minfree_adj = Resources.getSystem().getInteger(
227635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn                com.android.internal.R.integer.config_lowMemoryKillerMinFreeKbytesAdjust);
228635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        int minfree_abs = Resources.getSystem().getInteger(
229635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn                com.android.internal.R.integer.config_lowMemoryKillerMinFreeKbytesAbsolute);
230635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        if (false) {
231635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn            Slog.i("XXXXXX", "minfree_adj=" + minfree_adj + " minfree_abs=" + minfree_abs);
232635a6d5a0b922b5d845b6e2c7ec8453b14fe4b01Dianne Hackborn        }
233fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross
2349d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn        final boolean is64bit = Build.SUPPORTED_64_BIT_ABIS.length > 0;
2359d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn
2367d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        for (int i=0; i<mOomAdj.length; i++) {
237bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            int low = mOomMinFreeLow[i];
238bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            int high = mOomMinFreeHigh[i];
239bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            mOomMinFree[i] = (int)(low + ((high-low)*scale));
2409d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn            if (is64bit) {
2419d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                // On 64 bit devices, we consume more baseline RAM, because 64 bit is cool!
2429d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                // To avoid being all pagey and stuff, scale up the memory levels to
2439d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                // give us some breathing room.
2449d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                mOomMinFree[i] = (3*mOomMinFree[i])/2;
2459d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn            }
246fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross        }
247fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross
248fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross        if (minfree_abs >= 0) {
249fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross            for (int i=0; i<mOomAdj.length; i++) {
2509d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                mOomMinFree[i] = (int)((float)minfree_abs * mOomMinFree[i]
2519d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                        / mOomMinFree[mOomAdj.length - 1]);
252fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross            }
253fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross        }
2547d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
255fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross        if (minfree_adj != 0) {
256fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross            for (int i=0; i<mOomAdj.length; i++) {
2579d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                mOomMinFree[i] += (int)((float)minfree_adj * mOomMinFree[i]
2589d52f791b94bbf03739bdee4ccdd3ecb514c8eebDianne Hackborn                        / mOomMinFree[mOomAdj.length - 1]);
259fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross                if (mOomMinFree[i] < 0) {
260fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross                    mOomMinFree[i] = 0;
261fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross                }
262fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross            }
263fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross        }
264fcdad6f292a1f83da3bbadc45779ae85307a6f3eColin Cross
2653bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        // The maximum size we will restore a process from cached to background, when under
2663bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        // memory duress, is 1/3 the size we have reserved for kernel caches and other overhead
2673bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        // before killing background processes.
2683bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        mCachedRestoreLevel = (getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024) / 3;
2693bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
27059d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        // Ask the kernel to try to keep enough memory free to allocate 3 full
27159d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        // screen 32bpp buffers without entering direct reclaim.
27259d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        int reserve = displayWidth * displayHeight * 4 * 3 / 1024;
27359d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        int reserve_adj = Resources.getSystem().getInteger(com.android.internal.R.integer.config_extraFreeKbytesAdjust);
27459d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        int reserve_abs = Resources.getSystem().getInteger(com.android.internal.R.integer.config_extraFreeKbytesAbsolute);
27559d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross
27659d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        if (reserve_abs >= 0) {
27759d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross            reserve = reserve_abs;
27859d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        }
27959d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross
28059d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        if (reserve_adj != 0) {
28159d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross            reserve += reserve_adj;
28259d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross            if (reserve < 0) {
28359d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross                reserve = 0;
28459d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross            }
28559d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross        }
28659d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross
2877d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        if (write) {
288bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            ByteBuffer buf = ByteBuffer.allocate(4 * (2*mOomAdj.length + 1));
289bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            buf.putInt(LMK_TARGET);
290bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            for (int i=0; i<mOomAdj.length; i++) {
291bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                buf.putInt((mOomMinFree[i]*1024)/PAGE_SIZE);
292bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                buf.putInt(mOomAdj[i]);
293bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            }
294bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
295bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            writeLmkd(buf);
29659d80a5270249b8b0b32b7ce8e081f4fbd41129aColin Cross            SystemProperties.set("sys.sysctl.extra_free_kbytes", Integer.toString(reserve));
2977d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        }
2987d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        // GB: 2048,3072,4096,6144,7168,8192
2997d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        // HC: 8192,10240,12288,14336,16384,20480
3007d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    }
3017d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
3022286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    public static int computeEmptyProcessLimit(int totalProcessLimit) {
3032286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn        return (totalProcessLimit*2)/3;
3042286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn    }
3052286cdc0cab77e61b75e6fe9a45b91f6e57cd46dDianne Hackborn
3068e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    private static String buildOomTag(String prefix, String space, int val, int base) {
3078e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        if (val == base) {
3088e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            if (space == null) return prefix;
3098e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return prefix + "  ";
3108e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        }
3118e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        return prefix + "+" + Integer.toString(val-base);
3128e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    }
3138e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn
3148e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    public static String makeOomAdjString(int setAdj) {
3158e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        if (setAdj >= ProcessList.CACHED_APP_MIN_ADJ) {
3168e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("cch", "  ", setAdj, ProcessList.CACHED_APP_MIN_ADJ);
3178e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.SERVICE_B_ADJ) {
3188e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("svcb ", null, setAdj, ProcessList.SERVICE_B_ADJ);
3198e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.PREVIOUS_APP_ADJ) {
3208e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("prev ", null, setAdj, ProcessList.PREVIOUS_APP_ADJ);
3218e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.HOME_APP_ADJ) {
3228e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("home ", null, setAdj, ProcessList.HOME_APP_ADJ);
3238e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.SERVICE_ADJ) {
3248e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("svc  ", null, setAdj, ProcessList.SERVICE_ADJ);
3258e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) {
3268e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("hvy  ", null, setAdj, ProcessList.HEAVY_WEIGHT_APP_ADJ);
3278e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.BACKUP_APP_ADJ) {
3288e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("bkup ", null, setAdj, ProcessList.BACKUP_APP_ADJ);
3298e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.PERCEPTIBLE_APP_ADJ) {
3308e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("prcp ", null, setAdj, ProcessList.PERCEPTIBLE_APP_ADJ);
3318e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.VISIBLE_APP_ADJ) {
3328e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("vis  ", null, setAdj, ProcessList.VISIBLE_APP_ADJ);
3338e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.FOREGROUND_APP_ADJ) {
3348e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("fore ", null, setAdj, ProcessList.FOREGROUND_APP_ADJ);
3358e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.PERSISTENT_PROC_ADJ) {
3368e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("pers ", null, setAdj, ProcessList.PERSISTENT_PROC_ADJ);
3378e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.SYSTEM_ADJ) {
3388e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("sys  ", null, setAdj, ProcessList.SYSTEM_ADJ);
3398e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else if (setAdj >= ProcessList.NATIVE_ADJ) {
3408e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return buildOomTag("ntv  ", null, setAdj, ProcessList.NATIVE_ADJ);
3418e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        } else {
3428e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn            return Integer.toString(setAdj);
3438e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn        }
3448e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn    }
3458e69257a9c7e9c1781e1f53d8856358ada38921dDianne Hackborn
3463bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    public static String makeProcStateString(int curProcState) {
3473bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        String procState;
3483bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        switch (curProcState) {
3493bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case -1:
3503bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "N ";
3513bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3523bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_PERSISTENT:
3533bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "P ";
3543bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3553bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_PERSISTENT_UI:
3563bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "PU";
3573bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3583bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_TOP:
3593bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "T ";
3603bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3613bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND:
3623bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "IF";
3633bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3643bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND:
3653bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "IB";
3663bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3673bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_BACKUP:
3683bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "BU";
3693bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3703bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_HEAVY_WEIGHT:
3713bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "HW";
3723bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3733bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_SERVICE:
3743bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "S ";
3753bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3763bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_RECEIVER:
3773bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "R ";
3783bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3793bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_HOME:
3803bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "HO";
3813bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3823bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_LAST_ACTIVITY:
3833bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "LA";
3843bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3853bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY:
3863bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "CA";
3873bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3883bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT:
3893bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "Ca";
3903bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3913bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            case ActivityManager.PROCESS_STATE_CACHED_EMPTY:
3923bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "CE";
3933bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3943bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            default:
3953bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                procState = "??";
3963bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                break;
3973bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        }
3983bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        return procState;
3993bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    }
4003bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
4013bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    public static void appendRamKb(StringBuilder sb, long ramKb) {
4023bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        for (int j=0, fact=10; j<6; j++, fact*=10) {
4033bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            if (ramKb < fact) {
4043bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn                sb.append(' ');
4053bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn            }
4063bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        }
4073bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        sb.append(ramKb);
4083bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    }
4093bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
410f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The minimum amount of time after a state change it is safe ro collect PSS.
411f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PSS_MIN_TIME_FROM_STATE_CHANGE = 15*1000;
412f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
413f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The maximum amount of time we want to go between PSS collections.
414f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PSS_MAX_INTERVAL = 30*60*1000;
415f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
416f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The minimum amount of time between successive PSS requests for *all* processes.
417f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PSS_ALL_INTERVAL = 10*60*1000;
418f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
419f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The minimum amount of time between successive PSS requests for a process.
420f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final int PSS_SHORT_INTERVAL = 2*60*1000;
421f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
422f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The amount of time until PSS when a process first becomes top.
4233bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    private static final int PSS_FIRST_TOP_INTERVAL = 10*1000;
4243bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
4253bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    // The amount of time until PSS when a process first goes into the background.
4263bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    private static final int PSS_FIRST_BACKGROUND_INTERVAL = 20*1000;
427f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
428f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The amount of time until PSS when a process first becomes cached.
4293bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    private static final int PSS_FIRST_CACHED_INTERVAL = 30*1000;
430f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
431f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The amount of time until PSS when an important process stays in the same state.
432f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final int PSS_SAME_IMPORTANT_INTERVAL = 15*60*1000;
433f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
434f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The amount of time until PSS when a service process stays in the same state.
435f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final int PSS_SAME_SERVICE_INTERVAL = 20*60*1000;
436f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
437f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    // The amount of time until PSS when a cached process stays in the same state.
438f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final int PSS_SAME_CACHED_INTERVAL = 30*60*1000;
439f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
440f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PROC_MEM_PERSISTENT = 0;
441f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PROC_MEM_TOP = 1;
442f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PROC_MEM_IMPORTANT = 2;
443f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PROC_MEM_SERVICE = 3;
444f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static final int PROC_MEM_CACHED = 4;
445f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
446f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final int[] sProcStateToProcMem = new int[] {
447f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_PERSISTENT,            // ActivityManager.PROCESS_STATE_PERSISTENT
448f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_PERSISTENT,            // ActivityManager.PROCESS_STATE_PERSISTENT_UI
449f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_TOP,                   // ActivityManager.PROCESS_STATE_TOP
450f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_IMPORTANT,             // ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND
451f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_IMPORTANT,             // ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
452f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_IMPORTANT,             // ActivityManager.PROCESS_STATE_BACKUP
453f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_IMPORTANT,             // ActivityManager.PROCESS_STATE_HEAVY_WEIGHT
454f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_SERVICE,               // ActivityManager.PROCESS_STATE_SERVICE
455f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_RECEIVER
456f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_HOME
457f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_LAST_ACTIVITY
458f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY
459f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT
460f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PROC_MEM_CACHED,                // ActivityManager.PROCESS_STATE_CACHED_EMPTY
461f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    };
462f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
463f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final long[] sFirstAwakePssTimes = new long[] {
464f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SHORT_INTERVAL,             // ActivityManager.PROCESS_STATE_PERSISTENT
465f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SHORT_INTERVAL,             // ActivityManager.PROCESS_STATE_PERSISTENT_UI
466f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_TOP_INTERVAL,         // ActivityManager.PROCESS_STATE_TOP
4673bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_BACKGROUND_INTERVAL,  // ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND
4683bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_BACKGROUND_INTERVAL,  // ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
4693bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_BACKGROUND_INTERVAL,  // ActivityManager.PROCESS_STATE_BACKUP
4703bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_BACKGROUND_INTERVAL,  // ActivityManager.PROCESS_STATE_HEAVY_WEIGHT
4713bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_BACKGROUND_INTERVAL,  // ActivityManager.PROCESS_STATE_SERVICE
4723bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_RECEIVER
473f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_HOME
474f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_LAST_ACTIVITY
475f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY
476f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT
477f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_FIRST_CACHED_INTERVAL,      // ActivityManager.PROCESS_STATE_CACHED_EMPTY
478f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    };
479f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
480f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    private static final long[] sSameAwakePssTimes = new long[] {
481f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_PERSISTENT
482f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_PERSISTENT_UI
483f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SHORT_INTERVAL,             // ActivityManager.PROCESS_STATE_TOP
484f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND
485f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND
486f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_BACKUP
487f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_IMPORTANT_INTERVAL,    // ActivityManager.PROCESS_STATE_HEAVY_WEIGHT
488f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_SERVICE_INTERVAL,      // ActivityManager.PROCESS_STATE_SERVICE
489f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_SERVICE_INTERVAL,      // ActivityManager.PROCESS_STATE_RECEIVER
490f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_CACHED_INTERVAL,       // ActivityManager.PROCESS_STATE_HOME
491f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_CACHED_INTERVAL,       // ActivityManager.PROCESS_STATE_LAST_ACTIVITY
492f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_CACHED_INTERVAL,       // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY
493f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_CACHED_INTERVAL,       // ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT
494f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        PSS_SAME_CACHED_INTERVAL,       // ActivityManager.PROCESS_STATE_CACHED_EMPTY
495f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    };
496f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
497f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static boolean procStatesDifferForMem(int procState1, int procState2) {
498f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        return sProcStateToProcMem[procState1] != sProcStateToProcMem[procState2];
499f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    }
500f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
501f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    public static long computeNextPssTime(int procState, boolean first, boolean sleeping,
502f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn            long now) {
503f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        final long[] table = sleeping
504f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                ? (first
505f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                        ? sFirstAwakePssTimes
506f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                        : sSameAwakePssTimes)
507f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                : (first
508f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                        ? sFirstAwakePssTimes
509f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn                        : sSameAwakePssTimes);
510f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn        return now + table[procState];
511f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn    }
512f1cca18ae460b66242988a8a6204c4a42b6fa1c1Dianne Hackborn
5137d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    long getMemLevel(int adjustment) {
5147d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        for (int i=0; i<mOomAdj.length; i++) {
5157d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            if (adjustment <= mOomAdj[i]) {
5167d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn                return mOomMinFree[i] * 1024;
5177d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            }
5187d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        }
5197d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        return mOomMinFree[mOomAdj.length-1] * 1024;
5207d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    }
5217d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn
522bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    /**
5233bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn     * Return the maximum pss size in kb that we consider a process acceptable to
5243bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn     * restore from its cached state for running in the background when RAM is low.
5253bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn     */
526cbd9a52f256087426feb19ac6e51eff772e81375Dianne Hackborn    long getCachedRestoreThresholdKb() {
5273bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn        return mCachedRestoreLevel;
5283bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn    }
5293bc8f78d7a3d23a67c06221cc41292d04a2fd439Dianne Hackborn
5309bef5b67dc48568e6f8be065dd7016f04058351cDianne Hackborn    /**
531bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     * Set the out-of-memory badness adjustment for a process.
532bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     *
533bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     * @param pid The process identifier to set.
534d908edd810dd22d8ec512a19c32637df464e9d0aColin Cross     * @param uid The uid of the app
535bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     * @param amt Adjustment value -- lmkd allows -16 to +15.
536bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     *
537bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     * {@hide}
538bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     */
539d908edd810dd22d8ec512a19c32637df464e9d0aColin Cross    public static final void setOomAdj(int pid, int uid, int amt) {
540bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        if (amt == UNKNOWN_ADJ)
541bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            return;
542bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
543ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn        long start = SystemClock.elapsedRealtime();
544d908edd810dd22d8ec512a19c32637df464e9d0aColin Cross        ByteBuffer buf = ByteBuffer.allocate(4 * 4);
545bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        buf.putInt(LMK_PROCPRIO);
546bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        buf.putInt(pid);
547d908edd810dd22d8ec512a19c32637df464e9d0aColin Cross        buf.putInt(uid);
548bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        buf.putInt(amt);
549bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        writeLmkd(buf);
550ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn        long now = SystemClock.elapsedRealtime();
551ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn        if ((now-start) > 250) {
552ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn            Slog.w("ActivityManager", "SLOW OOM ADJ: " + (now-start) + "ms for pid " + pid
553ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn                    + " = " + amt);
554ecf1cda068c95c58d296d508d34706d659e4a1aeDianne Hackborn        }
555bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    }
556bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
557bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    /*
558bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     * {@hide}
559bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor     */
560bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    public static final void remove(int pid) {
561bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        ByteBuffer buf = ByteBuffer.allocate(4 * 2);
562bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        buf.putInt(LMK_PROCREMOVE);
563bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        buf.putInt(pid);
564bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        writeLmkd(buf);
565bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    }
566bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
567bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private static boolean openLmkdSocket() {
5687d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        try {
569bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            sLmkdSocket = new LocalSocket(LocalSocket.SOCKET_SEQPACKET);
570bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            sLmkdSocket.connect(
571bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                new LocalSocketAddress("lmkd",
572bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                        LocalSocketAddress.Namespace.RESERVED));
573bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            sLmkdOutputStream = sLmkdSocket.getOutputStream();
574bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        } catch (IOException ex) {
575bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            Slog.w(ActivityManagerService.TAG,
576bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                   "lowmemorykiller daemon socket open failed");
577bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            sLmkdSocket = null;
578bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            return false;
579bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        }
580bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
581bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        return true;
582bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    }
583bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
584bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor    private static void writeLmkd(ByteBuffer buf) {
585bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
586bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor        for (int i = 0; i < 3; i++) {
587bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            if (sLmkdSocket == null) {
588bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                    if (openLmkdSocket() == false) {
589bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                        try {
590bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                            Thread.sleep(1000);
591bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                        } catch (InterruptedException ie) {
592bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                        }
593bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                        continue;
594bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                    }
595bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            }
596bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
597bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            try {
598bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                sLmkdOutputStream.write(buf.array(), 0, buf.position());
599bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                return;
600bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor            } catch (IOException ex) {
601bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                Slog.w(ActivityManagerService.TAG,
602bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                       "Error writing to lowmemorykiller socket");
603bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
6047d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn                try {
605bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                    sLmkdSocket.close();
606bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                } catch (IOException ex2) {
6077d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn                }
608bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor
609bfdd62323e7b3bb724c98730e4143afa3e4d9cb5Todd Poynor                sLmkdSocket = null;
6107d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn            }
6117d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn        }
6127d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn    }
6137d608423b721e0153f37bfd5eba78fcd2489562dDianne Hackborn}
614