Android가 너무 자주 버전업이 되면서 내부적으로도 많은 부분이 너무 자주 바뀌는것 같아요..
주 업무가 안드로이드 단말 테스팅 툴 개발이라 이럴때마다 일 하기 싫어집니다.ㅠㅠ
2.1/2.2 버전은 화면에 UI를 그리고 있는 Activity/Service에 한해서는 OOM Killer를 피해갈 수 있었는데, 2.3 버전 부터 화면에 UI를 그리고 있어도 OS가 판단하기에 정리대상이라고 생각되면 OOM Killer에 의해서 프로세스가 킬 됩니다.
안드로이드의 OOM Killer(Out-Of-Memory Killer)는 기본적으로 Linux의 OOM Killer와 같은 컨셉입니다.
그렇다면 OOM Killer을 피해 갈 수 있는 방법은 무엇인가?
OOM Killer을 피해갈수 있는 방법은 zygote(app_process)로 실행시키는 프로그램이거나 시스템 프로세서로 개발하면 됩니다.
그렇다고 android framework위에 돌아가면서 activity <- (IPC) -> service 를 zygote, 시스템 프로세서로 개발하기엔 수고가 필요합니다.
(단말 제조사가 아니라면 양산폰에 올리기 위해선 이 방법으로 개발 해야합니다. 물론 루팅도 필수..)
그래서 가장 간단한 방법으로 android framework source를 일부 수정 하는 부분입니다.
(이 문제의 문제점은 단말 제조사가 아니라면 양산 단말에 포팅 할 수가 없습니다)
Android Activity Service의 코드를 보면 oom_adj 값을 내부적으로 관리하도록 되어 있습니다.
따라서 /proc/<pid>/oom_adj 값을 수정해도 OOM Killer에 의해서 종료가 될 수 있습니다.
private final int computeOomAdjLocked(ProcessRecord app, int hiddenAdj, ProcessRecord TOP_APP, boolean recursed) { .... // Determine the importance of the process, starting with most // important to least, and assign an appropriate OOM adjustment. int adj; int schedGroup; int N; /* added by idccc - start */ if(app.processName.indexOf("com.idccc.qm") != -1) { adj = SYSTEM_ADJ; schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; app.adjType = "home"; } else /* added by idccc - end */ if (app == TOP_APP) { // The last app on the list is the foreground app. adj = FOREGROUND_APP_ADJ; schedGroup = Process.THREAD_GROUP_DEFAULT; app.adjType = "top-activity"; } else if (app.instrumentationClass != null) { .... }
다음과 같이 oom_adj 값을 관리하는 메서드에서 OOM Killer 을 회피하고 싶은 프로세스를 이름을 기반하여 강제로 값을 셋팅 할 수 있습니다.
잘 동작하는지 확인은 풀 소스를 빌드하시고 만들어진 이미지를 가지고 예뮬레이터를 띄워서 확인 하시면 됩니다.
근데 고수님들은 저 처럼 허접하게 풀 소스 안고치고 하실 방법이 있을것 같은데…
[OOM Killer 참고 자료]
http://wiki.kldp.org/wiki.php/AndroidPortingOnRealTarget
http://barriosstory.blogspot.com/2009/02/taming-oom-killer.html
http://andstudy.springnote.com/pages/3763687
http://andstudy.springnote.com/pages/3667993
http://lwn.net/Articles/317814/
아..글 열심히 썼는데 멜주소 안 적었다고…ㅜㅜ
안녕하세요. 질문이 있는데요. 시간 되시면 답변 좀 부탁드릴게요.
웹서핑 하다가 우연히 위 포스팅을 봤습니다. 지금 이 글이 딱 제가 찾는 해답인 거 같은데 전 전문가가 아니라서 무슨 말인지 모르겠어요.ㅜㅜ
제가 인터넷라됴를 들으면서 웹서핑을 자주 하는데 하다보면 라됴가 자동킬을 당해버립니다. 지금은 아쉬운대로 어플을 통해 라디오의 oom값을 2에서 -17로 바꿔주는데요. 어플을 실행할 때마다 일일이 바꿔줘야 하니까 좀 번거롭습니다.
위 글의 내용을 보면 스크립트 수정을 통해 자동킬을 막을 수 있는 방법처럼 보이네요. 맞나요?
혹시 맞다면 저에게 좀 쉽게 설명 해 주실수 있는지요? 어디 폴더에 어디 파일을 어떻게 수정해주라고 간단히 설명해 주시면 정말 고맙겠습니다.
부탁드릴게요. 수고하세요.
안드로이드 폰 유저 분이시면 지금 쓰고 계신방법으로 사용하셔야 해요..
루팅 안된 폰일 경우 /proc 이하에 값을 셋팅 할 수가 없습니다.
만약 플랫폼 개발자 분이시라면 풀소스에 포함된 jgrep alias로 computeOomAdjLocked 메서드를 검색 하시면 수정해야 할 파일/라인을 쉽게 찾으실 수 있을겁니다-