<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-1518098013643077976</id><updated>2011-12-16T12:30:20.035+09:00</updated><category term='linux kernel'/><category term='Redhat'/><category term='Samsung'/><category term='눈'/><category term='Guitar'/><title type='text'>barrios kernel story</title><subtitle type='html'></subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>95</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5095628218864602878</id><published>2011-09-15T23:44:00.000+09:00</published><updated>2011-09-15T23:44:20.436+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Samsung'/><category scheme='http://www.blogger.com/atom/ns#' term='Redhat'/><title type='text'>정든 회사를 떠나며</title><content type='html'>오늘은 삼성에서의 마지막 날이었다.&lt;br /&gt;마지막 날은 평소보다 더 분주한 하루였다.&lt;br /&gt;갑작스런 퇴직일자 결정과 추석 연휴등으로 인하여, &lt;br /&gt;제대로된 인사도 드리지 못하고 나오게 되어 아쉬운 마음이 크다.&lt;br /&gt;그 동안 사용했던 장비들을 정리하고, 항상 뒷주머니에 꼽아 놓고 다니던 &lt;br /&gt;값비싸고 무거운 사원증을 반납하고, Gate를 빠져 나오는 기분이 좋지 않다.&lt;br /&gt;&lt;br /&gt;삼성에 입사한 것은 2006년이었다. 난 그곳에서 Linux를 알게 되었으며,&lt;br /&gt;상당히 일을 즐기는 편에 속했다고 생각한다. 다양한 사업부를 이동하며,&lt;br /&gt;다양한 경험들을 했으며, 훌륭한 많은 동료들을 만났다.&lt;br /&gt;그들이 많이 그리울 것이다. 그래도 다행스러운 것은 주위 동료들이 오픈소스에&lt;br /&gt;대해 보다 적극적인 호의를 가지는 모습들을 최근 많이 볼수 있었다는 것이다.&lt;br /&gt;조만간 그들을 메일링 리스트에서 볼수 있을 것이라 기대하며 그들과의 그곳에서의&lt;br /&gt;조우는 색다른 느낌일 것으로 기대한다.&lt;br /&gt;&lt;br /&gt;다음달부터는 Redhat에서 KVM 관련하여 Linux kernel 일을 하게 된다.&lt;br /&gt;그러므로 kernel 일을 한다는 것은 예전이나 지금이나 큰 변화는 없다.&lt;br /&gt;또 다른 훌륭한 동료들과 재밌는 일들이 나를 기다리고 있다는 것에 난 지금&lt;br /&gt;매우 흥분되는 반면, 여유있게 커피한잔하며 소소한 얘기들을 나눌 동료가 없다는&lt;br /&gt;것이 매우 아쉽기도 하다. 얻는 것이 있으면 잃는 것도 있다고 하지 않던가.&lt;br /&gt;&lt;br /&gt;여러 감정들이 교차하는 하루였다. 하지만 확실한 것 하나는 난 바른 길을&lt;br /&gt;가고 있다고 믿고 있다는 것.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5095628218864602878?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5095628218864602878/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5095628218864602878&amp;isPopup=true' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5095628218864602878'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5095628218864602878'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2011/09/blog-post.html' title='정든 회사를 떠나며'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2290068004120340553</id><published>2011-02-08T23:40:00.000+09:00</published><updated>2011-02-08T23:40:32.381+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>오랜만의 포스팅</title><content type='html'>블로깅은 정말 오랜만이다.&lt;br /&gt;블로깅을 잘 못하게 된 시점이 공교롭게 일하는 곳을 옮긴지 얼마되지 않은 시점으로&lt;br /&gt;몇몇분들은 예상되로 리눅스와 영원히 안녕하게 된 것이 아니냐고 묻는 분도 계셨다. :)&lt;br /&gt;결코 그렇지는 않다. 일하는 곳이 워낙에 유별난 곳이라 뭔가를 떠든다는 것이 조심스러운 것은&lt;br /&gt;사실이지만. &lt;br /&gt;&lt;br /&gt;사실 블로깅을 잘 못하기 시작한 시기는 필연적으로 아들이 제대로 뛰기 시작하며 엄마를&lt;br /&gt;괴롭히기 시작하는 시점과 일치한다. 여느 평범한 가정의 가장이 그러하듯이 barrios 또한&lt;br /&gt;일찍 퇴근하여 아들과 놀아주지 않고 컴퓨터에 앞에 붙어 있게 되면 어디선가 따가운 시선이&lt;br /&gt;간담을 서늘케 하기 때문이다. 잠시 짬을 내서 컴퓨터 앞에 앉으면, 쏜살 같이 달려와 나보다&lt;br /&gt;먼저 컴퓨터 앞에 앉아 키보드와 마우스를 뚜드려 대는 아들녀석 때문에 아들이 잠들기 전까진&lt;br /&gt;아무것도 할 수 없다. 모든 부모들이 이해할만한 시나리오이다. (지금도 1시간 여만에 재우고&lt;br /&gt;나와 블로깅을 한다. :( )&lt;br /&gt;&lt;br /&gt;그러므로 어쩔 수 없이 나의 여가시간의 재분배가 필요했다. &lt;br /&gt;즉, 다소 블로깅은 우선순위가 낮은 task였다. 무엇보다 우선순위가 낮아진 시간은 독서이다.&lt;br /&gt;거의 1년간 어떤 서적도 보지 못했다. "1년에 책 1권도 안 읽는다" 성인 35%에 들어가 버리고 &lt;br /&gt;만 것이다. 내가 이런소리를 하면 주윗 분들이 "평소에 그렇게 책을 많이 읽었어?" 하실지도 몰라서&lt;br /&gt;첨언한다. barrios가 주로 읽는 서적들은 전공서적들이었다. 교양없는 barrios :(&lt;br /&gt;언제나 그렇듯 연초 계획은 책을 좀 보자라고 하고 싶었는데, 올 해는 것 보다는 책을 좀 쓰자로&lt;br /&gt;바뀌었었는데 역시나 오래가지 허덕이고 있다. 쓰고 싶은 책도 역시나 전공에 관한 것이다. :)&lt;br /&gt;사실, barrios는 몇 년전부터 많은 시도들을 했었다. 알고 있는 내용들을 어떻게 정리를 해야 &lt;br /&gt;잘 하는 것인지. 다양한 툴과 형식을 사용하여 시도해보았다. &lt;br /&gt;Wiki, MS office, excel, flow chart, springnote, google doc, latex&lt;br /&gt;결국 남은 건 많은 문서들이 여러가지 형태로 파편화되어 있고 다양한 형태로 정리되어 있다.&lt;br /&gt;그래도 가장 좋았던 것은 wiki였다. 아직도 이 고민은 진행형이다. 어떤 형태로 지식을 정리해야&lt;br /&gt;효율적으로 정리할 수 있을지는.. 좋은 아이디어를 가지고 계신분들의 많은 조언 좀...&lt;br /&gt;&lt;br /&gt;블로깅은 사실 몇번 시도를 했었다. 하지만 publish하지 못했다. 다소 감정적인 것들이 많았기&lt;br /&gt;때문이다. 지금 여기 이곳에 draft 형태로 남아 있는 글들이 서너개 되는 것 같다. 예전과 같이&lt;br /&gt;주로 술을 먹고 썼던 글들인데 요즘은 술에 취하면 피곤해서 자기 바쁘다. 모두 아들 덕택이다.&lt;br /&gt;기술적인 내용들은 블로깅보다는 위에서 얘기했던 다양한 곳에 writing을 했었는데 지금 쳐다도&lt;br /&gt;보지 않는 글이 되어버렸다. &lt;br /&gt;&lt;br /&gt;그 동안 Linux VM에도 재밌는 일들이 많이 있었다. 그런 일들을 그때 그때 공유하지 못해&lt;br /&gt;아쉬움이 남지만 현재 여건상 어찌하기 어렵다.(예전에 회사에 처음 입사 하였을 때는 한달에 &lt;br /&gt;한번씩 커널의 새로운 기능들을 소개하는 newspaper를 만들어 배포한적이 있었다.&lt;br /&gt;그런 일을 하자고 제안했던 분이나 그러한 일을 할 수 있게 허락하신 분 또한 &lt;br /&gt;요즘 생각하면 대단한 용기라고 생각한다. 당장의 이익을 위해서가 아닌..) &lt;br /&gt;여하튼 올 한해는 다시 블로깅을 다시 활성화 해보려고 한다. 혹시나 아직 이곳을 찾고 계신 분들이&lt;br /&gt;계시다면 화이팅 좀 부탁. :)&lt;br /&gt;&lt;br /&gt;최근, 올해 LSF/MM summit의 초청장을 받았다. 그 summit은 Linux kernel의 Storage, File system,&lt;br /&gt;Memory management의 개발자들이 참여하여 Linux의 현안과 향후 발전방향, 개발계획등에&lt;br /&gt;논의하는 exclusive, invitation-only summit이다. 원래는 Storage와 File system 개발자들이 함께하고&lt;br /&gt;Memory management는 또 따로 summit을 해왔었는데, file system과 VM의 dependency가 커지며 함께&lt;br /&gt;cross-session을 갖자는 목소리가 나와 작년부터 함께 열리기 시작했다. &lt;br /&gt;대부분의 core 개발자들이 paid developer로 Linux 관련 회사에서 일하는 사람들이 대부분이고, 그들은 &lt;br /&gt;당장 자신의 회사 이익을 위해 Linux kernel에 기능들을 구현해야 하는 입장이기 때문에 다양한 재밌는&lt;br /&gt;안건들을 가지고 있다. 이번 summit에서는 주로 memcg 얘기가 될 것으로 보인다. memcg안에는 또 다양한&lt;br /&gt;subtopic들이 있다. 또한 최근 barrios의 관심을 끌고 있는 IO throttling 또한 얘기가 될 것으로 보인다. &lt;br /&gt;아쉬운 것은 최근 barrios가 storage/file system session에서 의견 교환하고 싶은 부분들이 &lt;br /&gt;많이 있는데 개인적으로 아직 지식이 충분치 않아 얘기를 꺼내는 것이 쉽지 않다는 것이다. summit 자체가&lt;br /&gt;core developer들이 모이는 자리이기 때문에 섣부른 지식으로 공개석상에서 이렇다 저렇다 얘기하기가&lt;br /&gt;힘들 것 같기 때문이다. 내년 이맘때쯤은 barrios가 memory management 뿐만이 아니라 storage 쪽에도 &lt;br /&gt;활발한 활동을 하고 있기를 희망한다. 하지만 가난한 barrios에게 가장 중요한 것은 travel budget이다.&lt;br /&gt;과연 회사가 나를 그곳에 보내줄 것이냐이다. 잘 아는 것 처럼 barrios가 일하는 곳은 Open Source와 &lt;br /&gt;정반대 위치하고 있으며, Host에서 모 하는 것을 결코 좋아하지 않는 곳이다.(firmware로 대동단결)&lt;br /&gt;이런 곳에서 그러한 summit의 가치를 설명하기는 쉽지 않은 일이 될 것으로 보인다. 혹시나 가난한 &lt;br /&gt;barrios의 travel budget을 해결해줄 고마운 sponsor가 있다면 소개부탁드린다. Sponsor에게 돌아가는&lt;br /&gt;것이 모냐고 물으신다면.... 음.... 다녀와서 재밌는 얘기들을 해드리겠다고... 정도. 기념품도 &lt;br /&gt;사다드리겠다고.. 펭귄 박힌 T 셔츠로.&lt;br /&gt;&lt;br /&gt;언제나 그렇듯 머릿속에 생각나는 것들을 두서없이 나열하는 형태의 블로깅과 퇴고없는 글은 읽는이로 하여금&lt;br /&gt;짜증을 유도할 수 있으나, 올 한해도 간곡히 이해부탁드린다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2290068004120340553?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2290068004120340553/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2290068004120340553&amp;isPopup=true' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2290068004120340553'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2290068004120340553'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2011/02/blog-post.html' title='오랜만의 포스팅'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4835036666534422053</id><published>2010-06-13T01:57:00.002+09:00</published><updated>2010-06-13T01:59:26.069+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>OOM killer Internal</title><content type='html'>최근 몇달간 OOM killer를 향상시키기 위한 많은 논의들이 있었다.&lt;br /&gt;그 시작은 fork-bomb를 detect하는 것에서 시작하였으나, David는 OOM전체의&lt;br /&gt;개선으로 긴 여정을 시작하였다. &lt;br /&gt;&lt;br /&gt;현재 mmotm 2010-06-11-16-40에 merge되었다. 이 패치를 Andrew가 받아들이기&lt;br /&gt;전까지 정말 많은 우여곡절이 있었다. 휴.. 얘기하자면 정말 재밌는데 온라인에서 &lt;br /&gt;글로 설명하기에는 한계가 있다. 이런 재밌는 얘기는 맥주한잔하며 재밌는 일화정도로&lt;br /&gt;얘기하면 딱이다.&lt;br /&gt;&lt;br /&gt;사실 이 패치들에 대해서 글을 쓰려고 하였으나, 최근 많은 분들이 OOM의 &lt;br /&gt;동작과정에 대해서 궁금해 하는 것 같아 OOM의 동작과정에 대해서 간단히 정리해 보았다. &lt;br /&gt;&lt;br /&gt;워낙에 글솜씨가 없는 편에다 코드를 설명해야 하는 것은 말이든 글이든 더욱 소질이 없지만&lt;br /&gt;이 별볼일 없는 설명이 도움이 되었으면 한다. &lt;br /&gt;&lt;br /&gt;하지만 알아두어야 할 부분은 아래의 내용 중 일부는 곧 바뀌게 될 것이라는 것이다.&lt;br /&gt;&lt;br /&gt;---&lt;br /&gt;&lt;br /&gt;우선 OOM killer가 언제 호출되는지 살펴보도록 하자.&lt;br /&gt;&lt;br /&gt;1. mm_fault_error&lt;br /&gt;2. moom_callbak&lt;br /&gt;3. __alloc_pages_may_oom&lt;br /&gt;&lt;br /&gt;mm_fault_error가 호출되는 시점은 system의 page fault handler가 &lt;br /&gt;호출되어 fault를 처리하는 도중 필요한 메모리를 할당하지 못하고 반환되는 &lt;br /&gt;경우 호출된다.  일반적으로는 페이지를 할당하는 함수내에서 먼저 OOM killer가 &lt;br /&gt;동작하여 페이지를 회수하지만 그렇지 못할 경우 error는 page fault handler에게&lt;br /&gt;까지 propagate되어 결국 mm_fault_error가 호출되어 OOM kill을 하게 된다.&lt;br /&gt;&lt;br /&gt;이렇게 호출되는 out_of_memory는 다른 두 곳에서 호출되는 out_of_memory함수와는 &lt;br /&gt;다르다. 다른 out_of_memory 함수들은 out of memory 상황이 발생된 context를 &lt;br /&gt;알수 있는 반면 page fault handler를 통해 호출되는 out_of_memory에서는 알수 없다. &lt;br /&gt;&lt;br /&gt;out of memory의 자세한 동작에 관해서는 3번 __alloc_pages_may_oom을 통해서 &lt;br /&gt;호출되는 경우를 통해 자세히 살펴보도록 하자.&lt;br /&gt;&lt;br /&gt;Linux의 page allocator의 page 할당 실패는 우선 kswapd를 깨워 &lt;br /&gt;background reclaim을 하게 된다. 그래도 필요한 페이지 할당에 실패할 경우 &lt;br /&gt;direct reclaim을 하게 된다. direct reclaim을 한후마저 어떤 페이지도 회수하지 &lt;br /&gt;못하는 경우 __alloc_pages_may_oom을 호출하게 된다.&lt;br /&gt;&lt;br /&gt;__alloc_pages_may_oom 함수는 zonelist의 OOM lock을 hold 시도한다.&lt;br /&gt;zonelist란 현재 할당을 요구한 zone이하의 모든 zone을 의미한다. 모든 zone에서 &lt;br /&gt;OOM이 발생하지 않고있는 경우 OOM lock의 hold 시도는 성공하게 되지만 어느 한 zone이라도 &lt;br /&gt;이미 OOM killer가 동작하고 있는 경우라면 OOM lock hold에 실패하게 되며 더 진행하지 &lt;br /&gt;못하게 된다.&lt;br /&gt;&lt;br /&gt;OOM lock을 획득한 경우 out_of_memory 함수를 호출하게 된다.&lt;br /&gt;이 함수는 우선 constrained_alloc을 호출하여 현재 할당 요청에 constrain이 &lt;br /&gt;있었는지 파악한다. constrin은 2가지 경우가 있다.&lt;br /&gt;&lt;br /&gt;1. MPOL_BIND와 같은 memory policy 때문에 발생한 경우&lt;br /&gt;2. CPUSET의 softwall에 의해 발생한 경우&lt;br /&gt;&lt;br /&gt;1에 의해 OOM이 발생한 경우는 oom_kill_process를 호출하고 current를 kill하게 된다.&lt;br /&gt;이 함수는 추후 살펴보기로 한다.&lt;br /&gt;2의 경우나 constrain이 없는 일반적인 경우 __out_of_memory 함수를 호출하게 된다.&lt;br /&gt;&lt;br /&gt;__out_of_memory 함수는 우선 victim process를 찾기 위해 select_bad_process를 호출한다.&lt;br /&gt;우선 victim의 대상은 시스템 전체의 process들이다. 하지만 kernel thread와 &lt;br /&gt;init process는 대상에서 제외된다.&lt;br /&gt;&lt;br /&gt;또한 victim을 찾기위해 process들을 scanning하는 과정에서 이미 reserved memory를 &lt;br /&gt;사용하도록 허락된 process를 만나게 되면 scanning을 종료하고 반환한다. &lt;br /&gt;TIF_MEMDIE가 process의 그러한 status를 나타내기 위해 사용되는데 이 flag가 지정된 경우 &lt;br /&gt;process가 종료하고 있는 과정에 있고 종료를 하기 전 까지(즉, KILL signal을 처리하기 전까지) &lt;br /&gt;하던 작업을 마무리 하기 위해 dynamic memory가 필요할 수 있기 때문에 reserved memory를&lt;br /&gt;사용하도록 허락한 것이다. 그러므로 다른 task 들에게도 reserved memory 사용하도록 허락하게 &lt;br /&gt;되면 앞의 task가 종료하기 위한 메모리가 모자라 livelock 상황에 처할 수도 있게 된다.&lt;br /&gt;&lt;br /&gt;또 다른 exception case로 task의 flag가 PF_EXITING인 경우가 있다.&lt;br /&gt;PF_EXITING의 flag가 지정된 task는 종료처리를 하고 있는 과정임을 의미한다.&lt;br /&gt;이 flag과 TIF_MEMDIE와의 다른 점은 TIF_MEMDIE는 kill signal을 보냈고 task의 &lt;br /&gt;빠른 종료를 위해 reserved memory를 사용해도 좋다는 것을 의미하는 반면 PF_EXITING은 &lt;br /&gt;kill signal을 처리해서 현재 do_exit 함수를 실행하고 있다는 것을 의미한다. &lt;br /&gt;즉 PF_EXITING이 지정된 task가 실제 종료되고 있는 task이다. 이런 task를 만났을 경우, &lt;br /&gt;그리고 그 task가 current가 아닌 경우 앞의 경우와 마찬가지로 무고한 task를 kill하지 &lt;br /&gt;않고 함수는 즉시 반환한다. 즉 무고한 다른 프로세스를 kill하지 않고 조금 기다리겠다는 것이다. &lt;br /&gt;반면 current인 경우 한시라도 빨리 죽기를 희망하여 TIF_MEMDIE를 지정해주기 위해 &lt;br /&gt;그 task를 victim으로 선정한다. (reserved memory를 사용할 수 있게 해주기 위해서이다.)&lt;br /&gt;&lt;br /&gt;위의 exception case에 걸리지 않는 일반적인 task들은 badness 함수를 호출하여 task의 &lt;br /&gt;oom point를 계산하게 된다.&lt;br /&gt;&lt;br /&gt;badness 함수의 목적은 victim 프로세스를 최대한 다음과 같은 rule에 맞게 결정하기 &lt;br /&gt;위해 힘쓴다.&lt;br /&gt;&lt;br /&gt;1. 최소한의 양의 일만을 잃을 것&lt;br /&gt;2. 많은 memory를 회수할 것&lt;br /&gt;3. 메모리를 많이 소비하는 task중에 죄없는 프로세스는 죽이지 말것&lt;br /&gt;(즉, memory leak을 하고 있는 프로세스를 죽이자는 것이다.)&lt;br /&gt;4. 최소한의 프로세스만 죽일 것&lt;br /&gt;(되도록 한 프로세스만을 kill해서 시스템을 위급 상황에서 벗어나도록 하자는 것이다.)&lt;br /&gt;5. 사용자가 죽길 원하는 프로세스를 죽이려고 노력할 것&lt;br /&gt;&lt;br /&gt;우선 task가 OOM_DISABLE로 설정되어 있다면 score는 0이다. &lt;br /&gt;즉, kill되지 않는다는 것이다.이는 oom_adj를 통해 설정할 수 있다. &lt;br /&gt;자세한 것은  Documentation/filesystems/proc.txt 파일을 참조하라.&lt;br /&gt;&lt;br /&gt;OOM_DISABLE이 되어 있지 않은 프로세스는 badness score를 계산히기 위해 &lt;br /&gt;total_vm의 크기를 base로 삼는다.p-&gt;flags가 PF_OOM_ORIGIN으로 되어있는 &lt;br /&gt;경우 별다른 계산 없이 OOM의 최대 score를 반환한다.&lt;br /&gt;이 flag는 swapoff를 하는 시점이나 KSM을 실행시켰을 때 임의의 task에 &lt;br /&gt;설정될 수 있다. swapoff난 KSM이 실행될 때의 process context는 많은 메모리를 &lt;br /&gt;소모할 수 있기 때문에 그러한 task를 먼저 kill하도록 하는 것이다.&lt;br /&gt;&lt;br /&gt;다음 task의 children 중 현재 task와 mm이 같지 않은 task들(!CLONE_VM)의 &lt;br /&gt;total_vm size의 1/2을 score에 더한다. 즉, 많은 task들을 fork한 fork-bomb를 &lt;br /&gt;detect하기 위함이다. 하지만 1/2을 더하는 이유는 실제로 children 중의 하나가 많은 &lt;br /&gt;메모리를 소모하고 있을 경우 parent보다는 child를 victim이 되게 하기 위해서다.&lt;br /&gt;&lt;br /&gt;다음으로 task와 그 thread 그룹들이 시작된 이후로 얼마나 많은 CPU를 소모했는지에 &lt;br /&gt;따라 point값이 변하게 된다. CPU를 많이 사용했다는 것은 한 일이 많다는 것이다. &lt;br /&gt;즉 1번 rule에 따라 많은 일을 한 프로세스의 score는 낮아진다. 또한 얼마나 오랫동안 &lt;br /&gt;실행되어 왔는지도 영향을 미친다. 오랫동안 실행된 프로세스가 많은 일을 했을 가능성이 높기&lt;br /&gt;때문이다. &lt;br /&gt;&lt;br /&gt;task의 nice가 고려된다. nice한 프로그램은 다른 프로그램보다 score가 배로 높아진다.&lt;br /&gt;task가 superuser process들이라면 point 값은 낮아진다.&lt;br /&gt;&lt;br /&gt;task를 구성하고 있는 쓰레드 그룹들이 OOM이 발생된 current와 같은 CPU_SET group을 &lt;br /&gt;가지고 있지 않다면 point를 낮춘다.&lt;br /&gt;&lt;br /&gt;마지막으로 oom_adj 값을 가지고 지금까지 계산된 points를 가감한다. &lt;br /&gt;oom_adj가 큰 양수일 수록 score 값은 높아지게된다.&lt;br /&gt;&lt;br /&gt;위와 같은 rule에 의해 선정된 victim task는 oom_kill_process 함수를 통해 killing된다.&lt;br /&gt;이 함수는 victim task의 child를 먼저 kill하고 children들이 모두 kill될 수 없는 경우만&lt;br /&gt;parent인 victim task를 kill하게 된다.&lt;br /&gt;&lt;br /&gt;실제 kill을 하는 함수는 oom_kill_task이다.&lt;br /&gt;&lt;br /&gt;이 함수는 __oom_kill_task를 호출하여 SIGKILL을 보내게 된다. &lt;br /&gt;이때 task의 time_slice 값을 HZ로 올려주어&lt;br /&gt;task를 bump up시키며 task가 reserved mempool을 접근할 수 있도록 &lt;br /&gt;TIF_MEMDIE를 지정해준다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4835036666534422053?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4835036666534422053/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4835036666534422053&amp;isPopup=true' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4835036666534422053'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4835036666534422053'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/06/oom-killer-internal.html' title='OOM killer Internal'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4910822503748282440</id><published>2010-06-13T01:22:00.001+09:00</published><updated>2010-06-13T01:23:26.821+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>lowmem_reserve_ratio</title><content type='html'>최근 어떤 개발자로부터 memory fragmentation으로 인한 문제를 들은적이 있다.&lt;br /&gt;음. 많은분들이 lowmem_reserve_ratio에 관해 아직은 잘알지 못하고 있는 것 같아&lt;br /&gt;정리한다. &lt;br /&gt;&lt;br /&gt;일반적으로 1G 이상의 물리 메모리를 갖는 시스템에서 kernel은 동작의 효율을 &lt;br /&gt;위해 high memory 공간을 잘 활용하지 않는다. 왜냐하면 kernel이 highmem공간을&lt;br /&gt;주소로 접근하기 위해서는 kmap/kmap_atomic과 같은 함수를 통해서 page-to-address&lt;br /&gt;변환 작업이 필요하기 때문이다.(user process의 경우에는 문제 되지 않는다.) &lt;br /&gt;그러므로 low memory는 커널이 제일 선호하는 공간이다. &lt;br /&gt;&lt;br /&gt;그렇다면 이런 low memory를 application이 사용하게 되면 무슨 일이 벌어질 수 있을까?&lt;br /&gt;사실, kernel은 application들의 사용을 위해 할당하는 메모리는 high memory를 사용하려고&lt;br /&gt;애쓴다.하지만 high memory의 페이지가 부족할 경우, fallback zones 즉, &lt;br /&gt;NORMAL, DMA32, DMA zone을 사용할 수 밖에 없게 된다. 이때 NORMAL zone에서 &lt;br /&gt;application을 위한 페이지를 할당하게 됐다고 가정할 경우, application이 해당 page를&lt;br /&gt;mlock해버린다면 또는 임베디드 시스템에서와 같이 swap system을 가지고 있지 않을 경우, heap이나&lt;br /&gt;stack을 위한 페이지를 할당하게 된다면 무슨 일이 발생할까?&lt;br /&gt;이것이 의미하는 것은 kernel은 페이지 회수를 할 수 없게 된다는 것을 의미하고 이는&lt;br /&gt;바로 memory fragmentation 문제로 이어지게 된다. &lt;br /&gt;&lt;br /&gt;이러한 현상을 막기 위해 커널은 /proc/sys/vm/lowmem_reserve_ratio 라는 knob을 제공한다.&lt;br /&gt;barrios의 system에서의 lowmem_reserve_ratio는 다음과 같이 출력된다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;#&gt; cat /proc/sys/vm/lowmem_reserve_ratio&lt;br /&gt;256      32       32 &lt;br /&gt;&lt;/blockquote&gt;라고 출력된다. &lt;br /&gt;&lt;br /&gt;이 값은 다음과 같이 사용된다. &lt;br /&gt;&lt;br /&gt;1G RAM을 기준으로 DMA(16M), NORMAL(784M), HIGH(224M)를 쓰게 될 경우라고 가정하고&lt;br /&gt;ZONE_DMA의 경우, ZONE_NORMAL의 target의 fallback으로 memory를 할당하게 될 경우, &lt;br /&gt;784/256의 메모리를 reserve한다. &lt;br /&gt;ZONE_DMA의 경우, ZONE_HIGHMEM의 target의 fallback으로 memory를 할당하게 될 경우,&lt;br /&gt;(224 + 784) / 256의 메모리를 reserve하게 된다.&lt;br /&gt;ZONE_NORMAL의 경우, ZONE_HIGHMEM의 target의 fallback으로 memory를 할당하게 될 경우,&lt;br /&gt;224/32 의 메모리를 reserve하게 된다. &lt;br /&gt;&lt;br /&gt;이것이 어떻게 사용되는지 살펴보자. &lt;br /&gt;&lt;blockquote&gt;#&gt; dmesg | grep zone&lt;br /&gt;...&lt;br /&gt;Normal zone: 221486 pages, LIFO batch:31&lt;br /&gt;....&lt;br /&gt;HighMem zone: 294356 pages, LIFO batch:31&lt;br /&gt;...&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;barrios의 system에는 normal zone이 221486개의 page로 이루어져 있고&lt;br /&gt;high zone이 294356의 page로 이루어져 있음을 볼 수 있다.&lt;br /&gt;그러므로 위의 rule을 적용시켜 보면&lt;br /&gt;&lt;br /&gt;- NORMAL zone을 대신해서 DMA_ZONE이 사용될 경우) &lt;br /&gt;&lt;br /&gt;221486 / 256 = 865 &lt;br /&gt;&lt;br /&gt;- HIGHMEM zone을 대신해서 DMA_ZONE이 사용될 경우&lt;br /&gt;&lt;br /&gt;(221486 + 294356) / 256 = 2015 &lt;br /&gt;&lt;br /&gt;의 메모리가 reserve된다는 것이다. &lt;br /&gt;실제로 아래의 명령을 통해 확인해보자.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;#&gt; cat /proc/zoneinfo | more&lt;br /&gt;...&lt;br /&gt;protection: (0, 865, 2015, 2015)&lt;br /&gt;...&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;위의 계산과 일치하는 것을 볼 수 있다.&lt;br /&gt;마지막 2015는 ZONE_MOVABLE zone을 위한 것인데 지금은 신경쓰지 말자. (얘기할 기회가 있겠지)&lt;br /&gt;&lt;br /&gt;이와 같이 하위 zone은 상위 zone들의 fallback으로 사용될 경우 위와 같은 rule에 의해&lt;br /&gt;page를 reserve하게 된다. &lt;br /&gt;&lt;br /&gt;정리하자면, 커널은 메모리 요구가 발생하였을 경우, 호출자가 선호하는 zone에서 page를 할당하기&lt;br /&gt;위해 노력한다. 하지만 그 요구를 만족시키지 못할 경우 어쩔 수 없이 fallback list에서(ex, 하위 zone들)&lt;br /&gt;에서 페이지 할당을 하게 된다. 이는 자원을 효율적으로 사용한다는 측면에서 나쁘지는 않다. 하지만 각 zone들은&lt;br /&gt;원래의 목적이 있기 마련인데 다른 목적을 위해 페이지가 사용될 경우, 원래의 목적에 페이지가 필요한 경우&lt;br /&gt;페이지가 모자라게 되어 심각한 문제가 발생할 수 있다. 이는 order 0 페이지의 경우에는 덜하지만 &lt;br /&gt;order가 커지면 커질수록 문제가 발생할 확률이 커지게 된다. &lt;br /&gt;&lt;br /&gt;이글이 memory fragmentation으로 인해 문제를 겪는 몇몇 분들에게 도움이 되었으면 한다.&lt;br /&gt;&lt;br /&gt;P.S) 한국:그리스 = 2:0  ^O^&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4910822503748282440?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4910822503748282440/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4910822503748282440&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4910822503748282440'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4910822503748282440'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/06/lowmemreserveratio.html' title='lowmem_reserve_ratio'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-932099499084608471</id><published>2010-04-20T23:52:00.001+09:00</published><updated>2010-04-21T00:01:43.214+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>2010 Linux Foundation Collaboration Summit</title><content type='html'>LWN에 재밌는 기사가 떠서 그냥 넘어갈 수가 없었다. &lt;br /&gt;원문은 subscriber만 볼수 있는 시기이기 때문에 1주가 지나고 나면 link를 걸 예정이다. &lt;br /&gt;&lt;br /&gt;San Francisco에서 열린 &lt;a href="http://events.linuxfoundation.org/events/collaboration-summit"&gt;LFCS(Linux Foundation Collaboration Summit)&lt;/a&gt;에 관한 요약 기사이다.&lt;br /&gt;이 summit은 barrios 개인적으로는 굉장히 참석해보고 싶은 summit이었지만 여&lt;br /&gt;건이 절대 허락하지 않는 멋쟁이 회사에서 근무하고 있기 때문에 절대 불가능한 일이라 &lt;br /&gt;꿈도 꾸지 않는다. &lt;br /&gt;&lt;br /&gt;Barrios의 눈길을 단숨에 사로잡은 것은 Graybeards에 관한 기사였다. &lt;br /&gt;요는 커널 개발자들의 젊은피(새로운 피라고 해석하는 것이 더 좋을 것 같다.)가 수혈되지 않는&lt;br /&gt;다는 것에 관한 토론이었다. &lt;br /&gt;&lt;br /&gt;하지만 결론은 그렇지 않다는 것이다. 매 커널 릴리즈 주기마다 1000명 이상의 개발자들이 &lt;br /&gt;관계하고 있고 그 중의 상당 부분이 처음으로 contribution을 하는 사람들이며 그 중에 &lt;br /&gt;20%정도는 barrios와 같이 취미(돈을 받지 않고 자신이 원해서 contribution하는)로 &lt;br /&gt;즐기는 사람이라고 말하고 있으며 오히려 contributor중 일부는 다른 application project로 &lt;br /&gt;발을 돌리는 것이 차라리 나을 것이라고 말한 것을 들은적까지 있다고 말할 정도로 많은 개발자들이&lt;br /&gt;충원되고 있고 발전하고 있다는 것이다.&lt;br /&gt;&lt;br /&gt;하지만 글에 link되어 있는 다른 기사에서는 &lt;a href="http://www.jfplayhouse.com/2010/04/why-linux-is-not-attracting-young.html"&gt;http://www.jfplayhouse.com/2010/04/why-linux-is-not-attracting-young.html&lt;/a&gt; 좀 다른 말을 하고 있다. &lt;br /&gt;새로운 피들이 모이지 않는 이유가 Linux는 이미 corporation stakeholder에 의해 점유되어&lt;br /&gt;발전되고 있다고 말하고 있으며, 이러한 가운데 개인이 취미로 활동하는 작은 부분(ex, webcam driver)에서 &lt;br /&gt;얻을 수 있는 만족감이 크지 않다는 것이다. 하지만 barrios는 그렇게 생각하지 않는다. &lt;br /&gt;Mainline kernel community에서는 대부분 그들만의 무대가 있다. 각자의 무대에서 각자의 분야에 &lt;br /&gt;집중하다 보면 자연스레 충분한 만족할 수 있다. 물론 개인별로 어느 정도의 만족을 느껴야만 자신이 &lt;br /&gt;그 프로젝트에서 큰 contribution을 하고 있다고 느끼는지는 모르겠지만. &lt;br /&gt;&lt;br /&gt;하지만 Linux kernel이 이미 돈을 받으며 contribution하고 있는 full-time developer들의 비중이&lt;br /&gt;크다는 것은 부정하지 않는다. 그들이 paid full-time developer가 된 것은 알이 먼저인지 닭이 먼저인지 &lt;br /&gt;문제이긴 하지만. 이로 인해 사실 부정적인 영향도 있는 것도 사실이다. 하지만 전체로 보았을 때 긍정적인&lt;br /&gt;면이 훨씬 많기 때문에 지금까지 그래왔듯이 Linux kernel은 잘 진화하고 있는 것이라고 생각한다.&lt;br /&gt;&lt;br /&gt;또 다른 얘기로는 Andrew Morton이 말한 kernel core developer들의 경험치와 자신감이 쌓여가며,&lt;br /&gt;점점 더 복잡한 코드들을 넣고 있다는 것이다. 이로 인해 커널 개발의 진입장벽은 점점 높아지며 &lt;br /&gt;그로 인해 복잡한 코드들을 유지보수하기 어려워질 것이라는 이슈가 있다. &lt;br /&gt;&lt;br /&gt;이것도 정말 공감한다. 지금 리눅스 커널은 barrios가 linux를 보기 시작한 몇년전에 비해 너무나도 &lt;br /&gt;급변하고 있으며 너무나도 복잡해지고 있다. 또한 점점 많은 feature들이 들어가며 알아야 할 것들이 &lt;br /&gt;너무 많아지고 있는 추세이다. 이는 새로운 커널 개발자들의 진입을 저해하기에 안성맞춤이다. &lt;br /&gt;최근 몇년 전가지는 훌륭한 커널 서적들이 많았으나, 최근 주춤하는 시기에 커널은 급변했고, &lt;br /&gt;저자들은 black hole(Robert Love)로 들어갔거나, 박사학위 준비중에 바쁘거나(Mel), &lt;br /&gt;먹고 사느라 힘들기(Jonathan) 때문에 Gap을 채워줄 훌륭한 material들이 절대 부족하다. &lt;br /&gt;다행스러운 것은 kernel의 document들과 source code들의 주석, git등이 점점 잘 되어가고 있다는&lt;br /&gt;것이다. &lt;br /&gt;&lt;br /&gt;이 말고도 이번 Summit에서는 Google의 Open Source Program Manager인 Chris DiBona의 talk도&lt;br /&gt;있었다. 구글은 Open Source Developer의 black hole이라는 평판을 들을 정도로 한번 구글로 입사한&lt;br /&gt;개발자들은 Open Source Community에서 모습을 감추는 경우가 종종 있다.(이것에 대해서는 구글 나름데로&lt;br /&gt;이유가 있는데 다음에 기회가 되며 얘기하기로 하고..) 이번 talk에서 Chris는 구글이 Open Source 진영에&lt;br /&gt;얼마나 많은 contribution을 하고 있는가를 설명하며 사과를 해야하는 입장이 아니라 오히려 칭찬받아야 하는&lt;br /&gt;입장이라고 말한다고 전하고 있다. 하지만 많은 사람들이 수긍하는 분위기는 아니었던 것 같다.&lt;br /&gt;Android에 관해서는 자신들의 코드를 upstream에 merge시킬 메조키스트가&lt;br /&gt;필요하다고 말하고 있다. 이 말에서 늬앙스는 mainline kernel의 upstream에 merge시키는 프로세스와 &lt;br /&gt;따가운 시선들(many reviewers)을 다 극복하고 자신의 에너지를 쏟아 부어 그 안에서 보람을 &lt;br /&gt;느끼는 사람이 없다는 것이다. Barrios는 거꾸로 메조키스트를 언급한 것을 보면 구글 내부적으로 그러한&lt;br /&gt;일을 못하게 하지는 않지만 누군가 총대를 매고 하지 않는 한 굳이 시간과 노력을 당분간은 들이고 싶지 &lt;br /&gt;않겠다는 뜻으로 해석한다. 어쨌든 그의 talk은 성공적이지 못했다고 전하고 있으며, 더욱 중요한 것은&lt;br /&gt;성공적이지 못한 talk 대신에 그의 세션을 참석했던 모든 사람에게 Nexus One phone을 주었다는 것이다. &lt;br /&gt;이것은 많은 blame들을 잠재우는 데 크게 한 몫 했다는 후문이다. 이게 오늘의 Point이다. 대인배 구글. &lt;br /&gt;원래 barrios와 같이 소심한 엔지니어들은 이런 사소한(?) 것 하나하나에도 마음이 휘둘리기 쉽상이다. -_-;;&lt;br /&gt;&lt;br /&gt;세션이 끝나고 Jonathan은 따로 Android 커널 개발자들을 만났다고 한다. 이들의 얘기는 &lt;br /&gt;Chris의 얘기는와는 또 달랐다고 한다. 그들은 굉장히 여느 embedded systems developer와 &lt;br /&gt;같았으며 즉, 언제나 상품 개발 주기는 매우 짧고, 시간은 항상 부족하고 해서 upstream에 source를 &lt;br /&gt;merge시킬 엄두를 못내고 있다고 한다.(이 말에 절대 "우리도"라고 동조하지 말자. 우리는 시간이&lt;br /&gt;없어서가 아니라 우선 가장 크게는 "mind가 안되어 있고" 둘째로 "내공"이 부족하다. &lt;br /&gt;솔직히 인정할 건 인정하자.엔지니어니까)이 부분은 barrios도 상당부분 공감한다.&lt;br /&gt;&lt;br /&gt;하여튼 Android 커널 개발자들은 점점 외톨이가 되가고 있음을 느끼고 있으며 그것은 &lt;br /&gt;그들을 좌절시킨다고 느끼고 있다고 전하고 있다. Jonathan은 이 시점에서 Android 커널 개발자들이 &lt;br /&gt;community가 그들과 소통하려고 하고 있는 것을 들어왔고 잘 이해하고 있다고 말하며, &lt;br /&gt;이번 기회를 발판으로 그들의 merge 시도를 좀더 도와줘야 하는 시점이라고 말하고 있다.&lt;br /&gt;&lt;br /&gt;Barrios야 예전부터 android kernel의 입봉을 원하고 있었기 때문엔 당연히 그런 시점이 오면&lt;br /&gt;절대적으로 support할 것이다.^^&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-932099499084608471?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/932099499084608471/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=932099499084608471&amp;isPopup=true' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/932099499084608471'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/932099499084608471'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/04/2010-linux-foundation-collaboration.html' title='2010 Linux Foundation Collaboration Summit'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8714293509500013959</id><published>2010-04-19T22:44:00.001+09:00</published><updated>2010-04-19T22:48:29.061+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Problem of direct reclaim page writeback</title><content type='html'>오랜만이다. 이렇게 블로깅을 하는 것은. &lt;br /&gt;이유야 여러가지가 있지만 구구절절 말할만한 상황은 아니고. &lt;br /&gt;&lt;br /&gt;그동안 mainline에는 재미있는 일이 너무나도 많았다. &lt;br /&gt;그 많은 것을 다 같이 공유하고 싶은 마음이 큰데 시간과 barrios의 &lt;br /&gt;게으름이 허락치 않는다. 가장 최근에 벌어지는 이슈에 대해서만 먼저 &lt;br /&gt;한번 얘기해보자. (나머지는 차차 기회가 있겠지)&lt;br /&gt;&lt;br /&gt;&lt;a href="http://lkml.org/lkml/2010/4/12/366"&gt;http://lkml.org/lkml/2010/4/12/366&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;지금 barrios가 가장 관심을 가지고 있는 issue는 direct reclaim의 &lt;br /&gt;page write back문제이다. 다들 잘 알고 있겠지만 kernel은 OOM 상황을 &lt;br /&gt;막기 위해 시스템의 process들의 귀중한 시간을 훔친다. 즉, 하찮은 커널이 &lt;br /&gt;무대의 주인공인 프로세스들의 context에서 프로세스를 위해 일을 하는 것이 아니라,&lt;br /&gt;메모리를 회수하기 위해 귀중한 프로세스의 resource를 것도 많이 사용한다는 것이다.&lt;br /&gt;&lt;br /&gt;이 자체가 썩 유쾌하지 못한 상황이긴 하지만 kernel 입장에서는 어쩔수가 없다. &lt;br /&gt;프로세스를 죽이는 것 보다야 낫지 않는가.&lt;br /&gt;&lt;br /&gt;어쨌든, 지금 이슈는 이 direct reclaim path에서 stack overflow가 &lt;br /&gt;발생한다는 것이다. 이 문제를 제일 먼저 report한 이는 xfs의 maintainer라고 &lt;br /&gt;볼 수 있는 Dave Chinner이다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Depth    Size   Location    (47 entries)&lt;br /&gt;-----    ----   --------&lt;br /&gt;0)     7568      16   mempool_alloc_slab+0x16/0x20&lt;br /&gt;1)     7552     144   mempool_alloc+0x65/0x140&lt;br /&gt;2)     7408      96   get_request+0x124/0x370&lt;br /&gt;3)     7312     144   get_request_wait+0x29/0x1b0&lt;br /&gt;4)     7168      96   __make_request+0x9b/0x490&lt;br /&gt;5)     7072     208   generic_make_request+0x3df/0x4d0&lt;br /&gt;6)     6864      80   submit_bio+0x7c/0x100&lt;br /&gt;7)     6784      96   _xfs_buf_ioapply+0x128/0x2c0 [xfs]&lt;br /&gt;....&lt;br /&gt;32)     3184      64   xfs_vm_writepage+0xab/0x160 [xfs]&lt;br /&gt;33)     3120     384   shrink_page_list+0x65e/0x840&lt;br /&gt;34)     2736     528   shrink_zone+0x63f/0xe10&lt;br /&gt;35)     2208     112   do_try_to_free_pages+0xc2/0x3c0&lt;br /&gt;36)     2096     128   try_to_free_pages+0x77/0x80&lt;br /&gt;37)     1968     240   __alloc_pages_nodemask+0x3e4/0x710&lt;br /&gt;38)     1728      48   alloc_pages_current+0x8c/0xe0&lt;br /&gt;39)     1680      16   __get_free_pages+0xe/0x50&lt;br /&gt;40)     1664      48   __pollwait+0xca/0x110&lt;br /&gt;41)     1616      32   unix_poll+0x28/0xc0&lt;br /&gt;42)     1584      16   sock_poll+0x1d/0x20&lt;br /&gt;43)     1568     912   do_select+0x3d6/0x700&lt;br /&gt;44)      656     416   core_sys_select+0x18c/0x2c0&lt;br /&gt;45)      240     112   sys_select+0x4f/0x110&lt;br /&gt;46)      128     128   system_call_fastpath+0x16/0x1b&lt;/blockquote&gt;&lt;br /&gt;위의 로그를 살펴보면 direct reclaim path전까지 3.1K정도의 &lt;br /&gt;stack이 사용되어졌으며 XFS가 3.5K를 사용하는 것을 볼 수 있다. &lt;br /&gt;다음 block layer와 몇가지 더 하면 금방 8K가 바닥이 나버린다. &lt;br /&gt;XFS가 3.5K를 사용하는 것도 크지만 direct reclaim path만도 &lt;br /&gt;대략 1.1K나 사용하고 있다. 불과 함수 몇개가 말이다. &lt;br /&gt;&lt;br /&gt;이 report는 또 다른 문제를 언급하고 있다. VM의 reclaim으로 인해 &lt;br /&gt;발생하는 I/O와 flusher가 발생시키는 I/O가 섞여 결국 random write가 &lt;br /&gt;발생하게 되고 이는 reclaimer와 flusher의 throughput을 떨어뜨리게 &lt;br /&gt;될 것이다. &lt;br /&gt;&lt;br /&gt;이를 해결하기 위해 Dave가 제안한 것은 direct reclaim path에서 &lt;br /&gt;아예 writeback을 하지 말자는것이다. 굉장히 공격적인 방법이다. &lt;br /&gt;그러므로 해당 thread는 현재 74개의 메일들로 토론이 진행되고 있다. &lt;br /&gt;&lt;br /&gt;처음 토론이 진행되었던 것은 lumpy reclaim 문제이다. &lt;br /&gt;Mel의 lumpy reclaim은 LRU distance와는 관계없이 특정 상황이 되면 &lt;br /&gt;lru list에 있던 페이지들에 물리적으로 근접해 있는 페이지들을 회수하여 &lt;br /&gt;big order contiguous page들을 만들어 내는 것이다. 이때 필요에&lt;br /&gt;따라 우리는 dirty page들을 flush해야 하는 상황이 필연적으로 발생한다. &lt;br /&gt;그런데 pageout을 생략하게 되면 그러한 lumpy reclaim이 직접적으로 타격을 &lt;br /&gt;받게 되는 것이다. &lt;br /&gt;&lt;br /&gt;그래서 Mel과 Kosaki는 stack diet를 시도하고 있고, 반면 그것이 근본적인 &lt;br /&gt;해결책이 아니라고 사람들도 있다. barrios도 처음에는 전자의 편에 있었지만 &lt;br /&gt;좀더 생각해보니 후자가 더 좋을 것이라고 생각한다. 위의 로그를 보면 &lt;br /&gt;direct reclaim path도 stack을 많이 사용하였지만 XFS 또한 많이 사용하였다.&lt;br /&gt;그리고 direct reclaim path전에도 무시하지 못한다. &lt;br /&gt;결국 stack diet를 해서 어느 한 곳을 줄여봐야 모든 곳을 줄이지 못하면 언젠가 &lt;br /&gt;다시 이 문제를 만나게 될 것이라고 생각한다(우리는 함수가 nesting되는 경우나 &lt;br /&gt;다른 함수들을 통해서 호출되는 경우도 생각해야 한다. 위에서 보는 log의 사용량이 &lt;br /&gt;절대 worst case가 될 수 없다는 것이다.) 또한 barrios는 앞으로 reclaim path를 &lt;br /&gt;수정할때마다 stack 사용량을 일일이 계산하며(ie, 걱정하며 :)) coding하고 싶지 않다. &lt;br /&gt;&lt;br /&gt;그렇다고 direct reclaim path에서 I/O를 하지 않게 되면 우리는 보다 많은 &lt;br /&gt;OOM을 만나게 될 것이다. 사실 direct reclaim path에서의 writeback은 &lt;br /&gt;process들의 progress를 다소 완화시켜주는 역할도 하기 때문이다.&lt;br /&gt;&lt;br /&gt;이 와중 Andrew Morton은 양심고백을 하나 하였다. &lt;br /&gt;사실 direct reclaim path에서의 write가 어느날 갑자기 심해졌다는 것이다. &lt;br /&gt;아마 2.6.16 근처였던 것으로 기억하며 아무도 그 문제에 대해서 fix하려고&lt;br /&gt;시도하지 않았다는 것이다. 또한 writeback을 다른 곳으로 돌리는 것은 &lt;br /&gt;2.5.10에 시도되었었지만 그리 효과가 없었다고 말하며 address_space를 &lt;br /&gt;pinning할 수 없어 writearound 자체가 구현하기 쉽지 않다고 말하고 있다. &lt;br /&gt;&lt;br /&gt;Dave의 patch에 관해서는 flusher는 target zone을 고려하지 않고 있어 &lt;br /&gt;잘못된 페이지들만을 계속해서 flush하는 상황이 발생하며 이는 system을 &lt;br /&gt;livelockable하게 만들수도 있다고 한다. 여기에 barrios는 한가지 더 우려가 &lt;br /&gt;되는 것은 LRU distance와 상관없는 페이지들을 대거 writeout함으로써 &lt;br /&gt;이어지는 write-merge등에 손해를 볼 수 있고, working set들이 밀려나가게 &lt;br /&gt;되어버리는 일도 발생할 수 있다고 생각한다.&lt;br /&gt;&lt;br /&gt;Andrew는 I/O pattern 문제를 해결하기 위해서 이전에 언급했던 &lt;br /&gt;"왜 갑자기 direct reclaim path에서 많은 I/O가 발생하기 시작하였나? &lt;br /&gt;우리가 그 문제를 피할수는 없는 것인가?" 부터 생각해야 하며 &lt;br /&gt;Stack Overflow문제를 풀기 위해서는 자신없어하며 target page를 &lt;br /&gt;다른 쓰레드에게 패스하여 해당 쓰레드와 동기를 맞추면 어떨까 한다.&lt;br /&gt;&lt;br /&gt;현재까지 이 문제에 대한 별다른 해결책이 없어 보이는 가운데 &lt;br /&gt;James Bottomley는 이번 MM summit과 FS summit이 함께 열리기 때문에 &lt;br /&gt;그때까지도 문제가 해결이 되지 않으면 그 자리에서 안건을 올려 한번 얘기해보자고 &lt;br /&gt;하고 이에 다른 개발자들은 이 제안에 환영하고 있다. 그 이유는 이미 FS 개발자들에게 &lt;br /&gt;random I/O 문제는 consensus를 이룬 문제이며, 정말 문제는 MM guys들이 &lt;br /&gt;이 문제를 이해하지 못하고 있다고 생각하고 있기 때문이다. 사실 MM guys들이 &lt;br /&gt;이해를 못하고 있는 것이 아니라, 어떻게든 많은 부분을 수정하지 않고 고쳐보려고 &lt;br /&gt;하는 것이다. -_-;; 하지만 barrios의 생각으론 FS guys들의 의견에 전적으로 &lt;br /&gt;동의한다. 간만에 MM summit이 열리는데 재밌는 안건이 될 것이다. &lt;br /&gt;비록 참석은 못하더라도 재밌는 토론거리가 될 것 같다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8714293509500013959?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8714293509500013959/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8714293509500013959&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8714293509500013959'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8714293509500013959'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/04/problem-of-direct-reclaim-page.html' title='Problem of direct reclaim page writeback'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-224402988218593868</id><published>2010-03-07T01:05:00.004+09:00</published><updated>2010-03-07T01:09:27.575+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Innovators get Linux to boot in 1 second</title><content type='html'>&lt;a href=" http://lwn.net/Articles/377507/"&gt;&lt;br /&gt;http://lwn.net/Articles/377507/&lt;/a&gt;&lt;br /&gt;&lt;a href="http://www.edn.com/article/CA6720353.html"&gt;http://www.edn.com/article/CA6720353.html&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Montavista가 1초 부트를 했다는 기사가 떴다.&lt;br /&gt;자동차 계기판 시스템을 Linux를 사용하여 한 것 같다.&lt;br /&gt;&lt;br /&gt;기술내용은 위의 글들로 미루어보아&lt;br /&gt;&lt;br /&gt;첫째, 불필요한 커널 옵션 정리, 부트로더에서 redundant한 부분 정리&lt;br /&gt;(임베디드에서 하드웨어가 한번 fix되면 변하지 않는 성질을 응용)&lt;br /&gt;&lt;br /&gt;둘째, Linux의 부팅과정 중 필요한 여러 일들을 수행함에 있어 필요한 task들을 로딩하거나 &lt;br /&gt;파일들을 읽어오기 위한 Flash와 Memory의 복사 비용을 DMA를 사용하여 줄임. &lt;br /&gt;이때 CPU는 다른 task를 수행함(요즘 CPU는 예전에 비하여 상대적으로 큰 cache를 가지고 있기 &lt;br /&gt;때문에 대부분 필요한 일들을 cache에서 hit시켜 위의 여러 작업을 병렬적으로 할 수 있다.)&lt;br /&gt;&lt;br /&gt;셋째, 부팅시에 필요한 즉, 사용자에게 마치 모든 작업이 완료되어 당신의 입력을 기다리고 &lt;br /&gt;있어요라고 말할만큼의 일을 하기 위해 필요한 application들만을 모아서 ramfs 사용(ramdisk 아님)&lt;br /&gt;으로 생각된다.&lt;br /&gt;&lt;br /&gt;기술적으로 별것 아니라고 하면 별것 아닐수도 있지만 한편으로 대단하다 생각하면 &lt;br /&gt;대단하기도 하다.&lt;br /&gt;위의 기술들이 upstream에 merge될 수 있느냐, 없느냐가 중요한 것은 아닌 것 같다.&lt;br /&gt;중요한 건 지금 그들은 1초 부트를 하고 있다는 것 뿐이고 다른 사람들은 아직 Linux를&lt;br /&gt;가지고 1초 부트를 하지 못하고 있다는 것이다. &lt;br /&gt;&lt;br /&gt;또 여러 사람 고생할게 눈에 불 보듯 선하다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-224402988218593868?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/224402988218593868/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=224402988218593868&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/224402988218593868'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/224402988218593868'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/03/innovators-get-linux-to-boot-in-1.html' title='Innovators get Linux to boot in 1 second'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4062314184580203379</id><published>2010-03-01T13:28:00.000+09:00</published><updated>2010-03-01T13:28:19.677+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>sys_membarrier()</title><content type='html'>&lt;a href="http://lwn.net/Articles/369567/"&gt;http://lwn.net/Articles/369567/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;최근 membarrier에 대한 system call추가에 관한 논의가 계속되어 왔다.&lt;br /&gt;&lt;br /&gt;이 새로운 system call은 Mathieu Desnoyers에 의해 시작되었으며, &lt;br /&gt;자신이 만들고 있는 LTTng tracing toolkit에서 성능을 높이기 위한 목적으로&lt;br /&gt;사용하려고 한다.&lt;br /&gt;&lt;br /&gt;Mathieu는 얼마전 Paul과 User-Level RCU library를 만들었었다.&lt;br /&gt;물론 이 library또한 LTTng tracing toolkit에서 사용하기 위해 만들었던 것이다. &lt;br /&gt;&lt;br /&gt;User-Level RCU라 하면 가장 먼저 드는 의문이 어떻게 Kernel-Level RCU의 &lt;br /&gt;(wait for pre-existing RCU readers to complete) property를 만족시킬&lt;br /&gt;것인가이다. Kernel-Level RCU는 rcu_read_lock의 kernel preemption을 disable하는&lt;br /&gt;특성으로 위의 property를 만족시키고 있다. 하지만 User-Level에서 kernel preemption을&lt;br /&gt;막는다는 것은 ugly한 방법을 사용하지 않고는 가능하지 않다. (일시적으로 task를 제일 높은&lt;br /&gt;priority의 RT task로 변환하면 가능하지만 다른 RT task를 선점하는 좋지 않은 side effect&lt;br /&gt;이 발생한다.)&lt;br /&gt;&lt;br /&gt;그리하여 User-Level RCU에서 취한 방법은 thread가 RCU critical section에 있다는 &lt;br /&gt;것을 표헌하기 위해 특정 메모리 영역에 변수를 setting하는 것이다. &lt;br /&gt;하지만 이과 같은 approach의 문제는 memory misordering 문제에서 시작된다.&lt;br /&gt;CPU 1에서 실행되고 있는 A 라는 쓰레드가 RCU critical section이 완료되었다는 것을 &lt;br /&gt;보장받기 위해 CPU 2에서 실행되는 B 라는 쓰레드는 synchronize_rcu를 호출할 것이다.&lt;br /&gt;하지만 이때 synchronize_rcu는 memory misordering문제로 인하여 A 쓰레드가 &lt;br /&gt;RCU critical section에 존재한다는 것을 missing할수 있게 된다. 즉 B가 모든 RCU&lt;br /&gt;critical section이 완료되었다고 판단하였지만 실제로는 쓰레드 A가 RCU critical section&lt;br /&gt;에 남아 있을 수 있다는 것이다. 이는 A가 사용하는 자원이 갑자기 사라질 수 있음을 의미한다.&lt;br /&gt;&lt;br /&gt;이 문제는 간단히 rcu_read_lock/unlock에 memory barrier를 두면 해결되는 문제이지만, &lt;br /&gt;일반적으로 RCU reader들은 fast path에 속하기 때문에 간혹 수행되는 slow RCU updater들로&lt;br /&gt;인해 fast path에 성능을 손해봐야 한다는 것은 기본적으로 RCU policy에 적합하지 않다.&lt;br /&gt;&lt;br /&gt;이와 같은 문제를 해결하기 위해 Mathieu는 membarrier라는 새로운 system call을 추가하고자 한다.&lt;br /&gt;이 새로운 membarrier를 통해서 기존의 rcu_read_lock/unlock은 Kernel-Level RCU와 마찬가지로&lt;br /&gt;compiler level의 reordering만을 막고(CPU level의 reordering을 막는 것은 아니다), 대신 &lt;br /&gt;updater가 동기화를 요구할 때 새로운 system call을 호출하여 reader들의 memory barrier들을 &lt;br /&gt;실행하는 것이다. Update의 실행이 적은 RCU의 policy에 잘 만족하는 overhead 분산이다.&lt;br /&gt;&lt;br /&gt;이 함수의 초기 구현은 시스템의 모든 CPU에 IPI를 날리고 그 반응으로 각 CPU에서 memory barrier&lt;br /&gt;를 실행하는 것이었다. 하지만 이와 같은 방법은 user space가 모든 CPU에 강제로 interrupt를&lt;br /&gt;날릴수 있는 기회를 제공함으로써 또하나의 DoS attack을 만들수 있는 기회를 제공한다는 문제가 있다.&lt;br /&gt;또 다른 문제점은 실제 membarrier를 호출한 프로세스와 관계없는 CPU들까지(즉, 다른 task들을 &lt;br /&gt;수행하고 있는 CPU)까지 쓸데 없이 interrupt을 한다는 것이다. 다른 task가 RT task라면 문제는&lt;br /&gt;더욱 심각해질 것이다. 또 다른 문제는 인터럽트된 프로세서가 sleep mode에 있었다면.... &lt;br /&gt;Green IT 하자고 난리인 이 판국에. &lt;br /&gt;&lt;br /&gt;이 패치는 많은 lock expert들에 의해 in-depth review가 이루어지며 optimization작업이 &lt;br /&gt;진행되어 왔다. 현재 이 system call은 시스템에 모든 CPU를 살펴 caller와 같은&lt;br /&gt;address space를 공유하는 녀석들이 실행되고 있는 CPU들만을 참조하여 IPI를 보내게 된다.&lt;br /&gt;이 방법은 위에서 문제되었던, DoS, RT task performance, Energy Consumption 문제를 &lt;br /&gt;해결한다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4062314184580203379?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4062314184580203379/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4062314184580203379&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4062314184580203379'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4062314184580203379'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/03/sysmembarrier.html' title='sys_membarrier()'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-9104245356810692493</id><published>2010-02-08T00:59:00.000+09:00</published><updated>2010-02-08T00:59:35.460+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Improve scalability of rmap scanning of anonymous pages</title><content type='html'>최근 Rik은 anon page들의 rmap을 통한 scanning overhead를 &lt;br /&gt;줄이기 위한 패치를 제출하였다. 지금까지의 문제는 다음과 같다. &lt;br /&gt;&lt;br /&gt;A라는 프로세스가 있다고 가정하자. A라는 프로세스는 1000개의 page들로 &lt;br /&gt;이루어진 하나의 vma를 가지고 있다고 하자. 그리고 A는 1000개의 프로세스를 &lt;br /&gt;fork한다고 하자. 너무나도 잘 알듯이 A process의 vma에 해당되는 &lt;br /&gt;PTE들은 protect되어질 것이다. (For Copy-On Write)&lt;br /&gt;&lt;br /&gt;이제 예를 들어 child 0이 vma의 0 page, child 1이 vma의 1 page, &lt;br /&gt;child 2가 vma의 2 page.... child 999는 vma 999번째 page를 &lt;br /&gt;write한다고 가정하자. &lt;br /&gt;&lt;br /&gt;무슨일이 일어날까?&lt;br /&gt;&lt;br /&gt;Process A의 VMA의 anon_vma에 연결되는 vma들은 1001가 될 것이며, &lt;br /&gt;페이지 회수를 위해서 하나의 page에 대한 matching vma 검색은 &lt;br /&gt;worst case 1000번의 mismatch가 발생할 것이다.&lt;br /&gt;&lt;br /&gt;여기서 심각한 것은 1000개의 vma를 lookup하는 동안 anon_vma의 &lt;br /&gt;lock이 hold되고 있다는 것이다. 그러므로 모든 CPU에 anon_vma의 lock을 &lt;br /&gt;필요로 하는 모든 opeartion들 또한 위의 operation이 종료하기 전까지 &lt;br /&gt;모두 stuck되는 것이다. &lt;br /&gt;&lt;br /&gt;이 문제를 풀기 위해 Rik이 제안한 방법은 anon_vma와 vma가 연결되는 방식을 &lt;br /&gt;하나의 vma가 여러개의 anon_vma들과 연결될 수 있도록 개선한 것이다. &lt;br /&gt;fork시점에 각 child process들은 각자 자신의 anon_vma를 갖게 되며 &lt;br /&gt;COWed page들은 각 자식 프로세스들의 anon_vma에 연결되게 하는 것이다. &lt;br /&gt;또한 COWed page가 속해 있는 vma는 parent의 anon_vma와도 연결된다. &lt;br /&gt;왜냐하면 non-COWed page들이 child에 속해있을 수도 있기 때문이다. &lt;br /&gt; &lt;br /&gt;이는 1000개의 child process들의 1/N개의 page들에 대한 rmap scanning &lt;br /&gt;complexity를 O(N)에서 O(1)로 줄여준다. worst case 또한 O(N)에서 2,&lt;br /&gt;base case 1이 될 것이다. &lt;br /&gt;&lt;br /&gt;하지만 barrios가 우려하는 것은 이러한 anon_vma의 lock overhead는 &lt;br /&gt;server중에서도 heavily forkbomb workload 즉, apache와 같은 경우를 &lt;br /&gt;제외하곤 그리 흔한 workload는 아닐 것 같다는 것에 있다. 그러므로 가뜩이나 &lt;br /&gt;SWAP을 잘 사용하지 않아 anonymous page의 scanning이 필요하지 않은 &lt;br /&gt;embedded 동네에서 이 patch는 다소 overkill이라는 점이다. &lt;br /&gt;&lt;br /&gt;이와 같은 우려의 목소리는 Rik에게 전달했으며 그 또한 충분히 공감하고 있음으로, &lt;br /&gt;그에 대한 패치는 Rik이 하던, Barrios가 하던 어렵지 않게 merge될 것으로 생각된다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-9104245356810692493?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/9104245356810692493/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=9104245356810692493&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/9104245356810692493'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/9104245356810692493'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/02/improve-scalability-of-rmap-scanning-of.html' title='Improve scalability of rmap scanning of anonymous pages'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-327456653545222256</id><published>2010-01-16T23:50:00.001+09:00</published><updated>2010-01-23T18:22:29.752+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Linux Foundation CTO leaves for Google</title><content type='html'>&lt;a href="http://www.internetnews.com/software/article.php/3858856/Linux+Foundation+CTO+Leaves+for+Google.htm"&gt;http://www.internetnews.com/software/article.php/3858856/Linux+Foundation+CTO+Leaves+for+Google.htm&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;Ted 또한 Google로 자리를 옮겼다. &lt;br /&gt;그는 IBM에 근무하는 동안 ext4를 성공적으로 Linux에 안착시켰으며,&lt;br /&gt;Linux Foundation에서 2년간 CTO 업무를 수행하였다. 이번 2년간의&lt;br /&gt;CTO 업무를 마감하며, Google로 자리를 옮기게 되었다. &lt;br /&gt;&lt;br /&gt;Google로써는 또 한명의 재능있는 kernel hacker를 얻었으며, IBM으로써는&lt;br /&gt;잃게 된 것이다. 개인적으로는 아직까지 구글이 kernel community에서 차지하는&lt;br /&gt;위상이 그리 높지 않아, Ted의 앞으로의 kernel community에 대한 기여가&lt;br /&gt;조금 걱정되기는 하나, Google의 기업 이미지 상 Ted가 뜻이 있다면 kernel community&lt;br /&gt;활동을 하는데는 큰 지장이 없을 것으로 생각한다. &lt;br /&gt;&lt;br /&gt;기사의 소개에 따르면 Ted가 맡게 될 첫번째 임무는 Google의 system들을 ext2에서 &lt;br /&gt;ext4로 migration시키는 것이다. 지난번 kernel summit에서도 말이 나온 것과 같이&lt;br /&gt;Google은 현재 metadata 처리의 성능 개선을 위해 유별난 방법을 사용하고 있다.&lt;br /&gt;결국 이 문제를 해결하기 위해 유별난 방법을 버리고 ext4로 migration을 시도하는 것 같다.&lt;br /&gt;&lt;br /&gt;Ted는 Google에는 많은 재밌는 kernel project들과 뛰어난 kernel hacker들이 있는 것에&lt;br /&gt;흥미를 느끼고 있다. &lt;br /&gt;&lt;br /&gt;앞으로 Google에서의 Ted의 건투를 빈다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-327456653545222256?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/327456653545222256/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=327456653545222256&amp;isPopup=true' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/327456653545222256'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/327456653545222256'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/01/linux-foundation-cto-leaves-for-google.html' title='Linux Foundation CTO leaves for Google'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5175368991207829728</id><published>2010-01-16T23:36:00.001+09:00</published><updated>2010-01-16T23:37:21.353+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Speculative Page Fault</title><content type='html'>Barrios는 page fault의 문제에 관하여 항상 관심을 가지고 있었다.&lt;br /&gt;&lt;br /&gt;그 이유는 100T1P(100 Threads in 1 Process)의 application을 본 적이 있기 때문이다.&lt;br /&gt;하지만 이러한 괴물 프로그램은 다른 곳에도 많이 있었다.&lt;br /&gt;(지난 번 Google을 얘기하면서 이 문제를 언급한 적이 있었다.)&lt;br /&gt;&lt;br /&gt;이 문제를 풀기 위해 Google은 I/O request 전 mmap_sem를 release하는 패치를 자체적으로 &lt;br /&gt;사용하고 있었으며, mainline에 submit을 시도하였었다(하지만 공식적인 패치는 아니였다.)&lt;br /&gt;이 패치는 mmap_sem에 write-side lock으로 인해 다수의 reader들이 stuck되는 현상을 막기&lt;br /&gt;위한 패치였다. &lt;br /&gt;&lt;br /&gt;작년 11월경, 새로운 패치가 Kame에 의해 RFC되었다. 이 패치는 Google의 문제와는 달리, &lt;br /&gt;mmap_sem의 contention에 대한 cache line bouncing문제를 해결하기 위한 패치였다.&lt;br /&gt;제목은 &lt;a href="http://thread.gmane.org/gmane.linux.kernel.mm/40888"&gt;speculative page fault&lt;/a&gt;였다. 제목 그대로 page fault에 대해 추측을 한후, &lt;br /&gt;추측이 실패하였을 경우, retry를 하는 방식이다. 추측을 해서 얻으려고 하는 이득은&lt;br /&gt;mmap_sem의 lock을 hold하지 않고 하겠다는 것이다. 해서 cache line bouncing을 &lt;br /&gt;없애겠다는 것이며, 추측이 틀렸을 경우, 제대로 다시 Lock을 hold하고 retry를 하겠다는 &lt;br /&gt;approach이다. approach 자체는 simple하지만 구현하기에 그리 순탄지는 않다. &lt;br /&gt;&lt;br /&gt;이를 구현하기 위해 다양한 시도들을 했었다. vma에 reference counter를 두는 방식, &lt;br /&gt;rb tree에 RCU를 적용하는 방식등.. 시도는 계속되었다. &lt;br /&gt;&lt;br /&gt;Barrios는 이 패치들을 11월 첫 버젼 부터 review하기 시작했으며 12월 말까지 계속해서&lt;br /&gt;Kame와 패치에 대해 얘기하고 있었다. 이런 와중, Peter는 Kame의 패치의 atomic operation에 &lt;br /&gt;대한 문제를 꼬집기 시작하였다. 문제는 atomic opeartion에 대한 비용은 거의 spin lock의 &lt;br /&gt;비용만큼이나 크다는 것이다. 우리는 기존의 page table lock과 RCU를 사용하여 atomic op를&lt;br /&gt;사용하지 않고도 문제를 해결할 수 있다고 주장하였으며, 그에 대한 패치를 제시하였다. &lt;br /&gt;&lt;br /&gt;Peter의 첫 패치는 부팅조차 되지 않는 상태였으나, 몇가지 버그를 해결하고 간신히 부팅은 되는 &lt;br /&gt;형태였지만 어디까지나 RFC 단계의 패치 형태였으며 방향성만을 보여주기 위한 것이었다.(Peter의&lt;br /&gt;패치가 완성되기 위해서는 SRCU의 개선이 필요하였다. 이를 위해 Peter는 Paul과 얘기중이었으며,&lt;br /&gt;패치는 빠르게 settle down되어가는 듯 하였다.)&lt;br /&gt;&lt;br /&gt;패치는 굉장히 깔끔한 코드였다. 지금껏 Kame에 의해 만들어진 것 보다는 좋아 보였다. &lt;br /&gt;하지만 한가지 치명적인 문제를 가지고 있었다. 문제는 vma 자체는 RCU에 의해 보호되지만,&lt;br /&gt;vma와 연결된 VFS stack은 그렇지 못하다는 것이었다. 이 문제를 해결하기 위해서는 &lt;br /&gt;VFS stack 전체가 RCU에 의해 보호되어야 한다. 이는 전체 kernel core에 광범위한 패치가&lt;br /&gt;필요하다, 또한 RCU에 의한 보호는 unmap path의 실행시간을 bound하기 어렵게 되는 문제 또한&lt;br /&gt;가지고 있었다. 이 문제는 RCU를 sync하여 어느 정도 해결할 수 있지만 synchronize_rcu 함수의&lt;br /&gt;비용은 상당히 크다. 그러므로 unmap path에 그런 함수를 넣는 것은 모두가 좋아하지 않고 있다.&lt;br /&gt;또한 map path 만큼이나 unmap path의 성능이 중요한 application도 있다고 Peter는 조언하였다.&lt;br /&gt;&lt;br /&gt;얘기가 이렇게 풀어가고 있을 무렵, Linus는 전체적인 잘못된 문제를 짚어주었다.&lt;br /&gt;문제는 우리가 너무 technical detail에 매달리고 있다는 것이다. 이러한 문제는 &lt;br /&gt;더 높은 higher layer의 design을 통해 해결하는 것이 좋다는 의견이었다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;I would say that this whole series is _very_ far from being mergeable. &lt;br /&gt;Peter seems to have been thinking about the details,&lt;br /&gt; while missing all the subtle big picture effects that seem to actually &lt;br /&gt;change semantics. &lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;이 말에 대부분의 개발자들은 동의를 하였으며 그러던 중, Linus는 새로운 문제를 발견하였다.&lt;br /&gt;Kame의 profile을 보는 순간 이 문제는 mmap_sem의 cache line bouncing문제가 아니라고 &lt;br /&gt;결론을 내린것이다. 그 이유는 profile data에 schedule footprint가 보이지 않는다는 것이다. &lt;br /&gt;정말 mmap_sem에 대해서 서로 치열하기 가지려고 경쟁을 하였다면 wait 상태로 들어가건 runnable 상태로 &lt;br /&gt;들어가 건 schedule과 관련된 footprint이 보여야 한다. 하지만 profile 데이터 상에는 그러한 &lt;br /&gt;것은 보이지 않았다.&lt;br /&gt;&lt;br /&gt;Linus는 문제의 원인을 X86_64의 naive한 spinlock구현을 지적하였다. &lt;br /&gt;X86은 이미 xadd 명령을 이용하여 rw semaphore를 optimize하고 있었지만, &lt;br /&gt;X86_64는 그렇지 못하고 있었다. 해서 X86_64의 rw semaphore는  generic한 형태의 &lt;br /&gt;rw semaphore를 그대로 사용하고 있었다.&lt;br /&gt;사실 barrios도 Kame의 Test program을 x86에서 테스트 해보았지만 Kame와 같은 profile &lt;br /&gt;결과를 얻지 못하였었다. barrios는 그것은 Kame의 테스트 환경이 2 socket 8 core 환경이었지만 &lt;br /&gt;barrios는 1 socket에 4 core 환경이어서 그런가보다 하고 넘어갔었는데 문제 자체가 X86과 &lt;br /&gt;X86_64의 spinlock구현에서 벌어진 것이었다.&lt;br /&gt;&lt;br /&gt;Linus는 금방 최적화된 spinlock을 구현하여 패치를 올렸으며, 예상은 적중하였다. &lt;br /&gt;Kame와 Peter의 패치 이상으로 결과가 좋았던 것이다. &lt;br /&gt;결국 문제는 우리가 생각했던 것과는 다른 곳에 있었다. &lt;br /&gt;&lt;br /&gt;이 문제는 불과 몇일 만에 80여개의 쓰레드를 만들어내며 결국 naive한 X86_64의 rw semaphore&lt;br /&gt;의 문제를 해결하며 결론을 보았다.(하지만 아직까지 Linus의 패치는 최적화된 버젼이 아니며, Linus&lt;br /&gt;는 누군가가 더 최적화해서 패치를 올려주길 기다리고 있는 것 같다.)&lt;br /&gt;이 문제를 통해 아직 mmap_sem가 그리 큰 bottle neck은 아니라는 것이 반증되었다. &lt;br /&gt;&lt;br /&gt;하지만 mmap_sem와 같은 coarse-grained lock은 언젠가 해결되어야 하며, 이 문제를 해결하기 위해서&lt;br /&gt;lock 자체에 대한 수정 보다는 VMM의 page fault handling 자체를 redesign이 필요가 있을 것으로 &lt;br /&gt;생각된다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5175368991207829728?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5175368991207829728/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5175368991207829728&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5175368991207829728'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5175368991207829728'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2010/01/speculative-page-fault.html' title='Speculative Page Fault'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7189294347743750248</id><published>2009-12-31T22:24:00.003+09:00</published><updated>2009-12-31T22:56:15.987+09:00</updated><title type='text'>EOF of 2009</title><content type='html'>이렇게 의지와는 관계없이 2009년도 가버린다. &lt;br /&gt;마음같아서는 잡을 수만 있으면 보내고 싶지 않은 해이다.&lt;br /&gt;&lt;br /&gt;올해에 무엇보다 가장 큰 변화는 지금 내 무릎위에 앉아 나의&lt;br /&gt;모니터를 함께 쳐다보고 있는 녀석이 생겼다는 것이다. 그 만큼 또 &lt;br /&gt;내 욕심이 늘었다. 자꾸 자꾸 버리는 것 없이 늘어만 가는 욕심에 갇혀&lt;br /&gt;힘들적도 있지만 아직은 견딜만 하다. &lt;br /&gt;&lt;br /&gt;돌이켜보면 그다지 후회가 남는 일은 없는 것으로 보아 선방한&lt;br /&gt;해였다. 최근 몇가지 안 좋은 모습으로 스스로에게 약간 짜증이 나있는&lt;br /&gt;상태이긴 하지만 금방 좋아질 것이라고 낙관한다. &lt;br /&gt;&lt;br /&gt;올 한해 가장 와 닿았던 것은 내가 어찌 할 수 없는 일을 어찌해보려고 &lt;br /&gt;하는 것은 분명 정신건강에 좋지 않다는 것이다. &lt;br /&gt;어찌 할 수 없었던 것은 능력이 부족한 나의 잘못임이 자명하니 능력밖의&lt;br /&gt;일을 못한다고 투덜거려봐야... 부족하면 키우면 되는 것이고. &lt;br /&gt;그런데 문제는 별로 키우고 싶지 않은 것들이 더 많다는 것이다. &lt;br /&gt;절대적인 상생을 위한 타협이 필요하다. &lt;br /&gt;&lt;br /&gt;내년을 위한 소망들도 몇가지 있다. 지금 막 떠오른 것도 있고 예전부터&lt;br /&gt;계획한 것도 있고, 최근 수정된 것도 있다. 내가 어찌한들 가는 2009년&lt;br /&gt;막을 재간은 없고, 계획된 2010년은 오고 있으니 선택의 여지가 없다. &lt;br /&gt;&lt;br /&gt;다윈의 진화론을 기반으로 "한해 한해 진보하지 못한다면&lt;br /&gt;나는 인간이 아니지 않을까?"는 궤변으로 올 한해 마무리하며, 내년에도 &lt;br /&gt;계속 인간일 수 있길 기대한다. &lt;br /&gt;&lt;br /&gt;주위 모든 고마운 분들 내년에도 계속 행복하길 바란다.&lt;br /&gt;&lt;br /&gt;&lt;object width="480" height="385"&gt;&lt;param name="movie" value="http://www.youtube.com/v/Pb1MNUoJg6c&amp;hl=ko_KR&amp;fs=1&amp;"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/Pb1MNUoJg6c&amp;hl=ko_KR&amp;fs=1&amp;" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="480" height="385"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7189294347743750248?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7189294347743750248/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7189294347743750248&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7189294347743750248'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7189294347743750248'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/12/eof-of-2009.html' title='EOF of 2009'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2235433677504437192</id><published>2009-12-27T20:00:00.004+09:00</published><updated>2009-12-27T20:18:12.469+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Drop Andorid drivers in Staging tree</title><content type='html'>최근 Greg은 Andorid를 staging tree에서 제거하기를 결정하였다. &lt;br /&gt;그 이유는 다음과 같다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;"Google and no one else stepped up to maintain them, so they will be dropped. So sad..."&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;나도 슬프다. 어쩌다가 일이 이렇게 되었는지 모르겠다. &lt;br /&gt;&lt;br /&gt;사실 구글의 커널 패치들은 mainline guy들과 여러차례 trouble을 일으켰다. &lt;br /&gt;Barrios는 모든 패치를 review하진 못하였지만 low memory killer 패치는 &lt;br /&gt;review한적이 있으며, 그것이 얼마나 ugly한 코드였는지 언급한 바 있다. &lt;br /&gt;&lt;br /&gt;몇몇 MM guys들은 심지어 구글의 커널 코드들을 staging tree에 &lt;br /&gt;add하는 것 조차 거부하였었다. &lt;br /&gt;&lt;br /&gt;그 이유는 Google의 소극적인 태도와 코드 개선의 의지를 보여주지 않았었기 때문이다. &lt;br /&gt;그럼에도 불구하고 Greg의 의지로 staging tree로의 입봉은 임베디드 리눅스 입장에서&lt;br /&gt;상당히 고무적인 일이었다. Google의 의지와는 관계없이 Greg의 판단에&lt;br /&gt;의해 merge되었기 때문이다. &lt;br /&gt;&lt;br /&gt;하지만 결과가 이러하다. Open Source Community의 힘을 모르지 않는 &lt;br /&gt;구글에서 나온 결과이기 때문에 더욱 놀랍다. 무슨 생각으로, 왜 그러한 방향으로 &lt;br /&gt;driven한 것인지 잘 모르겠지만 Embedded Linux의 Best Practice가 하나 사라진 것에 대&lt;br /&gt;해 상당히 아쉽다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2235433677504437192?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2235433677504437192/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2235433677504437192&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2235433677504437192'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2235433677504437192'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/12/drop-andorid-drivers-in-staging-tree.html' title='Drop Andorid drivers in Staging tree'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6421738523389223931</id><published>2009-12-24T15:40:00.001+09:00</published><updated>2009-12-24T15:49:29.237+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>RCU mistakes</title><content type='html'>&lt;a href="http://lwn.net/Articles/366718/"&gt;http://lwn.net/Articles/366718/&lt;/a&gt;&lt;br /&gt;&lt;a href="http://lwn.net/Articles/366717/"&gt;http://lwn.net/Articles/366717/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;지난 기사에 Thomas의 rwlock 제거 노력에 대한 언급을 하였었다. &lt;br /&gt;지난주 corbet은 Thomas의 패치에 대한 기사를 또 다시 실었다. &lt;br /&gt;&lt;br /&gt;주의하고 넘어가야 할 문제인 듯 싶어 언급한다. &lt;br /&gt;&lt;br /&gt;Thomas는 tasklist_lock을 RCU로 바꾸려는 노력 가운데, 몇몇 코드들이 RCU를 잘못사용하고 있는 case를 &lt;br /&gt;발견하였다. 가장 흔히 하는 실수가 rcu_read_[un]lock을 사용하지 않는 것이다. &lt;br /&gt;&lt;br /&gt;개발자들이 그런 실수를 하는 이유는 quiescent state를 보장받기 위해 해당 CPU의 preemption을 &lt;br /&gt;disable하면 충분하다고 판단하였기 때문이다. 맞다. Hierarchical RCU가 merge되기 전까지는 말이다. &lt;br /&gt;&lt;br /&gt;HRCU는 RCU의 grace period를 위해 cpumask와 cpumask의 각 CPU에 해당하는 bit을 보호하기 위한 &lt;br /&gt;spinlock 사용으로 인하여 떨어지는 scalability의 문제를 극복하기 위해 추가된 feature이다.&lt;br /&gt;또한 Classical RCU는 모든 CPU가 quiescent state를 거쳐야 하기 때문에 잠자고 있는 CPU마저도 &lt;br /&gt;모두 깨워야 하는 문제가 있다. 이는 16개의 core중 4개의 core만이 주로 사용되고 있다고 가정할 경우(&lt;br /&gt;흔한 경우라 한다.) power consumption에 있어 큰 문제가 된다. &lt;br /&gt;&lt;br /&gt;이 feature를 사용하게 될 경우, preemption disable만으로는 충분하지 못하다. &lt;br /&gt;개발자들이 흔히 했던 실수라는 것은 caller가 이미 preemption을 disable하고 있을 경우(또는 &lt;br /&gt;preemption_disable primitive가 이미 포함된 spinlock 구간 또는 interrupt disable 구간),&lt;br /&gt;굳이 rcu_read_lock을 호출하지 않았던 것이다. 이는 충분히 문제가 되는 경우이며, 진작에 문제가 &lt;br /&gt;터졌어야 정상인데 불행히도 아직까지 CONFIG_TREE_PREEMPT_RCU가 널리 사용되지 않고 있었기 때문이다. &lt;br /&gt;&lt;br /&gt;이러한 부분들이 수정되가며 점점 tasklist_lock 또한 RCU로 바뀌어가고 있다.&lt;br /&gt;이제 정말 얼마 안 남은 것 같다. rwlock이 사라질 날이.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6421738523389223931?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6421738523389223931/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6421738523389223931&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6421738523389223931'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6421738523389223931'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/12/rcu-mistakes.html' title='RCU mistakes'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2182381925285998539</id><published>2009-12-13T23:47:00.001+09:00</published><updated>2009-12-13T23:51:08.409+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Eliminating rwlocks and IRQF_DISABLED</title><content type='html'>&lt;a href="http://lwn.net/Articles/364583/"&gt;http://lwn.net/Articles/364583/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;조만간 rwlock이 커널에서 사라질 것 같다. &lt;br /&gt;rwlock은 unfair 하기로 유명한 lock이다. &lt;br /&gt;&lt;br /&gt;write side는 reader side가 모두 release될 때 까지 기다려야 하며, 심지어는 &lt;br /&gt;기다리는 도중 새로운 reader side들 막지 못한다. 그러므로 계속되는 reader side는&lt;br /&gt;system의 live lock 상황을 유발할 수 있게 된다. &lt;br /&gt;&lt;br /&gt;위와 같은 상황은 상당히 발생하기 드물기는 하지만 최근 Nick은 이 문제로 인하여&lt;br /&gt;심하게 performance regression이 발생하는 문제를 report하였으며 regression을 &lt;br /&gt;발생시키지 않으며 fair한 rwlock 구현을 생각하고 있다. &lt;br /&gt;&lt;br /&gt;이를 위한 soluation으로는 reader side 의 lock grab을 write side가 기다리고 있는 &lt;br /&gt;한 허용하지 않게되면 간단하다. 허용하지 않겠다는 것은 reader side를 block시키겠다는 &lt;br /&gt;것인데 말만큼 간단한 문제가 아니다. 이는 rwlock이 nesting이 허용되는 primitive를 &lt;br /&gt;근간으로 한다. &lt;br /&gt;&lt;br /&gt;예를 들어 Processor 1에서 reader side의 lock을 hold하고 있는 상태에서 &lt;br /&gt;Processor 2에서 해당 자원의 write lock을 요구한다고 하자. &lt;br /&gt;Processor 2의 task는 spinning하게 될 것이다. 이때 다시 Processor 1이 interrupt되며 &lt;br /&gt;interrupt handler안에서 해당 자원을 다시 read lock하게 될 경우 deadlock 상황이 발생 &lt;br /&gt;할 수 있게 된다. &lt;br /&gt;&lt;br /&gt;또 다른 해결책으로써는 lock을 잡을 때 IRQ를 disable해버리면 쉽게 해결 된다. &lt;br /&gt;하지만 커널 전체의 regression은 이로 말할 수 없게 될 것이다. &lt;br /&gt;&lt;br /&gt;rwlock에 대해서는 오랫동안 커널내에서 없애자는 움직이이 있어왔다. rwlock의 cost가 &lt;br /&gt;일반 spinlock에 비해 상당하기 때문이다. 그러므로 lock에서 소모되는 cost보다 &lt;br /&gt;훨씬 큰 benefit이 있지 않는 한 rwlock을 사용하는 것은 무모한 일이다. &lt;br /&gt;그래서 많은 rwlock들이 spinlock, RCU등으로 바뀌어 왔다. rwlock을 spinlock으로 &lt;br /&gt;바꾸는 것은 굉장히 쉬운 일이지만 문제는 tasklist_lock이다. &lt;br /&gt;&lt;br /&gt;이 lock은 커널의 core에서 많이 사용되어지고 있으며, 굉장히 critical한 fast path에서 &lt;br /&gt;사용되고 있다. 더욱 큰 문제는 tasklist_lock의 오남용은 실제 lock이 보호하는 것이 &lt;br /&gt;어떤 data인지 현재 명확하지 않고 있다는 것이다. 그러므로 함부로 lock을 바꿔서 생기게 &lt;br /&gt;되는 performance regression, stale data 문제등을 한번에 해결하기는 쉽지 않은 &lt;br /&gt;일이 되어 버렸다. 그래서 많은 커널 개발자들은 tasklist_lock을 손대는 것을 &lt;br /&gt;꺼려하여 왔다. &lt;br /&gt;&lt;br /&gt;하지만 Thomas Gleixner가 이 문제를 해결하기 위해 칼을 빼들었다. LWN의 기사가 &lt;br /&gt;나올때까지는 어떤 움직임도 없었지만 최근 LKML에 tasklist_lock을 없애기 위한 patch들이 &lt;br /&gt;포스팅 되고 있다. Thomas Gleixner가 이 문제를 해결하게 되면 나머지 rwlock은 쉽게 &lt;br /&gt;제거될 수 있다. 결국 커널의 rwlock을 볼 날도 이제 얼마 남지 않았다. &lt;br /&gt;&lt;br /&gt;IRQF_DISABLED&lt;br /&gt;&lt;br /&gt;오래전 리눅스는 top half자체도 자체도 "fast", "slow"로 나눠져 있었다고 한다. &lt;br /&gt;해서 fast interrupt handler는 모든 IRQ를 disable한 상태에서 빠르게 처리를 했고, &lt;br /&gt;slow irq interrupt handler는 IRQ를 enable하여 다른 IRQ의 처리를 허용한 상태에서&lt;br /&gt;동작하였다고 한다. 그렇지 않게 되면 다른 더 중요한 인터럽트들의 처리를 지연시켜 &lt;br /&gt;전체적인 시스템의 성능을 down시켰기 때문이다. &lt;br /&gt;&lt;br /&gt;하지만 점차 CPU의 성능이 좋아지고, Device들이 똑똑해지며 device driver들 또한 &lt;br /&gt;성숙하여 점차 IRQ를 enable하고 처리해야 하는 slow path가 점차 사라지게 된 것이다. &lt;br /&gt;이에 요즘 드라이버 개발자들은 인터럽트 핸들러를 등록할 때 IRQ를 enable하고 실행해야 &lt;br /&gt;할지 말아야 할지 조차 신경쓰지 않는다. 그럼에도 불구하고 여전히 인터럽트 핸들러를 &lt;br /&gt;등록할 때 우리는 인수를 신경써야 한다. 게다가 더 재밌는 것은 shared interrupt handler들은 &lt;br /&gt;IRQ를 disable되어 실행된다는 것을 보장받을 수 조차 없다는 것이다. 왜냐하면 해당 &lt;br /&gt;IRQ line에서 실행된 다른 interrupt handler가 IRQ를 enable할 수 있기 때문이다. &lt;br /&gt;&lt;br /&gt;해결책은 간단하다. IRQF_DISABLED 인수를 없애버리고 모든 IRQ handler가 실행될 때 &lt;br /&gt;IRQ를 disable하는 것이다. 하지만 여전히 IRQ를 enable하고 실행해야 할 상황은 있다. &lt;br /&gt;예를 들어 A interrupt handling의 time이 여전히 길다던가, 또는 A interrupt handling은 &lt;br /&gt;B의 interrupt handling에 의존적이라던가. 이와 같은 경우를 해결하기 위해서는 먼저 긴 &lt;br /&gt;시간이 길어지지 않게, 서로 다른 2 IRQ에 의존적이지 않게 redesign을 하는 것과, &lt;br /&gt;또는 interrupt handler를 thread IRQ handling으로 처리되게 바꾸는 것이다. &lt;br /&gt;thread IRQ handling은 선천적으로 모든 IRQ가 enable된 상태에서 동작하는 특성을 &lt;br /&gt;가지고 있기 때문이다. 그래도 안될 경우 마지막 보루로써 IRQF_NEEDS_IRQS_ENABLE를 &lt;br /&gt;사용하는 것이다. &lt;br /&gt;&lt;br /&gt;현재로선 어떻게 될지 명확하지 않지만 머지 않아 모든 IRQ hanlder들은 IRQ를 &lt;br /&gt;disable한 상태로 수행되게 될 것이며, 해당 요구를 만족하지 못하는 드라이버들의 개선이 &lt;br /&gt;이루어질 것으로 보인다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2182381925285998539?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2182381925285998539/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2182381925285998539&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2182381925285998539'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2182381925285998539'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/12/eliminating-rwlocks-and-irqfdisabled.html' title='Eliminating rwlocks and IRQF_DISABLED'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6301022685123483012</id><published>2009-11-15T21:45:00.001+09:00</published><updated>2009-11-15T23:03:35.966+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Toward a smarter OOM killer</title><content type='html'>&lt;a href="http://lwn.net/Articles/359998/"&gt;http://lwn.net/Articles/359998/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;최근 Kame는 OOM patch series의 review를 부탁했다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://lwn.net/Articles/359886/"&gt;http://lwn.net/Articles/359886/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이 문제는 얼마전 mailing list에 올라왔던 어떤 응용 개발자의 한건의 report에서 시작한다.&lt;br /&gt;&lt;br /&gt;시스템의 메모리가 부족하여 OOM이 발생하였는데, 실제 물리 메모리를 많이 사용하던 &lt;br /&gt;프로세스는 따로 있는데 X 또는 Gnome-Session이 죽는 경우가 발생한다는 것이다. &lt;br /&gt;이 문제를 파악해본 결과 우리는 현재 OOM의 victim 선정에 다소 문제가 있다고 &lt;br /&gt;판단하였다. &lt;br /&gt;&lt;br /&gt;Victim을 선정하는 데 있어, 현재 실행중인 프로세스의 가상 메모리 주소와&lt;br /&gt;그 프로세스의 하위 프로세스들이 사용하는 가상 메모리 크기를 고려하는 것이&lt;br /&gt;make sense하지 않다고 생각한 것이다. &lt;br /&gt;&lt;br /&gt;위와 같은 알고리즘 덕택에 gnome-session이나 X와 같이 많은 자식 또는 많은 라이브러리를 &lt;br /&gt;사용하는 프로세스들은 실제 사용되는 물리 메모리와는 상관없이 상당히 큰&lt;br /&gt;oom_score를 갖게 된다. &lt;br /&gt;&lt;br /&gt;이에 barrios는 vm size가 아닌 rss size를 고려하기를 제안하였으며,&lt;br /&gt;이를 바탕으로 kame가 구현하기 시작한 것이 이번 LWN의 주제인 OOM killer 패치이다. &lt;br /&gt;&lt;a href="http://lkml.org/lkml/2009/10/27/26"&gt;&lt;br /&gt;http://lkml.org/lkml/2009/10/27/26&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Kame와 barrios는 fork-bomb process를 구별하는 방법에 관해서도 의견을 나누었었지만, &lt;br /&gt;barrios의 의견은 커널이 그것 까지 고려하는 것은 overhead가 크다는 것이었고, &lt;br /&gt;그렇게 해서 알수 있다하더라도 정확한 구별을 할 수 없어 결국 innocent process가 여전&lt;br /&gt;히 죽임을 당할 수 있다고 판단하였다. 이에 kame는 barrios 의견에 동의하였으며, &lt;br /&gt;최근 KDE가 session manager를 위해 oom_adjust를 조정하도록 변경되었다는 점에 주목하며&lt;br /&gt;일단락을 맺는 것으로 생각하였으나, 얼마 후 이 patch series를 만들었던 것이다. &lt;br /&gt;&lt;br /&gt;이 패치에 대한 첫 인상은 굉장히 인상적이라는 것이다. 패치의 주된 내용은 다음과 같다. &lt;br /&gt;&lt;br /&gt;1. fork-bomb process 식별 방법, &lt;br /&gt;2. 오랫동안 실행되며 찔끔찔금 메모리 누수를 하는 프로세스 식별 방법&lt;br /&gt;3. low memory를 가장 많이 사용하는 프로세스 식별 방법.&lt;br /&gt;4. kill해서 가장 많은 메모리를 회수할 수 있는 프로세스&lt;br /&gt;5. 최근 실행된 프로세스들에게 페널티를 주는 루틴의 삭제&lt;br /&gt;&lt;br /&gt;위에 열거한 것들이 의미하는 것은 fork-bomb 프로세스, 메모리 누수 프로세스, &lt;br /&gt;low memory를 많이 사용하는 프로세스, 현재 가장 많은 물리 메모리를 &lt;br /&gt;사용하고 있는 프로세스를 kill하겠다는 것이다. 이 중에 low memory 문제는 &lt;br /&gt;메모리 할당에 있어 low memory를 필요로 할때, (즉 커널이 물리 메모리를 필요로 &lt;br /&gt;하는 경우가 대부분 이 경우에 속한다|) low memory를 많이 사용하는 프로세스를 &lt;br /&gt;kill하겠다는 것이고, 나머지는 일반적인 경우이다. &lt;br /&gt;&lt;br /&gt;LWN에서도 언급한 것과 같이 이 패치에 대해서 우려의 목소리가 있다. 너무 급진적인&lt;br /&gt;변경이라는 것이다. 그 우려의 목소리가 barrios의 목소리이다. &lt;br /&gt;&lt;br /&gt;개인적으로 barrios는 fork bomb detector는 현재의 OOM heuristic에 add되어 사용될 수 &lt;br /&gt;있을 것이라고 생각하였지만, 나머지들은 OOM hurisitic 계산의 큰 변경은 현재와는 &lt;br /&gt;상당히 다르기 때문에 차근차근 하나씩 변경해 나가는 것이 이미 널리 사용되고 있는 &lt;br /&gt;상용 운영체제의 문제 해결 과정이라고 생각한다. &lt;br /&gt;&lt;br /&gt;최근 이 패치는 아직 RFC 단계이며, swapout page의 수를 체크하는 것 까지 mm tree에&lt;br /&gt;merge되었으며 아직 갈길이 멀다. 이 문제는 위에서 언급하지 않았는데 swapout된 &lt;br /&gt;페이지를 많이 갖는 것은 그 만큼 많은 메모리를 사용했다고 볼 수도 있지만, 꼭 &lt;br /&gt;그렇다고만은 볼 수 없으며, OOM killer가 이런 프로세스를 죽인다고 해서 현재 가용한 &lt;br /&gt;물리 메모리를 확보하는 것은 아니다. &lt;br /&gt;&lt;br /&gt;어쨌든 swap page count는 꼭 이 경우가 아니더라도 여러가지 유용함으로 현재 merge가&lt;br /&gt;된 상태이다. &lt;br /&gt;&lt;br /&gt;barrios는 OOM에 관한 또 다른 생각을 가지고 있는데 기회가 되면 나중에 한번 더 &lt;br /&gt;정리하도록 한다. 왜냐하면 고이자던 아들이 깨고 말았다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6301022685123483012?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6301022685123483012/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6301022685123483012&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6301022685123483012'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6301022685123483012'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/11/toward-smarter-oom-killer.html' title='Toward a smarter OOM killer'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6876617868903354100</id><published>2009-11-08T20:38:00.000+09:00</published><updated>2009-11-08T20:38:39.857+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>How Google uses Linux</title><content type='html'>&lt;a href="http://lwn.net/Articles/357658/"&gt;http://lwn.net/Articles/357658/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;구글보다 더 많이 Linux를 사용하는 조직은 없을 것이다. 하지만 kernel community는 &lt;br /&gt;구글이 어떻게 리눅스를 사용하고 있으며 어떤 문제들을 겪고 있는지 아는 바가 거의 없었다.&lt;br /&gt;왜냐하면 구글은 kernel community에 모습을 잘 드러내지 않기 때문이다. 기껏해야 &lt;br /&gt;David Rientjes, Paul Manage정도가 주로 활동을 하고 있으며, 지금 우리나라의 개발자들이&lt;br /&gt;관심이 많은 구글의 Android kernel 개발자들은 메일링 리스트에서 가끔 눈에 띄긴 하지만&lt;br /&gt;그리 active하게 활동하진 않는다. 구글의 Android 커널 팀은 오늘의 주제와는 관련 없는 &lt;br /&gt;팀이며 오늘의 얘기는 구글의 서버를 maintain하고 있는 커널팀에 대한 얘기이다.&lt;br /&gt;&lt;br /&gt;이번 JLS(Japan Linux Symposium)에서 구글의 커널팀 Mike Waychison은 Linux kernel community&lt;br /&gt;에게 아주 흥미로운 주제들 몇가지 던지고 갔다. 비록 barrios는 JLS를 참가할 수 없어 &lt;br /&gt;직접들을수는 없었지만역시나 Jonathan Corbet이 잘 정리를 해주어서, LWN 기사로나마 &lt;br /&gt;그날의 흥미로움을 대신 전한다.&lt;br /&gt;&lt;br /&gt;생각보다 구글의 커널 조직은 크지 않았다. 대략 30명 정도의 개발자로 이루어져있으며 &lt;br /&gt;Andrew Morton은 이 팀에 속하지 않는 것으로 판단된다. Kernel의 형상관리는 Git이 아니라 &lt;br /&gt;Perforce라는 툴을 사용한다고 한다. 시작을 관리 툴을 언급하며 Git을 사용하지 않는다는 &lt;br /&gt;것에 대해 멋적어서인지 웃음으로 시작하였다고 한다. 리눅스 커널을 Git을 사용하여 관리하지&lt;br /&gt;않는다는 것이 그 만큼 창피한 일이 되어버린 것이다. 구글의 Perforce에는 단지 하나의 &lt;br /&gt;base tree만이 있을 뿐이며, 모든 개발자들이 그곳에 commit하고 있다. &lt;br /&gt;17개월마다 mainline kernel을 base로 그 tree를 다시 rebase하고 있어 항상 porting에 &lt;br /&gt;애를 먹는다고 한다. Porting이 정상적으로 동작하기 시작하면 6개월마다 내부 release를 &lt;br /&gt;한번씩 한다. 그들이 Porting에 애를 먹는 것은 그들의 feature가 드라이버들이 아닌 &lt;br /&gt;core 패치들이기 때문이다. 이를 미루어 볼때 30여명의 core 개발자들로 이루어진 구글의&lt;br /&gt;커널팀이 마냥 부럽기만 하다. &lt;br /&gt;&lt;br /&gt;구글은 이와 같은 작업을 2.4.18부터 시작해왔으며 2000개 이상의 패치들 492,000 line정도를 &lt;br /&gt;수정했다고 말하고 있다. 대부분의 작업은 kernel core에 관한 작업들이다. &lt;br /&gt;그래서 더욱 Porting에 있어 더욱 민감하며, 결국 구글은 일의 효율성을 위하여 &lt;br /&gt;mainline kernel community와 더욱 tightly 협력하도록 모든 것을 변경할 계획을 가지고 있다고&lt;br /&gt;말하고 있다. &lt;br /&gt;&lt;br /&gt;구글은 지금 2.6.26을 base로 하여 다시한번 rebase를 진행하고 있다. &lt;br /&gt;2.6.26에 1208개의 패치를 하고 있으며, 300,000 line의 코드가 들어가고 있고, 이중의 25%는 &lt;br /&gt;새로운 feature라고 언급하고 있다. 이에 Linus는 물었다. &lt;br /&gt;"왜 구글은 그러한 기능들을 upstream 올리지 않느냐? 구글은 그 코드들이 창피하냐? &lt;br /&gt;아니면 보안해야 할 사항이냐? 그것도 아니면 내부 프로세스 문제이냐?" 라는 질문에 &lt;br /&gt;Mike는 간단히 "창피하다"라고 말했다. 2.4.18로부터 온 굉장히 ugly stuff라는 것이다. &lt;br /&gt;또한 그러한 feature들이 다른 곳에 도움이 될지도 내부적으로 의문이 든다고 판단하고 &lt;br /&gt;있다는 것이다. 하지만 아마 코드의 반정도는 upstream될 수 있다고 보고 있다. &lt;br /&gt;Mike가 솔직하게 대답하고 있다. 대부분의 회사가 그럴 것이다. 사실 mainline에 merge될 &lt;br /&gt;정도의 code quality로 일을 하는 회사가 Redhat, SUSE, IBM, Intel 정도를 빼고는 &lt;br /&gt;몇이나 있을까? 다들 자신들의 제품의 특성에 맞게 동작할 수준의 코드들로 QA나 Review없이 &lt;br /&gt;일단 동작하기만 하면 넘어갈 것이다. 회사의 특성상 바쁘다는 핑계로, 여력이 없다는 핑계로&lt;br /&gt;말이다. 이렇게 넘어가자고 한 관리자의 말에 두 손을 들어버리면 결국 나중 그 관리안된 코드를&lt;br /&gt;기반으로 눈덩이처럼 불어난 코드들과 그로 인한 버그들로 그때 그 관리자한테 뒤통수를 맞는 &lt;br /&gt;것은 다시 그 개발자가 될 뿐이다. &lt;br /&gt;&lt;br /&gt;구글은 그 사실을 잘 알고 있으며, 더욱 중요한 것은 실천을 한다는 것이다.&lt;br /&gt;별것도 아닌 기술을 IP라고 포장하여 언제까지나 Close하는 회사들에 비해서는 약간 앞서&lt;br /&gt;있지만 솔직히 구글도 그러고 있을 것이라고는 생각치 못했었는데. barrios는 개인적으로&lt;br /&gt;그렇게 생각하고 있었다.&lt;br /&gt;&lt;br /&gt;현재 구글은 커널 소스 관리를 위해 Git으로 옮겨가고 있으며(이렇게 새로운 형상관리 툴로 &lt;br /&gt;전진해나가는 곳이 있는가 하면 후진하는 곳도 있다. 관리의 효율화와 일원화라는 명목하에 주객&lt;br /&gt;이 전도되는 상황을 barrios는 늘상 보곤한다), 3달마다 한번씩 mainline kernel에&lt;br /&gt;대해 rebase할 계획을 가지고 있다고 한다. 3달마다 한다는 것은 결국 mainline version의 &lt;br /&gt;출시와 발을 맞추겠다는 의도로 생각할 수 있으며, 그렇게 하려는 이유는 결국 개발자들의 &lt;br /&gt;code maintainace를 좋게 만들기 위해서 그리고 upstream kernel과 보조를 맞추기 위해서이다.&lt;br /&gt;왜 upstream kernel과 보조를 맞추어야만 하는지에 대해 따로 설명하지 않겠다. 최소한&lt;br /&gt;이 블로그의 글을 보는 사람이라면 이 문제에 대해서는 barrios가 굳이 설명을 안해도 될 것이다.&lt;br /&gt;&lt;br /&gt;지금까지 구글이 이렇게 mainline kernel과 괴리가 있었던 것은 3가지 이유에서 기인한단고&lt;br /&gt;barrios는 생각한다.&lt;br /&gt;&lt;br /&gt;첫째로 그들이 사용하는 커널은 소프트웨어 회사 중 가장 큰 server farm을 자랑하는 server&lt;br /&gt;들을 위한 커널이며, &lt;br /&gt;둘재로 그들은 그 커널을 마음대로 주무를 수 있는 capability를 가지고 있다는 것이다. &lt;br /&gt;셋째는 하지만 그들은 게을렀다는 것이며 이제는 그 결정을 다시 생각해야 할 때라는 것을&lt;br /&gt;알고 JLS에서 세션 하나를 맡아 주었다는 것이다. ^^; &lt;br /&gt;&lt;br /&gt;기사에 구글이 mainline kernel을 사용하며 겪었던 문제들을 열거하고 있다. &lt;br /&gt;하나씩 살펴보기로 하자. &lt;br /&gt;&lt;br /&gt;구글은 CFS로 넘어간 스케줄러에 대해서 별로 좋아하지 않고 있다.&lt;br /&gt;구글은 user space lock mechanism을 위한 별도의 library를 가지고 있는 듯하다. &lt;br /&gt;이에 문제가 발생한 것은 sched_yield의 semantics가 CFS가 도입되며 변했다는 것이다. &lt;br /&gt;기존의 semantic은 가장 높은 우선순위의 태스크가 sched_yield를 호출할 경우, &lt;br /&gt;같은 우선순위의 다른 task가 없다면, 자신이 다시 제어권을 받을 수 있음을 보장하였다. &lt;br /&gt;하지만 CFS에서는 그렇지가 못하다. 이는 그들이 사용하는 locking관련 라이브러리에서의 &lt;br /&gt;high priority 쓰레드들의 sched_yield 함수 호출은 다른 task로의 스케줄링으로 이루어지며 &lt;br /&gt;많은 load balancing을 현상을 만들어 낸다는 것이다. 구글은 16~32개의 core의 &lt;br /&gt;시스템에 5000개의 쓰레드들을 돌리고 있기 때문에 이는 심각한 성능 문제를 야기할 수 있다.&lt;br /&gt;&lt;br /&gt;무엇보다 그런 big thread design의 문제는 mmap_sem의 lock contention이 심하다는 것과 signal을 large thread group에보낼때 많은 run queue들의 lock contention이 심하다는 것이다. &lt;br /&gt;특히 mmap_sem에 관해서는 다음의 시나리오도 가능하다. 쓰레드 A,B,C가 있다고 가정하자.&lt;br /&gt;&lt;br /&gt;A - readlock - Wait I/O&lt;br /&gt;B - writelock -&gt; Wait to complete readlock&lt;br /&gt;C - readlock -&gt; Wait to complete B's writelock&lt;br /&gt;&lt;br /&gt;즉, A의 readlock으로 인해 B가 대기하게 되고, B의 writelock으로&lt;br /&gt;인해 C의 readlock이 대기하는 상황에서, 갑작스레 A가 OOM kill이 된다고&lt;br /&gt;가정하자. A,B,C를 포함하는 프로세스에 대한 mm관련 일들은 모두 halt될 것이며&lt;br /&gt;이 프로세스가 어떤 프로세스냐에 따라 시스템의 halt까지 유발할 수도 있다. &lt;br /&gt;&lt;br /&gt;mmap_sem 관려해서는 현재 Christoph가 per-cpu allocator와 mutex를 혼용하는 &lt;br /&gt;방법에 대한 새로운 패치를 내었다. barrios는 그 패치에 대한 몇가지 문제점을 &lt;br /&gt;지적해 놓은 상태이며 그 중의 일부 아이디어가 반영되어 다음 릴리즈에 반영되었다. &lt;br /&gt;하지만 그보다 심각한 문제가 있기때문에 아직은 RFC 단계이며, 그 패치가 merge가 &lt;br /&gt;될 경우, mmap_sem의 readpath는 RW semaphore를 사용하는 것이 비하여 굉장히 빨라질 수 있다. &lt;br /&gt;&lt;br /&gt;메모리 관리 측면에서는 dirty bit의 관리가 변경되며 kswapd는 small I/O operation들에&lt;br /&gt;대해 예전에 비하여 잦은 writeout을 발생시키게 된다. 이는 다른 writeback들을 &lt;br /&gt;starving시키게 될 수 있다. 이 문제는 2.6.32에 merge될 per-BDI writeback에 &lt;br /&gt;의해 fix될 수 있다. &lt;br /&gt;&lt;br /&gt;구글은 시스템의 성능이 overload되는 것을 막기 위해서 OOM killer를 사용하고 있다.&lt;br /&gt;하지만 위에 언급한 것과 같이 oom kill되는 프로세스가 mutex를 hold하고 있을 경우,&lt;br /&gt;시스템은 큰 문제에 빠질 수 있게 되는 문제를 가지고 있다. Mike가 궁금해했던 &lt;br /&gt;"memory가 tight하다면 단순히 allocation을 실패시키면되지, 왜 그렇게 열심히 &lt;br /&gt;OOM kill을 수행하는지"에 대한 답변은 kernel의 allocation은 그렇게 할 수 있으며 &lt;br /&gt;이미 그렇게 하고 있다. 이는 OOM이 아니라  page allocaion failure이다. &lt;br /&gt;하지만 user page는 그렇게 할 수 없다. 그 이유는 Linux kernel은 Demand Paging을 &lt;br /&gt;사용하기 때문에 allocation을 하는 시점과 paging in되는 시점이 다르기 때문이다. &lt;br /&gt;더 자세한 이야기는 오늘의 주제가 아니니 넘어가도록 하자. &lt;br /&gt;&lt;br /&gt;그래서 구글은 지금 무엇을 하고 있는가?&lt;br /&gt;구글은 그들의 work들을 3가지로 분류한다.&lt;br /&gt;&lt;br /&gt;"latency sessitive", "production batch", "best effort" 그래서 이 분류들을&lt;br /&gt;fake NUMA node 기능을 이용하여 분리하고 각 job들을 성격에 맞춰 하나 이상의&lt;br /&gt;노드들에 assign하는 것이다. 구글이 add한 기능은 barrios의 충분한 관심을 끈다.&lt;br /&gt;NUMA-aware VFS lru를 적요하고 있기 때문이다. &lt;br /&gt;이는 예전에 Nick Piggin이 했던 것과 유사하며 그는 구글의 코드들을 보길 원해왔다. &lt;br /&gt;&lt;br /&gt;구글은 SCHED_GIDLE 스케줄링 클래스를 만들었다. 어떤 spare CPU도 있지 않을 경우, &lt;br /&gt;이 클래스에 job들은 실행되지 않을 것이다. 이때 발생할 수 있는 priority inversion 문제를 &lt;br /&gt;풀기 위해 SCHED_GIDLE 프로세스들이 커널에서 sleep하게 될때는 일시적으로 priority를 &lt;br /&gt;높이게 된다. &lt;br /&gt;&lt;br /&gt;구글의 I/O scheduleing의 경우에는 proportional I/O scheduling을 사용하고 있다고 &lt;br /&gt;한다. 그것 말고도 구글은 시스템 monitoring을 위한 많은 코드들을 add하고 있어,&lt;br /&gt;disk, network traffic을 monitor하고 기록해두어 나중에 operation 분석을 위해 &lt;br /&gt;사용한다고 한다. &lt;br /&gt;&lt;br /&gt;다음은 구글은 2010년까지의 목표이다. &lt;br /&gt;&lt;br /&gt; * CPU limitations - latency-sensitive한 태스크들에게 더 높은 우선 순위 접근을 &lt;br /&gt;주면서도 전체 시스템을 장악하는 것은 막게 하겠다는 것.&lt;br /&gt;&lt;br /&gt; * RPC-aware CPU scheduleing - 들어오는 RPC traffic을 살펴보고 어떤 프로세스를 응답으로 깨울 것이며 그 wakeup이 얼마나 중요한 지를 결정하는 것.&lt;br /&gt;&lt;br /&gt; * Delayed scheduling - 대부분의 쓰레드들에게 있어 latency는 중요하지 않다. 하지만 kernel은 RPC msg가 들어왔을 때 즉시 그 쓰레드들을 실행시키려고 시도한다. 이 msg들은 CPU들에 고르게 분산되지 않아 심각한 load balancing 문제를 야기한다. 그래서 쓰레드들은 delayed scheduling으로 tagging될 수 있다. 즉, wakeup이 도달하면 즉시 run queue에 들어가는 것이 아니라 실제로 runnable해지기 전에 다음 global load balancing operation이 발생할때 까지 기다린다. &lt;br /&gt;&lt;br /&gt; * Idel cycle injection - machine을 항상 최고 power로 실행할 수 있도록 power-management를 하겠다는 것, 하지만 system이 melt down되게 하지는 않겠다는.&lt;br /&gt;&lt;br /&gt; * 커널 메모리 사용까지 accouting하는 향상된 memory controller&lt;br /&gt;&lt;br /&gt; * offline memory - 저렴한 가격으로 메모리를 구입하는 것이 점점 어려워 진다는 판단하에 단지 몇 개의 cell만이 bad가 났음에도 전체 메모리를 교체하는 것은 옳지 않다는. 해서 HWPOISON을 통해 bad page들만을 따로 관리하겠다는. &lt;br /&gt;&lt;br /&gt; * 동적으로 huge page들을 assemble하고 broken down하기 위한 방법&lt;br /&gt;&lt;br /&gt; * block layer overhead를 줄여 high-speed flash의 속도를 최대한 내겠다는. block layer에서 disk 가속을 위해 flash를 사용하겠다는 것이다. &lt;br /&gt;&lt;br /&gt;마지막으로 Mike는 몇가지 흥미있는 주제들을 던지며 그날 세션을 끝마쳤다. &lt;br /&gt;구글이 원하는 것 중의 하나는 file system metadata를 memory에 pinning하는 것이다. &lt;br /&gt;해서 I/O request를 service하는데 걸리는 시간을 bound하겠다는 것이다. &lt;br /&gt;디스크로부터 하나의 블록을 읽는데 걸리는 시간은 알수 있지만, &lt;br /&gt;관련 metadata가 메모리에 있지 않은 경우, 한번 이상의 disk I/O 이상이 필요해진다. &lt;br /&gt;이것은 시스템을 느리게 만들고 있다고 말하고 있다. 구글은 현재 file data를 &lt;br /&gt;user space에서 raw disk device로부터 직접 읽음으로써 이러한 문제를 우회하고 있다고 한다. &lt;br /&gt;하지만 언제까지 그렇게 할 수는 없고, 이제는 멈추고 싶어한다. &lt;br /&gt;&lt;br /&gt;다른 문제는 caching advise를 제공하기 위한 system call overhead를 낮추는 것이다. &lt;br /&gt;이 문제는 명확하지 않다. &lt;br /&gt;&lt;br /&gt;Anyway, 이번 구글의 세션은 kernel community가 가장 큰 customer로부터 많은 걸 배울 수 &lt;br /&gt;있었던 성공적인 session이었다. 구글은 앞으로 더욱 큰 결실을 맺기 위해 community와 &lt;br /&gt;협업을 더 적극적으로 할 계획을 가지고 있으며 이는 모두에게 더 훌륭한 커널을 안겨줄 수 &lt;br /&gt;있는 좋은 기회가 될 것이다. &lt;br /&gt;&lt;br /&gt;barrios는 위와 같은 선진 소프트웨어 회사들의 그 중에서도 커널 팀들의 행보를 지켜보며, &lt;br /&gt;우리의 현수준을 직시하고, 우리가 가야할 길에 대한 생각을 멈추지 않을 것이다. &lt;br /&gt;비록 지금은 먼 것 처럼 느껴지더라도, 조만간 쓸 일이 있지 않을까 한다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6876617868903354100?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6876617868903354100/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6876617868903354100&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6876617868903354100'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6876617868903354100'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/11/how-google-uses-linux.html' title='How Google uses Linux'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2339878134038110741</id><published>2009-09-16T08:55:00.002+09:00</published><updated>2009-09-16T09:31:34.548+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>2.6.32 merge plan</title><content type='html'>&lt;a href="http://"&gt;http://lkml.org/lkml/2009/9/15/471&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;2.6.32를 위한 merge plan이 발표되었습니다. by Andrew Morton. &lt;br /&gt;것이 의미하는 것은 그 동안 mm tree에서 잘 성숙되어 온 patch들중, &lt;br /&gt;Andrew Morton과 Subsystem maintainer들에 의해 어떤 patch들을&lt;br /&gt;이번에 mainline으로 밀어 넣을 것인지를 결정하는 일입니다. &lt;br /&gt;&lt;br /&gt;밀어 넣어진 patch들 또한 rc1~rc8 or rc9이 될 때 까지 약 3개동안 mainline&lt;br /&gt;tree에서 테스트를 거치게 됩니다. &lt;br /&gt;&lt;br /&gt;이번 2.6.32를 위한 patch들 중 특이한 점은 memory management patch들이 &lt;br /&gt;대거 포함되었다는 겁니다. 즉, 속된 말로 잘 되면 대박, 못되면 쪽박이 될 수도 있습니다.&lt;br /&gt;(제가 개발팀장이라면 2.6.32 커널은 되도록 피하라고 지시할 것 같습니다.)&lt;br /&gt;&lt;br /&gt;memory management 쪽의 패치가 많을 수 있었던 것은 “후지쯔 가이”들, &lt;br /&gt;즉 일본인들이 mm 쪽의 개발에 부지런히 참여했었고,&lt;br /&gt;늘상 부지런하던 Hugh, Rik, Mel, 그리고 VFS layer에 주로 놀던 Wu의 mm 참여,&lt;br /&gt;반대로 mm쪽에서 많은 활약을 하던 Nick의 VFS layer로의 이동.  &lt;br /&gt;그리고 한국의 hobbyist정도가  정도가 바쁘게 움직인 덕입니다. ^^&lt;br /&gt;&lt;br /&gt;그럼 3달동안 어떤 regression들이 생기는 지 두고 보기로 하죠. &lt;br /&gt;&lt;br /&gt;꼬랑지) &lt;br /&gt;&lt;br /&gt;MM쪽의 패치를 만들어 나가는 과정은 약간 복잡합니다. &lt;br /&gt;물론 다른 쪽도 얼마든지 복잡해 질 수 있지만, MM쪽은 시스템에 critical한 &lt;br /&gt;변경을 가하는 것이기 때문에, 하나의 패치에도 여러 사람들이 관계하게 됩니다. &lt;br /&gt;먼저, 최초 문제의 목격자 reporter(Reported-by),&lt;br /&gt;그 문제를 풀기 위한 패치의 저자(signed-off-by),&lt;br /&gt;패치를 review해주는 리뷰어(Reviewed-by)&lt;br /&gt;패치에 대한 승인을 해주는 영향력 있는 인물들의 승락(Acked-by)&lt;br /&gt;패치를 test해주는 테스터(Tested-by),&lt;br /&gt;등이 관계합니다 이밖에도 Andrew Morton은 해당 패치의 관계자들, &lt;br /&gt;즉 그 패치에 대해서 argue가 있었던 사람이나 해당 패치를 꼭 알고 해야&lt;br /&gt;하는 사람들을 patch description에 Cc하곤 합니다. &lt;br /&gt;MM쪽은 이렇듯 하나의 패치를 만들기 위해 많은 사람들이 작업을 하게 되며,&lt;br /&gt;관계하게 됩니다. &lt;br /&gt;&lt;br /&gt;아 그리고 mm tree가 Memory Management Tree가 아닙니다.&lt;br /&gt;쓰고 나니 mm tree가 그럼 무엇의 약자냐고 물어보는 이가 있어 부연합니다. &lt;br /&gt;mm tree는 memory management의 약어이긴 합니다.&lt;br /&gt;하지만 mm tree의 기능은 더 이상 mm만 care하지 않는다는 것입니다. &lt;br /&gt;mm tree는 memory management 뿐만이 아니라 다양한 subsystem들도 포함하며,&lt;br /&gt;마치 예전 홀수 버젼의 test version이라고 생각하시면 대충 맞습니다. &lt;br /&gt;참고로 mmtom은 "MM of the moment or MM of the minute"의 약어입니다. &lt;br /&gt;Andrew도 잊어먹었다고 하더군요.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2339878134038110741?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2339878134038110741/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2339878134038110741&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2339878134038110741'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2339878134038110741'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/09/2632-merge-plan.html' title='2.6.32 merge plan'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6423532592964874509</id><published>2009-09-12T09:20:00.002+09:00</published><updated>2009-09-12T11:37:46.873+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Offline Scheduler</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/8/22/89"&gt;http://lkml.org/lkml/2009/8/22/89&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;최근 mainline의 hot issue중의 하나이다. &lt;br /&gt;multi or many core system에서 CPU중 하나를 스케줄러에서 offline시키고 해당 CPU에&lt;br /&gt;특정 job을 binding하여 OS noise없이 사용하자는 것이다. 즉, task를&lt;br /&gt;특정 CPU에 dedication시키는 설비를 만들자는 것이다.  &lt;br /&gt;시간이 있으신 분들은 그 쓰레드들을 모두 읽어보아라. 현재 약 81개의 쓰레드가 달려 &lt;br /&gt;있는데 상당히 재미있다. barrios의 나쁜 기억력은 모든 내용을 기억할 수 없다.&lt;br /&gt;생각나는 부분들만을 위주로 정리한다. &lt;br /&gt;&lt;br /&gt;먼저 Christoph와 같은 HPC guy는 굉장히 찬성하는 입장이고, Peter, Ingo, Thomas와 &lt;br /&gt;같은 기존 scheduler나 HRT maintainer들은 반대의 입장이다. &lt;br /&gt;Christoph가 찬성하는 이유는 간단하다. 기존까지 약간의 솔루션들이 있었지만,&lt;br /&gt;offline scheduler와 같이 간단하게 모든 OS noise를 제거할 수 있는 방법은 없었다는 &lt;br /&gt;것이다. HPC에서는 CPU 1 cycle이라도 불필요하게 OS를 위해 App가 양보할 수 없다는&lt;br /&gt;생각을 가지고 있기 때문이다. 그 생각은 barrios도 공감한다. 시스템의 주인공은&lt;br /&gt;응용 프로그램들이니깐. 아. Offline scheduler의 동작원리를 간단히 설명하면(&lt;br /&gt;그럴수 밖에 없다. 원래 간단하니까). CPU Hotplug facility를 사용하게 되어 있다.&lt;br /&gt;즉, Offline 시키고 싶은 CPU를 Unplug시켜버리며 미리 등록되어 있던 커널 함수를 &lt;br /&gt;실행시키는 것이다. 이 커널 함수가 결국 태스크의 entry point가 될 것이다. &lt;br /&gt;&lt;br /&gt;그렇다면 Peter, Ingo와 같은 maintainer들이 반대하는 이유는 무엇인가?&lt;br /&gt;문제를 우회하고 있다는 것이다. OS noise에 대한 latency가 문제라면, &lt;br /&gt;해당 문제를 해결하여 Linus system 전반의 문제들을 해결해야지, 그런식의 &lt;br /&gt;work around는 오히려 앞으로 나오게 될 좋은 접근의 다른 시도들을 막을 수 &lt;br /&gt;있다는 것이다. 중요한 이유는 그런 식의 OS의 제어하에 벗어나게 되는 것을&lt;br /&gt;달가워하지 않는 것 같다. 얘기는 다소 잘못된 방향으로 나아가며 Chrisoph와&lt;br /&gt;Perter, Ingo가 감정의 날을 세우다가 Andrew Morton이 한마디 했다. &lt;br /&gt;"Problem State가 무엇이냐?"고 다들 구현을 가지고 따지고 있는 가운데&lt;br /&gt;다시 토론을 본론으로 가져왔다. 또한 Andrew는 것이 필요한 일이고, Design이&lt;br /&gt;깔끔하고, 유지보수가 용이하다면 merge하지 못할 이유가 없다고 입장을 밝혔다.&lt;br /&gt;&lt;br /&gt;여기서 또 다시 Andrew의 view를 알 수 있다. 유지보수의 용이성이다. 제 아무리&lt;br /&gt;좋은 기능을 잘 구현한다 하더라도, 조그만 변경이 시스템에 cirtical한 변경을 &lt;br /&gt;가할 수 있거나, 다른 subsystem의 변경에 민감하게 반응하는 패치라면 Andrew는&lt;br /&gt;상당히 꺼려한다. 왜? 그는 Linux kernel의 maintainer이기 때문이다. 다양한 시도들&lt;br /&gt;중 정말 nice한 것만을 선정하여 잘 유지하는 것이 그의 일이기 때문이다. &lt;br /&gt;&lt;br /&gt;우리도 본론으로 다시 돌아와서, 이때 Thomas가 involve된다. &lt;br /&gt;Thomas는 문제의 핵심을 언급했다. 결국 이 문제는 한 CPU에서 하나의 Task가 &lt;br /&gt;timer interrupt의 방해만 받지 않으면 되지 않겠느냐고 얘기하고 있다. &lt;br /&gt;물론 해당 CPU에 HARD IRQ, SOFT IRQ등의 event가 발생할 수도 있다.&lt;br /&gt;하지만 해당 CPU의 task가 irq를 발생시키는 device와 interaction하지 않는다면 &lt;br /&gt;irq는 다른 CPU쪽으로 affinity를 주면 된다. 그 얘기는 결국 SOFTIRQ도 해당 CPU에서&lt;br /&gt;disable 할 수 있다는 얘기이다. 반대로 그 Task가 특정 device와 interaction한다면&lt;br /&gt;해당 irq를 그 CPU와 affinity를 주면된다. 단 가정은 그 Task만 그 device와 interaction&lt;br /&gt;해야만 할 것이다. 그렇지 않으면 다른 task의 job에 해당 CPU가 시달리게 될 것이다. &lt;br /&gt;&lt;br /&gt;Thomas와 다른 개발자들의 논의 방향은 이 방향으로 흘렀다.&lt;br /&gt;scheduler에서 특정 priority이상으로 설정된 task가 CPU에 binding될때, tick interrupt를&lt;br /&gt;off시켜버리자는 것이다. 다음 그 task가 schedule out될 때 다시 tick interrupt를 enable하고&lt;br /&gt;그때 accounting을 갱신하자는 얘기 중심으로 무게가 쏠리고 있다. &lt;br /&gt;&lt;br /&gt;이 쓰레드에서 중요한 것은 대부분의 개발자들이 needs에 대해서는 공감하고 있다는 것이다.&lt;br /&gt;결국 이 문제는 manycore환경에서 CPU들을 어떻게 잘 활용할 것인가와 연결될 것 같다는게 &lt;br /&gt;barrios의 생각이며 offline scheduler가 굳이 아니더라도 새로운 형태의 task가 OS noise없이&lt;br /&gt;실행 할 수 있는 형태의 기능이 mainine에 merge될 것이라고 생각된다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6423532592964874509?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6423532592964874509/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6423532592964874509&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6423532592964874509'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6423532592964874509'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/09/offline-scheduler.html' title='Offline Scheduler'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-41028049351810280</id><published>2009-09-10T00:55:00.003+09:00</published><updated>2009-09-12T08:38:48.104+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>RT task and mlock race</title><content type='html'>Linux에서의 Real Time? &lt;br /&gt;시작부터 거창하다. 오늘 이 거창한 주제에 대해서 얘기하자는 것은 아니다. &lt;br /&gt;이 주제는 거의 반나절 이상 얘기가 되야하는 주제이고.. &lt;br /&gt;&lt;br /&gt;오늘 얘기하고 싶은 것은 RT task와 Mlock system call과의 문제이다. &lt;br /&gt;사실, Linux RT에 가장 큰 걸림돌은 Memory Subsystem이라고 생각한다.&lt;br /&gt;Ingo나 Robert과 같은 많은 개발자들이 Linux의 RT feature를 향상시키기&lt;br /&gt;위해 다각도로 노력을 해왔지만 아직까지 개척되지 못한 부분이 Memory 부분이다.&lt;br /&gt;&lt;br /&gt;현재 Linux kernel의 memory allocation/reclaim routine은 절대 deterministic&lt;br /&gt;하지 못하기 때문이다. 오늘 이 얘기를 하려고 하는 것이 아니니 여기서 각설하고.&lt;br /&gt;&lt;br /&gt;RT task를 사용하는 환경에서 page fault overhead를 줄이기 위해서&lt;br /&gt;mlock system call을 흔히 사용한다. 또는 Montavista의 RT programming guide를 봐도,&lt;br /&gt;또는 세미나를 들어도 mlock을 사용하라고 권한다. &lt;br /&gt;하지만 다음과 같은 경우 큰 문제를 발생시킬 수 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;1. taskset 0x2 ./test &lt;br /&gt;A. =&gt; Top과 Top 환경에서 숫자 1번 키를 통해 CPU1이 100% 소모되고 있는 것을 확인&lt;br /&gt;2. sudo chrt –fp 55 `pidof test`&lt;br /&gt;A. RT task로 변환 &lt;br /&gt;3. dd if=/dev/zero of=test.dat bs=4K count=1000000&lt;br /&gt;A. 4G의 파일을 생성하는 명령하나 수행&lt;br /&gt;4. .taskset 0x4 /test_mlock &lt;br /&gt;A. 3번째 CPU에서 Memory lock을 수행하는 application 수행&lt;br /&gt;&lt;/blockquote&gt;3번째 CPU에서 실행되는 test_mlock 응용이 mlockall system call에서 &lt;br /&gt;멈추어 더 이상 실행되지 않는 것을 확인할 수 있다. 만일 시스템에 top을 수행시킬 &lt;br /&gt;수 있다면 해당 프로세스의 state를 봐라. 'D' state일 것이다. &lt;br /&gt;그리고 시간이 좀 지나게 되면 운이 좋지 못하면 시스템 전체가 먹통이 되는 현상을 &lt;br /&gt;볼 수 있을 것이다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;./test &lt;br /&gt;&lt;br /&gt;#include &lt;stdio.h&gt;&lt;br /&gt;&lt;br /&gt;int main()&lt;br /&gt;{&lt;br /&gt;int i = 0;&lt;br /&gt;while(1) {&lt;br /&gt;i+=1;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;blockquote&gt;./test_mlock&lt;br /&gt;#include &lt;stdio.h&gt;&lt;br /&gt;#include &lt;sys/mman.h&gt;&lt;br /&gt;&lt;br /&gt;int main()&lt;br /&gt;{&lt;br /&gt;&lt;br /&gt;printf("mlock test\n");&lt;br /&gt;&lt;br /&gt;printf("before mlock\n");&lt;br /&gt;mlockall(MCL_CURRENT|MCL_FUTURE);&lt;br /&gt;printf("after mlock\n");&lt;br /&gt;return 0;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;자. 도대체 시스템에서 무슨 일이 일어났을까?&lt;br /&gt;CPU2에서 RT task가 user space에서 CPU를 100% 소모하며 실행되고 있다. &lt;br /&gt;이때 CPU3에서의 응용 프로그램이 mlockall system call을 수행한다. &lt;br /&gt;mlock system call은 kernel 내부에서 동작할 때, 먼저 per CPU page_vec&lt;br /&gt;에 저장되어 있는 lru pages들을 lru list로 drain하게 되어 있다. &lt;br /&gt;이때 문제가 발생한다. 모든 CPU들의 page_vec에 pages들을 drain하기 위해서&lt;br /&gt;커널은 workqueue를 사용하며 lru drain이 모두 완료될 때 까지 기다린다.&lt;br /&gt;즉 해당 work들을 flush한다는 말이다. 이때 CPU[1,3,4]는 문제가 안된다. &lt;br /&gt;문제가 되는 녀석은 RT task를 수행하고 있는 CPU2이다. &lt;br /&gt;CPU2의 RT task는 자발적으로 제어권을 놓지 않는 한 kenrel은 CPU2를 위한 제어권을&lt;br /&gt;받을 수 없다(timer tick을 제외하고. 하지만 timer tick이 우리의 상황을 해결해&lt;br /&gt;줄 수는 없다.). 그렇게 되면 CPU2의 eventd가 수행될 수 없고, 그 결과 CPU3에서 실행한&lt;br /&gt;lru_add_drain_all(모든 CPU의 page_vec을 flush하는)은 완결될 수 없다.&lt;br /&gt;즉 CPU3의 응용 프로그램은 CPU2에서 수행되고 있는 RT task의 execution time에 &lt;br /&gt;dependency를 갖게 된다. &lt;br /&gt;&lt;br /&gt;문제는 더욱 커질 수 있다. CPU2의 eventd에 pending되어 있던 work들이 수행되지 못할 경우,&lt;br /&gt;그 work의 event 완료를 기다리는 모든 task들은 모두 freeze되는 효과를 볼 것이다. &lt;br /&gt;&lt;br /&gt;이는 결국, 시스템 전체의 hang으로 이어질 수 있다는 것이다. RT task를 무한루프로 생성하는&lt;br /&gt;테스트가 다소 비약일 수 있다고 생각할 수도 있다. 하지만 문제의 요지는 RT task의 무한루프가&lt;br /&gt;아니다. 문제는 CPU3에서 실행된  task가 CPU1에서 실행되고 있는 task보다 더 높은 RT prio를&lt;br /&gt;가질수도 있으며 이와 같은 상황에서의 mlock system call은 priority inversion problem을&lt;br /&gt;만든다는 것이다. 물론 kernel에 많은 priority inversion problem 중의 하나일 뿐이지만,&lt;br /&gt;문제는 mlock system call이 RT task들이 흔히 사용할 수 있다는 데서 있다고 본다. &lt;br /&gt;&lt;br /&gt;barrios는 사실, mlock system call의 경우 굳이 page_vec을 drain할 필요가 없다고 생각한다.&lt;br /&gt;그 이유는 해당 page들은 결국에는 PG_mlocked될 것이며, unevictable list로 옮겨갈 것이기 때문이다. &lt;br /&gt;&lt;br /&gt;다른 개발자들의 의견을 기다려 보자.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-41028049351810280?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/41028049351810280/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=41028049351810280&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/41028049351810280'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/41028049351810280'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/09/rt-task-and-mlock-race.html' title='RT task and mlock race'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4421904803770585360</id><published>2009-09-01T23:15:00.003+09:00</published><updated>2009-09-02T08:33:08.181+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Static Trace Point에 관하여</title><content type='html'>&lt;a href="http://lwn.net/Articles/245671/"&gt;http://lwn.net/Articles/245671/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;좀 지나간 기사이지만, 갑자기 생각이 나서 읽어보았다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Adding a test-and-jump operation to a kernel hot path will always be a hard sell; the cache effects of referencing a set of global marker state variables could also be significant. &lt;/blockquote&gt;&lt;br /&gt;&lt;a href="http://thread.gmane.org/gmane.linux.kernel/568586"&gt;http://thread.gmane.org/gmane.linux.kernel/568586&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Immediate values are used as read mostly variables that are rarely updated. They&lt;br /&gt;use code patching to modify the values inscribed in the instruction stream. It&lt;br /&gt;provides a way to save precious cache lines that would otherwise have to be used&lt;br /&gt;by these variables.&lt;/blockquote&gt;&lt;br /&gt;위의 2개의 link는 kernel marker가 구현될 당시, &lt;br /&gt;관련 기사와 관련 패치의 일부이다. &lt;br /&gt;&lt;br /&gt;인용구를 보면 알겠지만 mainline kernel developer들은 &lt;br /&gt;test-and-jump instruction 하나를 없애기 위해서도 &lt;br /&gt;저렇게 애를 쓴다. 왜냐하면 그 문제를 풀지 못하면 mainline에 &lt;br /&gt;merge되기 어려울 테니. 왜 merge되기 어려울까?&lt;br /&gt;&lt;br /&gt;kernel marker는 kernel의 static trace point의 일부이다. 그 얘기는 커널이 &lt;br /&gt;release되더라도 enable 되어야 한다는 것이다. 이 논리에 대해서 &lt;br /&gt;이해가 가지 않는가?&lt;br /&gt;&lt;br /&gt;static trace point란 것은 dynamic probing과는 성격이 틀리다. &lt;br /&gt;static trace point는 이미 커널의 잘(?) 정의된 &lt;br /&gt;곳에 삽입되어 있어야 한다. 그래서 system administrator들이나 &lt;br /&gt;kenrel developer들은 기존에 잘 정의되어 있는 trace point를 기반으로 &lt;br /&gt;시스템의 성능을 분석하기 때문이다. 그러므로 사실 static trace point의 &lt;br /&gt;hot issue는 성능문제도 있지만 어떤 곳에 static trace point를 &lt;br /&gt;정의할 것이냐가 더 중요하다. &lt;br /&gt;&lt;br /&gt;다시 본론으로 들어가서 test-and-jump instruction을 제거하기 &lt;br /&gt;위해서 왜 그렇게 애를 쓰는가? 기껏해야 instruction 하나 더 &lt;br /&gt;수행하는 것인데? 라고 묻는다면. &lt;br /&gt;&lt;br /&gt;test-and-jump중 test를 위해 사용되는 shared variable은 귀중한 &lt;br /&gt;cache line을 한 line 소모한다. 그런데 shared varible은 하나일까?&lt;br /&gt;&lt;br /&gt;1. static trace point 전체를 enable/disable할수 있으면 좋을까? 아님,&lt;br /&gt;각각의 trace point를 enable/disable할 수 있으면 더 좋을까?&lt;br /&gt;2. 그럼 그런 shared varibale가 하나가 필요할까? 두개가 필요할까?&lt;br /&gt;3. 그럼 cache line을 하나만 소비할까? 두개 소비할까?&lt;br /&gt;4. 그런데 이 trace point가 kernel의 hot path 중 하나에 들어간다면. &lt;br /&gt;test를 위해서는 memory를 referencing해야 하고, 그럼 cache line이&lt;br /&gt;하나가 소비될 것이고, 그 얘기는 worst case 기존에 cache line이 &lt;br /&gt;하나 eviction되야 하고, hot path라면 이게 반복될 것이고... &lt;br /&gt;&lt;br /&gt;결국, trace point가 없을 때에 비해 working set의 많은 부분들이 &lt;br /&gt;cache line에서 eviction될 수 있다는 것이다. &lt;br /&gt;&lt;br /&gt;왜 갑자기 뜬금없이 barrios가 잘알지도 못하는 kernel의 marker에 &lt;br /&gt;대해 이런 부분들을 언급하는가?&lt;br /&gt;&lt;br /&gt;Engineer로써 생각해 볼 건 생각해보고 지킬 건 지키자.&lt;br /&gt;&lt;br /&gt;꼬랑지) kernel marker와 tracepoint에 대해 많은 사람들이 &lt;br /&gt;그 쓰임새를 혼돈하고 있는 것 같다. 다음을 참조하자. &lt;br /&gt;&lt;a href="http://ltt.polymtl.ca/tracingwiki/index.php/Tracepoints_and_Markers"&gt;http://ltt.polymtl.ca/tracingwiki/index.php/Tracepoints_and_Markers&lt;/a&gt;&lt;br /&gt;&lt;blockquote&gt;Markers are very much like Tracepoints, except that they declare a format string and export the data through a variable argument list. There is a small overhead associated with variable argument lists and the associated interpretation of the format string. The type of the arguments is also normally restricted to scalar types which can easily be described by the format string. The advantage of Markers is that they are self described. They do not require a prior declaration in an include (.h) file, and they can be processed by a generic probe, expecting a printf-like variable argument list.&lt;/blockquote&gt;&lt;blockquote&gt;Markers are thus used for simple ad-hoc instrumentation. Tracepoints are typically used when a formal hook is desired at an important location in the code. A tracepoint in the code is less visually invasive than a marker since it only contains the relevant arguments (no format string). Furthermore, a tracepoint is a general hooking mechanism which may be used for different purposes, one of which being tracing. The disadvantage is that for each tracepoint the developer must provide a prior definition and a corresponding probe.&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4421904803770585360?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4421904803770585360/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4421904803770585360&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4421904803770585360'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4421904803770585360'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/09/static-trace-point.html' title='Static Trace Point에 관하여'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7921914144420759057</id><published>2009-08-26T10:35:00.004+09:00</published><updated>2009-08-26T11:10:24.561+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Bad page state</title><content type='html'>이러니 Linus에게 반하지 않을 수 밖에. &lt;br /&gt;&lt;br /&gt;문제는 8월 초로 거슬러 올라간다.&lt;br /&gt;&lt;br /&gt;Title : Bad page state (was Re: Linux 2.6.31-rc7)&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;8월 1일 &lt;br /&gt;&lt;br /&gt;Greetings;&lt;br /&gt;&lt;br /&gt;2.6.31-rc5 rebooted to before amanda ran last night.  The amanda run looks ok, &lt;br /&gt;but I had also plugged in an empty 8GB usb key so I did a quick dmesg to see &lt;br /&gt;where it was, and found this at the end of the dmesg report:&lt;br /&gt;&lt;br /&gt;[ 7423.221754] BUG: Bad page state in process tar  pfn:a1293&lt;br /&gt;[ 7423.221760] page:c28fc260 flags:80004000 count:0 mapcount:0 mapping:(null) &lt;br /&gt;index:0&lt;br /&gt;[ 7423.221764] Pid: 19211, comm: tar Not tainted 2.6.31-rc5 #1&lt;br /&gt;[ 7423.221766] Call Trace:&lt;br /&gt;[ 7423.221774]  [&lt;c130b0e3&gt;] ? printk+0x23/0x40&lt;br /&gt;[ 7423.221780]  [&lt;c1083d6f&gt;] bad_page+0xcf/0x150&lt;br /&gt;[ 7423.221784]  [&lt;c1084e0d&gt;] get_page_from_freelist+0x37d/0x480&lt;br /&gt;[ 7423.221788]  [&lt;c107ed54&gt;] ? add_to_page_cache_lru+0x84/0x90&lt;br /&gt;[ 7423.221791]  [&lt;c10850ef&gt;] __alloc_pages_nodemask+0xdf/0x520&lt;br /&gt;[ 7423.221795]  [&lt;c1087954&gt;] __do_page_cache_readahead+0x104/0x220&lt;br /&gt;[ 7423.221798]  [&lt;c1087aa4&gt;] ra_submit+0x34/0x50&lt;br /&gt;[ 7423.221801]  [&lt;c1087d00&gt;] ondemand_readahead+0x120/0x240&lt;br /&gt;[ 7423.221804]  [&lt;c1087ebc&gt;] page_cache_async_readahead+0x9c/0xb0&lt;br /&gt;[ 7423.221807]  [&lt;c10806ac&gt;] generic_file_aio_read+0x33c/0x6a0&lt;br /&gt;[ 7423.221830]  [&lt;c10b09c9&gt;] do_sync_read+0xe9/0x140&lt;br /&gt;[ 7423.221835]  [&lt;c104e400&gt;] ? autoremove_wake_function+0x0/0x60&lt;br /&gt;[ 7423.221839]  [&lt;c115211e&gt;] ? security_file_permission+0x1e/0x40&lt;br /&gt;[ 7423.221842]  [&lt;c10b0a80&gt;] ? rw_verify_area+0x60/0xe0&lt;br /&gt;[ 7423.221845]  [&lt;c10b1827&gt;] vfs_read+0xb7/0x180&lt;br /&gt;[ 7423.221848]  [&lt;c10b08e0&gt;] ? do_sync_read+0x0/0x140&lt;br /&gt;[ 7423.221850]  [&lt;c10b19f8&gt;] sys_read+0x58/0xa0&lt;br /&gt;[ 7423.221854]  [&lt;c10031b7&gt;] sysenter_do_call+0x12/0x22&lt;br /&gt;[ 7423.221856] Disabling lock debugging due to kernel taint&lt;br /&gt;&lt;br /&gt;The machine seems 100% so far.  This kernel was built without that patch that &lt;br /&gt;would make an oom more verbose.  htop looks ok, as does slabtop.&lt;br /&gt;&lt;br /&gt;Where should I take this?&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;위와 같은 BUG reporting이 올라왔다. &lt;br /&gt;또한 8월 21일, 다시 한번 비슷한 문제가 같은 사람(Gene)에 의해 보고 되었다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152737] BUG: Bad page state in process lzma  pfn:a1093&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152743] page:c28fc260 flags:80004000 count:0 mapcount:0 mapping:(null) index:0&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152747] Pid: 17927, comm: lzma Not tainted 2.6.31-rc7 #1&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152750] Call Trace:&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152758]  [&lt;c130e363&gt;] ? printk+0x23/0x40&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152763]  [&lt;c108404f&gt;] bad_page+0xcf/0x150&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152767]  [&lt;c10850ed&gt;] get_page_from_freelist+0x37d/0x480&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152771]  [&lt;c10853cf&gt;] __alloc_pages_nodemask+0xdf/0x520&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152775]  [&lt;c1096b19&gt;] handle_mm_fault+0x4a9/0x9f0&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152780]  [&lt;c1020d61&gt;] do_page_fault+0x141/0x290&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152784]  [&lt;c1020c20&gt;] ? do_page_fault+0x0/0x290&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152787]  [&lt;c1311bcb&gt;] error_code+0x73/0x78&lt;br /&gt;Aug 21 22:37:47 coyote kernel: [ 1030.152789] Disabling lock debugging due to kernel taint&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;bad_page는 사실 커널에서 거의 볼 수 없는 문제이다.&lt;br /&gt;왜냐하면 mm guy들이 패치를 할 때 굉장히 꼼꼼히 챙기는 부분이기 때문이다. &lt;br /&gt;그럼에도 불구하고 발생했다. &lt;br /&gt;&lt;br /&gt;먼저 Linus가 의심한 것은 Wu의 20a0307c0396c2edb651401d2f2db193dda2f3c9 이 패치이다.&lt;br /&gt;이 패치는  /proc/pagemap을 Huge Page까지 확장하기 위한 단순한 변경이었다.  &lt;br /&gt;그러므로 그리 가능성이 그리 크지 않아 보였다.  &lt;br /&gt;&lt;br /&gt;barrios를 비롯한 다른 mm guy들도 그 문제에 대해서 &lt;br /&gt;별 다른 언급을 하지 않았다. 그랬던 이유는 특별히 의심가는 &lt;br /&gt;부분을 생각할 수 없었기 때문이다. &lt;br /&gt;&lt;br /&gt;하지만 Linus는 그 문제에 대해서 꾸준히 관심을 가지고&lt;br /&gt;개인적으로 Gene에게 메일을 더 보내 여러 테스트를 요구한 것으로 보인다.&lt;br /&gt; &lt;br /&gt;Gene가 보내온 또 다른 Oops.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053652] BUG: Bad page state in process python  pfn:a0e93&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053658] page:c28fc260 flags:80004000 count:0 mapcount:0 mapping:(null) index:0&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053662] Pid: 4818, comm: python Not tainted 2.6.31-rc7 #3&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053664] Call Trace:&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053672]  [&lt;c130fb33&gt;] ? printk+0x23/0x40&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053678]  [&lt;c108352f&gt;] bad_page+0xcf/0x150&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053682]  [&lt;c10845cd&gt;] get_page_from_freelist+0x37d/0x480&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053686]  [&lt;c10848af&gt;] __alloc_pages_nodemask+0xdf/0x520&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053691]  [&lt;c1095ff9&gt;] handle_mm_fault+0x4a9/0x9f0&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053695]  [&lt;c105ca83&gt;] ? tick_dev_program_event+0x43/0xf0&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053699]  [&lt;c105cbd6&gt;] ? tick_program_event+0x36/0x60&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053703]  [&lt;c1020d61&gt;] do_page_fault+0x141/0x290&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053707]  [&lt;c1020c20&gt;] ? do_page_fault+0x0/0x290&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053710]  [&lt;c131339b&gt;] error_code+0x73/0x78&lt;br /&gt;Aug 22 22:29:07 coyote kernel: [ 2449.053712] Disabling lock debugging due to kernel taint&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;결국, 8월 24일 Linus는 문제를 찾아냈다. &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;"It's not a kernel BUG!"&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;그것을 어떻게 알 수 있었을까?&lt;br /&gt;위의 3 Oops를 보면 모두 bad page에서 detection된 것을 알 수 있다. &lt;br /&gt;아주 운이 좋은 경우이다. bad page의 detection은 flag값을 &lt;br /&gt;통해 detect 되었음을 알 수 있다. &lt;br /&gt;&lt;br /&gt;flag값의 0x4000의 bit이 set되어져 있었기 때문에 bad_page가&lt;br /&gt;호출된 경우이다. 또한 3경우 모든 page의 가상 주소는 c28fc260이다. &lt;br /&gt;즉, x86의 경우 28fc260의 물리 주소에서 문제가 발생하였다는 것이다. &lt;br /&gt;왜 그렇게 생각할 수 있을까?&lt;br /&gt;&lt;br /&gt;그럼 생각해보자. 모두 다른 경로를 통해 Oops가 발생하였지만, &lt;br /&gt;희안하게도 Oops를 발생시켰던 곳은 28fc260 번지이고 모든 &lt;br /&gt;경우 flag 값이 같다. 즉, 0x4000이 set되어져 있다. PFN은 &lt;br /&gt;달라질 수 있다. 왜냐하면 pfn을 계산하기 위한 &lt;br /&gt;mem_map을 할당하는 위치가 booting 중 timing에따라 또는 &lt;br /&gt;kernel configuration에 따라 달라질 수 있기 때문이다. &lt;br /&gt;&lt;br /&gt;&lt;span style="font-style:italic;"&gt;하지만 barrios의 생각은 아무래도 booting 중 타이밍 &lt;br /&gt;문제보다는 kernel configuration이 틀려지지 않는 한 잘 &lt;br /&gt;바뀌지 않을 것 같다. kernel configuration 중에서도 &lt;br /&gt;bootmem allocator에 영향을 주는 경우에 한해서 그 값이 &lt;br /&gt;달라질 수 있을 것이다. &lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;또한 flag는 page descriptor의 첫번째 멤버이다. 위에서 본 것 처럼&lt;br /&gt;모든 error는 flag값에 의해 발생하였다. 그렇다는 얘기는 28fc260의 &lt;br /&gt;물리 메모리에 문제가 있다는 것을 의미할 수 있다. 그러므로 이 문제는&lt;br /&gt;운이 좋게 mem_map이 할당된 메모리의 일부가 깨졌기 때문에 또한 해당 &lt;br /&gt;page가 사용중이 아니며 buddy에 free page로 존재하고 있었기 때문에&lt;br /&gt;쉽게(?) 문제를 찾을 수 있는 경우이다. memory corruption이 다른 메모리&lt;br /&gt;번지 였다면 시스템이 runtime에 random하게 crash되는 현상이 발생하였을 &lt;br /&gt;것이다. &lt;br /&gt;&lt;br /&gt;현재 Linus는 문제가 28fc260의 bad memory로 인해 발생한 것이 &lt;br /&gt;거의 틀림 없다고 보고 있으며 Gene 또한 memory test로 인해 &lt;br /&gt;memory에 문제가 있음을 확인하였다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7921914144420759057?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7921914144420759057/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7921914144420759057&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7921914144420759057'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7921914144420759057'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/08/bad-page-state.html' title='Bad page state'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6046185358231976698</id><published>2009-08-25T20:50:00.008+09:00</published><updated>2009-08-25T23:00:31.367+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Flexible Array</title><content type='html'>8월에 글이 많이 부족했다. &lt;br /&gt;회사일로도 많이 바뻤고, 집안일로도 많이 바뻤고, 도저히 &lt;br /&gt;블로깅을 할 시간은 내기 힘들었다. &lt;br /&gt;&lt;br /&gt;8월이 가기전에 또 다른 시간을 내기 힘들 것 같아, 아들 밥 먹고&lt;br /&gt;있는 틈을 타서 지난번 봐두었던 기사에 대해 정리하기로 한다. &lt;br /&gt;&lt;a href="http://lwn.net/Articles/345273/"&gt;&lt;br /&gt;http://lwn.net/Articles/345273/&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;커널 프로그래밍을 할때 흔히들 큰 메모리 버퍼를 할당해서 사용해야 &lt;br /&gt;핲 필요가 있는 경우가 있다. 이때 큰 버퍼를 할당하기 위해서는 &lt;br /&gt;메모리 공간을 어떤 API로 확보해야 할까? &lt;br /&gt;이미 우리는 여러 서적이가 기타 article들을 바탕으로 커널에서 big&lt;br /&gt;order page allocation은 실패할 확률이 높다는 것을 알고 있다. &lt;br /&gt;그러므로 kmalloc은 선택할 수 있는 방법은 아니다. &lt;br /&gt;그래도 어쩔 수 없지 않는가? 우리는 big memory chunk가 필요한데.&lt;br /&gt;&lt;br /&gt;Big memory가 물리적으로 연속될 필요가 없다면 가장 쉽게 선택할 수&lt;br /&gt;있는 방법은 단연 vmalloc이다. vmalloc은 여러 문제가 있지만, &lt;br /&gt;이번 기사에서 지적하고 있는 문제는 일반적인 32 bit system에서의 &lt;br /&gt;linear address space의 부족함이다. 커널이 사용하는 메모리 1G 중&lt;br /&gt;896M는 direct mapped 되어지고, 나머지 공간 중에서도 일부는 &lt;br /&gt;kmap, kmap_atomic, fixed_map등을 위해 띠어주고 나면 대략 120M&lt;br /&gt;정도가 vmalloc을 위해 사용가능하다. &lt;br /&gt;&lt;br /&gt;또 다른 이유는 SMP system에서의 overhead가 크다는 것이다. &lt;br /&gt;(TLB flush 및 IPI로 인하여. 이 중 많은 부분이 Nick Piggin에 의해&lt;br /&gt;lazy flush방식으로 optimization되었었지만, 아무리 그렇더라도 &lt;br /&gt;vmalloc을 사용하지 않는 경우에 비해 overhead가 큰 것은 사실이다.)&lt;br /&gt;&lt;br /&gt;그럼 여지껏 개발자들은 어떻게 그런 요구를 만족시켰는가?&lt;br /&gt;답은 여러가지가 있을 수 있지만 일부 취했던 방식은 kmalloc을 통해 &lt;br /&gt;할당된 4K page들을 manage하여 array based로 접근하였다. array 방식으로 &lt;br /&gt;사용했던 이유는 간단하다. 여러분이 big memory chunk가 필요하다고 하자.&lt;br /&gt;단일 object을 위해 그 메모리 공간을 사용하려고 그 큰 공간이 필요한건가?&lt;br /&gt;그렇다. 대부분은 object pooling을 위해서이다. 그 얘기는 결국 array based&lt;br /&gt;접근하는 것이 효율적이라는 것을 의미한다. object size가 고정이라면 말이다. &lt;br /&gt; &lt;br /&gt;이러한 공통적인 need들이 증가하는 것은 결국 새로운 feature가 &lt;br /&gt;필요하다는 것을 암시하며, 그래서 나온 것이 vmalloc을 사용하지 않으면서도 &lt;br /&gt;large array를 할당하기 위한 general한 framework으로써, Andrew Morton에&lt;br /&gt;의한 idea로 IBM의 Dave Hansen에 의해 구현된 "flexible array"이다. &lt;br /&gt;&lt;br /&gt;Flexible array는 임의의 수의 고정된 크기의 array를 할당할 수 있으며, &lt;br /&gt;배열과 같이 index를 통해 접근된다. 내부적으로는 single page allocation을&lt;br /&gt;통해 page들 연결시켜 사용하기 때문에 fragmentation 문제를 발생시키지 않으며,&lt;br /&gt;kmalloc을 통해 할당된 4K page들이기 때문에 vmalloc과 같은 overhead도 존재하지 &lt;br /&gt;않는다. 하지만 단점은 array는 직접 addressing할 수 없으며, object의 크기는 &lt;br /&gt;시스템의 page size 이내여야 한며, array에 data를 저장하기 위해서는 &lt;br /&gt;copy operation이 필요하다는 것이다. &lt;br /&gt;&lt;br /&gt;현재 Flexible Array는 mmtom에서 계속 패치되고 있으며, 아직까지 특정 사용자가 &lt;br /&gt;존재하지 않음으로 API는 계속해서 바뀔 수 있다. 그러므로 사용법을 굳이 언급하지는 &lt;br /&gt;않는다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6046185358231976698?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6046185358231976698/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6046185358231976698&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6046185358231976698'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6046185358231976698'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/08/flexible-array.html' title='Flexible Array'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7659356122449651074</id><published>2009-08-03T08:35:00.002+09:00</published><updated>2009-08-03T08:49:27.404+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>OOM livelock problem</title><content type='html'>2ff05b2b4eac2e63d345fc731ea151a060247f53&lt;br /&gt;&lt;br /&gt;이 패치는 6월 16일 Google의 David에 의해 적용된 패치이다. &lt;br /&gt;이 패치의 요는 다음과 같다. &lt;br /&gt;&lt;br /&gt;1. oom_adj를 task_struct에서 mm_struct으로 옮긴다. &lt;br /&gt;2. OOM의 livelock 상황을 막는다. &lt;br /&gt;&lt;br /&gt;1.의 rationale은 쉽게 생각할 수 있다. &lt;br /&gt;oom_adj의 값은 per-task의 member로는 의미가 없기 때문이다. &lt;br /&gt;생각을 해보자. 특정 프로세스 A의 임의의 한 쓰레드의 oom_adj값을 -17(OOM_DISABLE)로 했다고 가정하자. &lt;br /&gt;OOM killer의 입장에서 한 task를 kill해야 하는 경우, &lt;br /&gt;특정 프로세스 A를 kill하는 것이 make sense한가? 당연히 No!. &lt;br /&gt;&lt;br /&gt;왜냐하면 프로세스의 A가 포함하고 있는 쓰레드 가운데 한 녀석이라도 &lt;br /&gt;OOM_DISABLE이 설정되어 있다면, mm_struct 즉 해당 쓰레드가 사용하고 있는 주소 공간은 &lt;br /&gt;보존되어야 하기 때문이다. 주소 공간이 보존된다는 것은 OOM killer는 메모리를 회수하기위해 &lt;br /&gt;프로세스 A를 kill할 수 없다는 것이다. &lt;br /&gt;&lt;br /&gt;이는 아래와 같이 oom_kill_task의 함수에서도 볼 수 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;366     /*&lt;br /&gt;367      * Don't kill the process if any threads are set to OOM_DISABLE&lt;br /&gt;368      */&lt;br /&gt;369     do_each_thread(g, q) {&lt;br /&gt;370         if (q-&gt;mm == mm &amp;&amp; q-&gt;oomkilladj == OOM_DISABLE)&lt;br /&gt;371             return 1;&lt;br /&gt;372     } while_each_thread(g, q);&lt;br /&gt;373 &lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;그러므로 oom_adj란 member는 task_struct의 member보다는 mm_struct의 member가 되는 것이 &lt;br /&gt;더 자연스러운 것이다. &lt;br /&gt;&lt;br /&gt;2.에서 말한 livelock 상황은 위에서 언급한 문제로 인해 발생한다. &lt;br /&gt;select_bad_process가 프로세스 A를 선택했다고 가정하자. &lt;br /&gt;이전의 예와 같이 A는 OOM immutable한 쓰레드를 가지고 있다고 가정하면 &lt;br /&gt;oom_kill_process는 결국 retry하게 될 것이다. &lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;530 retry:&lt;br /&gt;531     /*&lt;br /&gt;532      * Rambo mode: Shoot down a process and hope it solves whatever&lt;br /&gt;533      * issues we may have.&lt;br /&gt;534      */     &lt;br /&gt;535     p = select_bad_process(&amp;points, NULL);&lt;br /&gt;536  &lt;br /&gt;537     if (PTR_ERR(p) == -1UL)&lt;br /&gt;538         return;&lt;br /&gt;539  &lt;br /&gt;540     /* Found nothing?!?! Either we hang forever, or we panic. */&lt;br /&gt;541     if (!p) {&lt;br /&gt;542         read_unlock(&amp;tasklist_lock);&lt;br /&gt;543         panic("Out of memory and no killable processes...\n");&lt;br /&gt;544     }&lt;br /&gt;545 &lt;br /&gt;546     if (oom_kill_process(p, gfp_mask, order, points, NULL,&lt;br /&gt;547                  "Out of memory"))&lt;br /&gt;548         goto retry;&lt;br /&gt;549 }&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;이 상황은 OOM immuable 쓰레드가 종료될 때까지 계속 될 수 있으며, 해당 쓰레드가 언제 종료될지는 &lt;br /&gt;아무도 모른다. 그러므로 livelock 상황을 유발할 수 있었다. &lt;br /&gt;&lt;br /&gt;하지만 이 패치가 또 다른 side effect을 만들어 내기 시작했다. &lt;br /&gt;것은 다음 기회에.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7659356122449651074?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7659356122449651074/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7659356122449651074&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7659356122449651074'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7659356122449651074'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/08/oom-livelock-problem.html' title='OOM livelock problem'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6508602027016262278</id><published>2009-07-18T01:14:00.002+09:00</published><updated>2009-07-18T01:16:48.509+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>회상이 지나간 오후</title><content type='html'>&lt;a href="http://tvpot.daum.net/clip/ClipView.do?clipid=12845336"&gt;http://tvpot.daum.net/clip/ClipView.do?clipid=12845336&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Pop보다는 한국 대중 가요를 더 좋아하는 이유는 영어를 &lt;br /&gt;잘 못해서이기도 하지만, 그 가사에서 그 상황에서 느껴지는 그 멜로디와 그 의미를 &lt;br /&gt;내 의지대로 해석하지못하기 때문이다.&lt;br /&gt;&lt;br /&gt;20살 때의 일이다.&lt;br /&gt;&lt;br /&gt;완벽하게 이상적인 생각들로 가득찼던 시절이 있었다.&lt;br /&gt;&lt;br /&gt;내 눈으로 바라본 세상을 내 의지대로 해석하는 지금의 모습과는 분명 같지 않으며,&lt;br /&gt;지금의 모습을 상상할 수 없을 정도로 순수하게 이상을 쫓았던 시절이 내겐 분명 있었다.&lt;br /&gt;&lt;br /&gt;힘들지만 보람된 시간들이었으며, 너무 다행스러웠던 것은 &lt;br /&gt;내 주위 나와 같은 사람들도함께 하였지만, 그렇진 않지만 &lt;br /&gt;나를 이해해줄 수 있는 사람들도 있었다는 것이다.&lt;br /&gt;&lt;br /&gt;어느덧 시간이 흘러, 군을 나오고, 졸업을 하고, 취업을 하고, 정신 없이 시간을 흘려보내고 나니 &lt;br /&gt;그들은 여전히 이렇게 작은 기쁨을 선사한다.&lt;br /&gt;&lt;br /&gt;모두들 잘들 살고는 있는 것인지. 나와 같이 이미 그때의 모습을 잃어버린 것은 아닌지..&lt;br /&gt;&lt;br /&gt;내밀면 닿을 곳에 있는 그들을 한번 만나봐야 할 것 같다. &lt;br /&gt;누가 먼저 손을 내미느냐는중요하진 않다. 우리들에겐 의미 없는 허세일 뿐이다.&lt;br /&gt;&lt;br /&gt;술 많이 먹고 쓰는 건 아니다.그저 적당한 술이 나를 부지런하게 만들어 줄 뿐.&lt;br /&gt;&lt;br /&gt;꼬랑지) 적당한 제목을 만들어 주는 툴이 내겐 늘 필요하다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6508602027016262278?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6508602027016262278/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6508602027016262278&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6508602027016262278'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6508602027016262278'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/07/blog-post_8558.html' title='회상이 지나간 오후'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2022319768518174472</id><published>2009-07-14T22:47:00.004+09:00</published><updated>2009-07-15T09:17:50.338+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>come back zero_page</title><content type='html'>&lt;a href="http://lwn.net/Articles/340370/"&gt;http://lwn.net/Articles/340370/&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;ZERO_PAGE. Linux kernel의 VM에 관심있는 사람들은 한번쯤 들어봤을 법한 &lt;br /&gt;설비이다. Linux kernel은 2.6.24시절까지는 zero page를 사용하여 vma에 &lt;br /&gt;최초 발생한 read fault는 zero page에 매핑하였다. &lt;br /&gt;&lt;br /&gt;이는 다음과 같은 장점을 가져온다. &lt;br /&gt;&lt;br /&gt;1. memory save&lt;br /&gt;2. reduced cache pressure&lt;br /&gt;3. eliminating the need to clear the new page&lt;br /&gt;&lt;br /&gt;하지만 24때 Nick에 의해 MuliProcessor system에서 cache line bouncing문제가&lt;br /&gt;심각하다고 밝혀져 제거되었다.(물론 revert되기까지는 많은 discussion이 있었다.&lt;br /&gt;avoiding zero page reference counting, per-cpu zero page등)&lt;br /&gt;cache line bouncing이 발생하는 이유는 많은 CPU들이 하나의 zero page를 공유하게 &lt;br /&gt;되면서, zero page의 reference counting 때문에 발생하게 되었다. &lt;br /&gt;&lt;br /&gt;그 당시에 Nick의 이런 노력에 사실 Linus는 심기가 불편했지만 일단 Nick의 이 패치가&lt;br /&gt;어떤 문제들을 발생시킬지 보기로 하고는 우선 merge했었다. Linus가 zero page의 제거를 &lt;br /&gt;싫어했던 이유는 zero page는 리눅스와 함께 태동했기 때문이다. Linux가 세상에 알려지기&lt;br /&gt;시작할 무렵부터 zero page는 거기에 있었으며, 2.6.24까지도 큰(?) 문제 없이 잘 사용되고&lt;br /&gt;있어왔던 것이다. 그러므로 이미 몇몇 application들은 Linux kernel의 이런 특성(zero page)&lt;br /&gt;을 이미 활용하고 있어왔다. 그러므로 kernel에서 zero page를 제거하게 된다면, 그런 특성을 &lt;br /&gt;활용하던 application들의 regression은 피할 수 없게 될 것이다. &lt;br /&gt;&lt;br /&gt;정확히 18개월이 지나고, 문제가 터지기 시작했다. 마지막으로 카운터를 날린 것은 Kame였다&lt;br /&gt;Kame는 다음과 같이 주장했다. "Kernel이 바뀌어서 regression이 생겼다고, app 개발자들한테&lt;br /&gt;너희들이 다시 app를 개발해야해!" 라고 말할 수는 없는 것 아니냐고. &lt;br /&gt;&lt;br /&gt;Linus의 전폭적인 지지와 함께 zero page의 대한 구현이 다시 시작되었다.(물론 reference counting을&lt;br /&gt;피하기 위해 아소 깨끗하지 못한 구현이 되어가고 있을 무렵..). 다시 한번 Nick은 zero page의 도래를&lt;br /&gt;마땅해하지 못하고 있음을 여러모로 피력하였다. 하지만 Linus는 이미 마음을 굳힌 것 같다. 이에 대해&lt;br /&gt;Nick과 Linus가 다소 격양된 어조의 토론이 있었지만... &lt;br /&gt;언제나 그렇듯이, Linus의 승이다. &lt;br /&gt;&lt;br /&gt;결국 우리는 머지 않아 zero page를 다시 보게 될 것이며, 그 구현은 그렇게 평이한 수준이 되지는 &lt;br /&gt;않을 것이다. &lt;br /&gt;&lt;br /&gt;꼬랑지) &lt;br /&gt;barrios의 기억으로 zero page의 제거가 문제가 된 부분 중의 하나는, core파일을 만들어 낼때이다. &lt;br /&gt;core dump는 기본적으로 프로세스의 모든 vma에 page들을 읽어 file로 덤프를 뜬다. &lt;br /&gt;이때 zero page의 제거는 실제 page를 할당받게 됨으로써, vma의 크기에 따라 순식간에 시스템의 &lt;br /&gt;memory를 모두 소비할 수 있게 된다. 그러므로 embedded system에서는 oops로 swap을 가지고 있는&lt;br /&gt;일반 시스템 또한 순식간에 swap out이 발생하게 되어 working set들을 버릴 수도 있게 되며, &lt;br /&gt;그 순간 시스템의 응답성을 떨어뜨리게 된다. &lt;br /&gt;&lt;br /&gt;core dump에서 이 문제를 어떻게 해결했는지 barrios는 follow up하지 못하였으며, 이 부분에 대한 &lt;br /&gt;언급이 없는 것으로 봐서는 해결이 되었을 것으로 기대한다. (그렇지 않다면 역시 나의 몫!)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2022319768518174472?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2022319768518174472/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2022319768518174472&amp;isPopup=true' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2022319768518174472'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2022319768518174472'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/07/come-back-zeropage.html' title='come back zero_page'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-1261862060017997452</id><published>2009-07-06T19:38:00.006+09:00</published><updated>2009-07-06T22:35:28.587+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Perfcounters</title><content type='html'>&lt;a href="http://lwn.net/Articles/339361/"&gt;http://lwn.net/Articles/339361/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;2.6.31의 새로운 기능 중 가장 주목할 만한 것은 모니모니 해도 Ingo의 perfcounters가 아닐까 싶다. 오랫동안 tip-tree에서 성숙된 perfcounters가 드디어 2.6.31의 merge window에 merge되었다. &lt;br /&gt;&lt;br /&gt;perfcounters는 Ingo, Peter 등에 의해 최근 굉장히 활발히 개발된 performance analyser이다. 물론 여러분들이 아는 툴 중에 가장 유명한 oprofile과 같은 툴도 있겠지만, perfcounters의 취지는 정말 사용하기 쉬운, 그리고 정말 필요한 기능을 넣겠자는 의도에서 시작되었다. &lt;br /&gt;&lt;br /&gt;perfcounters를 개발하면서 perfmon의 개발자 Stéphane Eranianr과 Ingo는 많은 부분에서 의견충돌이 있었다. Ingo는 Stéphane Eranian가 PMU 기능의 많은 부분들을 export하자는 제안에 단호히 저지했다. 요는 다음과 같다. &lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;"A tool might want to do this" is not a good enough answer. We now have a working OSS tool-space with 'perf' where such arguments for more PMU features can be made in very specific terms: patches, numbers and comparisons. Actual hands-on utility, happy developers and faster apps is what matters in the end - not just the list of PMU features we expose. &lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;다시한번 Ingo의 kernel에 대한 철학을 엿볼수 있다. Ingo는 언제난 이런 투의 말을 싫어한다. - "Tool이란 이러한 것을 하길 원할지도 모른다". 막연한 추측 보다는 실제 필요한 것들을 먼저 해보고 데이터를 수집해보고 어떤 데이터가 어떻게 어떤 사용자들한테 유용할지 말하는 것이 결국 happy developer, faster apps들을 만들어 내는 것이다라고 생각한다. &lt;br /&gt;&lt;br /&gt;여기서 말하지 않고 넘어간 것이 하나 있다. perf라는 툴이다. perf는 perfcounters를 이용하는 user space tool이다. 이것이 중요한 이유는 이 tool이 커널의 tool 디렉토리에 merge되었다는 것이다. 지금까지 많은 커널 개발자들은 user space 툴들이 kernel에 merge되는 것을 좋아하지 않아왔다. 그럼에도 불구하고 이번 perf는 Linus의 지지를 받으며 입봉하게 된 것이다. Linus는 Oprofile의 예를 들며, 이번 perf의 입봉을 전격 추진하였다. Oprofile userspace tool은 커널의 밖에서 maintain되어왔다. 그러다 보니, 커널의 최신 패치를 항상 한발 늦게, 또는 3~4발 늦게 쫓아왔다. Linus는 항상 이게 불만이었다. Anyway 이게 적절한 예는 아닐지 몰라도, 다른 개발자들의 만류에도 불구하고 Linus는 이번에 한번 그렇게 해보는 게 어떻겠냐고 반문하며 perf의 입봉을 대환영하였다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;"Let's give a _new_ approach a chance, and see if we can avoid the mistakes of yesteryear this time." &lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;어떻게 됐든, 지금 perf와 perfcounter는 merge되었고 이변이 없는 한 revert되지는 않을 것이다. 또한 현재의 perfcounter는 개발 초기와는 달리 굉장히 많은 기능이 추가되고 있으며  barrios가 생각하건데, 1년 안에 Oprofile을 능가하는 멋진 툴이 될 것이라고 생각한다. &lt;br /&gt;&lt;br /&gt;현재 barrios 또한 perfcounter에 allocation과 reclaim의 분석을 위한 도구들을 add할 생각을 가지고 있다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-1261862060017997452?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/1261862060017997452/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=1261862060017997452&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1261862060017997452'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1261862060017997452'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/07/perfcounters.html' title='Perfcounters'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-253804912217815513</id><published>2009-07-04T00:37:00.006+09:00</published><updated>2009-07-04T11:09:07.115+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>기분 좋은 하루</title><content type='html'>간만에 즐거운 술 한잔.&lt;br /&gt;&lt;br /&gt;고등교육을 마치고 나서부터, 언제나 즐거웠던.(단 즐거운 사람들과 함께 있는 경우만. 굉장히 까탈스러운 성격으로 인해 어렵거나 유쾌하지 못한 술자리는 되도록 피하는 편이다.)&lt;br /&gt;&lt;br /&gt;여러가지 일로 미뤄왔었던 기분좋은 마무리다. &lt;br /&gt;&lt;br /&gt;창문을 열어 놓으니 바람이 솔솔 들어온다.&lt;br /&gt;아내는 TV를 보고 있고 아들은 조용히 잠을 자고 있는 이 순간이 삶의 낙이다.&lt;br /&gt;&lt;br /&gt;TV에 한 가수가 얼마전 종용했던 드라마의 주제가를 부르고 있다. &lt;br /&gt;&lt;br /&gt;나를 믿고 의지하는 가족이 있어서 행복하다.&lt;br /&gt;&lt;br /&gt;당장 패치를 하나 만들어야 하는데.. 코드를 볼 정신이 없다. &lt;br /&gt;(Andrew한테 상당히 미안하다.)&lt;br /&gt;&lt;br /&gt;끝으로 기분 좋게 울 아들 왕눈이 사진 한장.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_x1T3vyNglZo/Sk4ntZ6uvGI/AAAAAAAAAKQ/HK8pl9gBvdA/s1600-h/IMG_3191.jpg"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 267px;" src="http://4.bp.blogspot.com/_x1T3vyNglZo/Sk4ntZ6uvGI/AAAAAAAAAKQ/HK8pl9gBvdA/s400/IMG_3191.jpg" alt="" id="BLOGGER_PHOTO_ID_5354260667994913890" border="0" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-253804912217815513?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/253804912217815513/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=253804912217815513&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/253804912217815513'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/253804912217815513'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/07/blog-post.html' title='기분 좋은 하루'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_x1T3vyNglZo/Sk4ntZ6uvGI/AAAAAAAAAKQ/HK8pl9gBvdA/s72-c/IMG_3191.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4535878704789935664</id><published>2009-06-25T07:10:00.006+09:00</published><updated>2009-06-26T07:45:34.601+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Performance degradation seen after using one list for hot/cold pages</title><content type='html'>얼마전 보고된 내용이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://marc.info/?l=linux-mm&amp;m=124565003222392&amp;w=4"&gt;http://marc.info/?l=linux-mm&amp;m=124565003222392&amp;w=4&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;I/O performance가 degradation되었다는 내용이다. &lt;br /&gt;문제의 원인은 Mel의 PCP 패치때문이었다. &lt;br /&gt;PCP는 원래 hot/cold의 분리된 list로 관리되고 있었지만, Mel은 그 2개의 list를 하나로 합치면서&lt;br /&gt;cold page는 뒤에서부터 할당하고, hot page는 앞에서부터 할당하였다. &lt;br /&gt;&lt;br /&gt;그래서 발생한 문제가 cold page에 대해서 기존에는 A-B-C-D의 연속된 페이지의 순서로 할당되었던 PFN들이&lt;br /&gt;이제는 D-C-B-A의 order로 할당될 수 있다는 것이다. 이는 연속된 order의 buffer들을 merge하여 처리할 수 있는&lt;br /&gt;I/O device의 성능 저하를 초래하게 된다. &lt;br /&gt;&lt;br /&gt;현재 page allocator는 PCP를 채울때 연속된 페이지의 order를 유지하려고 애쓴다. 이 또한 그러한 I/O device들을 염두에 둔 것이다. 하지만 Mel의 PCP 패치가 이 약속을 깨버린 것이다. &lt;br /&gt;&lt;br /&gt;Mel은 이 report에 대해서 이미 알고 있었지만 왜 인지 당시에 patch는 만들지 못하였다. &lt;br /&gt;이번 패치는 이 문제를 해결하기 위해서 PCP에 page를 add할때 cold 페이지의 경우에 역순으로 배치하여, &lt;br /&gt;나중에 연속된 page의 순서대로 할당 가능하게 해준다. &lt;br /&gt;&lt;br /&gt;이문제에 대해서 barrios가 이 바쁜 시간(대체 요근래 모하고 사는지를 모르겠다. 내가 정말 엔지니어인지에 대하여 심각하게 고민을 하고 있는 중)을 짬내어 언급하는 이유는 이문제가 국내의 기업이 report한 문제이기 때문이며, report를 했던 이는 이미 이 문제의 원인에 대해서 알고 있었기 때문이다. &lt;br /&gt;&lt;br /&gt;국내 기업이 이런 critical한 report를 OpenSource 진영에 하는 것은 사실 처음 봤기 때문이다. &lt;br /&gt;국내 기업의 Open Source에 대한 자세가 긍정적으로 변한 것일까?..&lt;br /&gt;하지만 아쉽게도 올린이가 외국인인 것으로 봐서 해외 연구소의 연구원일 것으로 생각된다. &lt;br /&gt;아마도 국내에서는 쉽게 저런 글을 함부로 report하지 못했을 것이다.&lt;br /&gt;아침부터 쓸쓸하구만.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4535878704789935664?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4535878704789935664/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4535878704789935664&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4535878704789935664'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4535878704789935664'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/06/performance-degradation-seen-after.html' title='Performance degradation seen after using one list for hot/cold pages'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-1492406718081022469</id><published>2009-06-23T23:03:00.004+09:00</published><updated>2009-06-25T07:09:42.265+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Common OOM killer Problem in Embedded System</title><content type='html'>금일 report된 Oops이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://lkml.org/lkml/2009/6/22/604"&gt;http://lkml.org/lkml/2009/6/22/604&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;친절하게 Kame-san이 원인을 잘 설명해주고 있다. &lt;br /&gt;&lt;br /&gt;이번 문제는 사실 swap device를 가지고 있지 않은 Embedded System에서는 흔한 문제이다. &lt;br /&gt;문제를 살펴보면,&lt;br /&gt;먼저, 메모리 할당 실패는 order 2, 즉 16K의 연속된 메모리 할당에 있어 실패하였다. &lt;br /&gt;&lt;br /&gt;Total : 256M&lt;br /&gt;LRU(active + inactive) : 75M&lt;br /&gt;unevictable : 124M&lt;br /&gt;SLAB : 6M&lt;br /&gt;Free + pagetable : 29M&lt;br /&gt;&lt;br /&gt;위의 메모리 상태를 보면 시스템의 Memory leack은 아닐것이라고 추측해 볼 수 있다. &lt;br /&gt;또한 위의 정보를 통해 알 수 있는 내용은 &lt;br /&gt;1. unevitable이 저렇게 많이 채워져 있는 이유는 tmpfs를 rootfs로 사용했기 때문이라고 추측할 수 있으며&lt;br /&gt;2. file lru가 거의 비워져 있는 것으로 봐서 이미 memory pressure가 상당했다는 것이다.  &lt;br /&gt;&lt;br /&gt;다음으로 buddy를 살펴보자. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Normal: 1445*4kB 1781*8kB 15*16kB 2*32kB 1*64kB 0*128kB 0*256kB 0*512kB 0*1024kB 0*2048kB 0*4096kB = 20396kB&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;16k의 연속된 페이지가 15개나 있다. 또한 64k도 하나 있고.. &lt;br /&gt;그럼 왜 OOM이 발생한 것일까?&lt;br /&gt;&lt;br /&gt;Kame-san이 친절히 얘기해 준 것처럼 zone_watermark_ok의 zone defensive algorithm 때문이다. &lt;br /&gt;(사실 Kame의 계산은 조금 틀렸다. 하지만 zone_watermark_ok가 fail한 건 사실이니.)&lt;br /&gt;&lt;br /&gt;많은 embedded system들이 swap device가 없음으로 인해 anon page들을 회수할 수 없게 되고 그로인해 memory fragmentation 문제가 심각해져 발생하는 문제이다. (갑자기 떠오른 생각을 적어 놓는다. no swap system의 lumpy reclaim은 anon page를 고려해야 한다!)&lt;br /&gt;&lt;br /&gt;이를 해결하는 방법은 swap을 사용하거나 app 메모리 사용량을 줄이거나..&lt;br /&gt;또는 아직 검증되진 않았지만 compcache(&lt;a href="http://lwn.net/Articles/334649/"&gt;http://lwn.net/Articles/334649/&lt;/a&gt;)와 같은 방법을 사용하거나...&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-1492406718081022469?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/1492406718081022469/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=1492406718081022469&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1492406718081022469'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1492406718081022469'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/06/common-oom-killer-problem-in-embedded.html' title='Common OOM killer Problem in Embedded System'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8568311734954737697</id><published>2009-05-17T18:06:00.003+09:00</published><updated>2009-05-17T19:18:03.367+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Misleading OOM messages</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/5/12/353"&gt;http://lkml.org/lkml/2009/5/12/353&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;Christoph가 최근 android로 인해 이슈가 되고 있는 OOM 메시지에 대한 오해를 화두로 던졌다. &lt;br /&gt;&lt;br /&gt;"Out of memory" =&gt; 메모리를 다 소비했다는 것이다. &lt;br /&gt;&lt;br /&gt;Christoph는 OOM은 대부분 커널 내부의 메모리 회수의 실패이지 실제 메모리가 부족해서 발생하는 문제는 아니라고 말하고 있다. 그런 반면, 많은 user들은 이 잘못된 메시지를 보고 "시스템이 충분한 메모리를 가지고 있지 않구나!" 생각하고 user들이 많은 메모리를 할당할 수 없도록 ulimit 값을 낮추는 경우가 있다고 말하고 있다. &lt;br /&gt;이것은 OOM의 메시지에 대한 오해에서 비롯되는 현상이며 이 오해는 커널에서 출력하는 OOM message에서 기인하는 것이다. 그러므로 Christoph는 OOM message를 &lt;blockquote&gt;"Failure to reclaim memory"&lt;/blockquote&gt;으로 바꾸자고 제안하고 있다. &lt;br /&gt;&lt;br /&gt;이에 대해 예전부터 OOM을 작성해왔던 suse의 Pavel Machek은 현재 OOM의 메시지는 이상이 없다고 생각하고 있으며 여러 상황을 예로 들며 실제 메모리를 추가해야 하는 상황을 언급하고 있다. 그러므로 현재 OOM message는 이상이 없다고 주장하고 있다. &lt;br /&gt;&lt;br /&gt;또한, IBM의 Dave Hansen은 자신이 만난 OOM message중 단한번도 시스템의 free page가 0이어서 발생한 적은 없다고 말하고 있다. 단지 시스템의 free page가 zone-&gt;watermark이하인 상태에서 회수가 더 이상 진행되지 못한 경우에 발생하고 있다고 전하고 있다. 현재 OOM message의 문제점은 전체 스토리를 이야기하지 못하고 마지막 결과만을 이야기 한다는 것이 문제라고 지적하고 있며 다음과 같은 메시지가 좋지 않겠냐고 제안하고 있다. &lt;br /&gt;&lt;blockquote&gt;       &lt;br /&gt;"Unable to satisfy memory allocation request and not making&lt;br /&gt;progress reclaiming from other sources."&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;하지만 console에 위와 같은 한두줄의 출력에 큰 의미를 두는 것 보다는 &lt;a href="http://linux-mm.org/OOM"&gt;http://linux-mm.org/OOM&lt;/a&gt; 와 같이 웹 페이지에 보다 자세한 정보를 담는 것이 좋을 것 같다고 한다. &lt;br /&gt;&lt;br /&gt;이에 대해 Andorid의 low memory killer를 담당하고 있는 David Rientjes은 OOM message를 다음과 같이 바꾸자고 제안하고 있다. &lt;blockquote&gt;"No [available/allowable] memory"&lt;/blockquote&gt; &lt;br /&gt;cpuset allocator와 같은 경우도 현재 OOM을 출력하고 있는데 시스템에 물리 메모리가 많은 상태에서 cpuset hardwall로 인해서 메모리 할당이 실패했음에도 불구하고 out of memory를 출력한다는 것이다. 또한 watermark로 인해서 실패하는 것도 out of memory보다는 No available memory리가 보다 make sense하다는 것이다. &lt;br /&gt;&lt;br /&gt;No available memory는 out이라는 단어 사용을 하지 않았기 때문에 user들로 하여금 memory를 더 두어야 한다는 사실보다는 swap을 추가하거나, cgroup limit을 바꾸거나, 실제 메모리를 더 추가하거나와 같은 뉘앙스를 줄 수 있게 된다. 그러므로 완벽한 solution은 아니지만 out 이란 단어를 사용하는 것 보다는 훨씬 좋다. &lt;br /&gt;&lt;br /&gt;아직까지 어떤 메시지를 출력하는 것이 좋을지에 대해서는 consensus가 만들어지지는 않고 있지만 현재 OOM message의 문제점에 대해서는 대부분 공감하고 있는 것으로 보인다. 그러므로 머지 않아 우리는 친숙한 Out of memory 메시지를 보지 않게 될지도 모르겠다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8568311734954737697?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8568311734954737697/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8568311734954737697&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8568311734954737697'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8568311734954737697'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/05/misleading-oom-messages.html' title='Misleading OOM messages'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2464049845469543351</id><published>2009-05-07T23:01:00.002+09:00</published><updated>2009-05-07T23:27:31.044+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Kernel Shared Memory</title><content type='html'>현재 barrios가 관심을 가지고 있는 feature는 KSM(kernel shared memory)이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://lkml.org/lkml/2009/5/4/400"&gt;http://lkml.org/lkml/2009/5/4/400&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;기능의 이름만으로는 어떤 역할을 하는 것인지 쉽게 예측하기 어려울 수 있다. &lt;br /&gt;안그래도 Hugh는 이 패치의 이름을 바꿀 것을 제안하였다. &lt;br /&gt;&lt;br /&gt;이 기능의 목적은 user level의 shared memory와는 전혀 관련이 없다. &lt;br /&gt;이 패치가 이루고자 하는 목적은 application들의 page중 동일한 데이터를 가지고 있는 page들을 &lt;br /&gt;하나의 page로 merge하고 나머지 page들은 free시켜 주자는 것이다.(이것은 user level의 shared memory와는 전혀 관련이 없다)&lt;br /&gt;이것이 user application에게 transparent하게 동작할수 있는 이유는 merge된 하나의 페이지를 COW로 만들기 때문이다.&lt;br /&gt;&lt;br /&gt;이 패치는 KVM을 primary target으로 개발되어졌지만 general한 approach로 만들어졌기 때문에 &lt;br /&gt;일반 application들도 sysfs의 KSM node에게 ioctl을 사용하여 자신의 address range를 KSM에게 등록할 수 있다. &lt;br /&gt;&lt;br /&gt;이 패치를 개발하고 있는 Redhat의 Izik Eidus은 이 기능으로 KVM이 많은 메모리 이득을 본다고 얘기하고 있지만, 아직까지 어떤 benchmark 결과는 내놓지 않고 있다. 하지만 KVM과 같은 virtualization solution들에게 이득이 지될 수 밖에 없는 이유는 VMM 위의 guest들은 host memory를 유사한 kernels, librarys, cache와 같은 데이터로 채우게 될 것이기 때문이다. 또한 Jared Hulbert는 embedded 환경에서도 10% 정도의 memory save를 할 수 있었다고 말하고 있지만, 어떤 test 환경에서 어떤 application들을 테스트 했는지에 대해서 언급이 없기 때문에 사실 얼마나 이득이 될지 예측할 수는 없다.  &lt;br /&gt;&lt;br /&gt;현재 이 패치는 여러 design issue를 가지고 있다. 그 중 가장 대표적인 것이 user application과의 interface이다. 현재는 sysfs의 ksm node를 통해 ioctl을 통해 application들은 자신의 virtual address range를 등록할 수 있게 되어 있다. 하지만 Rik과 Hugh는 이 interface보다는 madivse와 가은 기존의 system call을 더 선호하고 있다. interface는 결국 madivse로 바뀔 것으로 보이며, 이 기능이 module로 들어갈 것인지 커널에 built-in으로 해서 VM code들의 약간의 수정과 함께 들어가게 될 것인지도 확실지 않다. 또한 rmap의 hooking을 통해 page들을 shared page들을 tracking하게 될지 또한 명확하지 않다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2464049845469543351?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2464049845469543351/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2464049845469543351&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2464049845469543351'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2464049845469543351'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/05/kernel-shared-memory.html' title='Kernel Shared Memory'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-401461230468232165</id><published>2009-04-17T08:15:00.007+09:00</published><updated>2009-04-17T08:41:49.959+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>COW and Direct I/O problem</title><content type='html'>barrios는 이 문제에 대해서 작년에 살짝 언급한 바 있다.&lt;br /&gt;http://barriosstory.blogspot.com/2008/12/corruption-with-odirect-and-unaligned.html&lt;br /&gt;&lt;br /&gt;사안이 사안이니만큼 한번 더 언급하기로 한다.&lt;br /&gt;사실 이것은 리눅스 커널의 전형적인 core bug이다. 그러므로 이 문제를 이해하기 위해서는 kernel core의 page handling과정에 대한 이해가 필요하다.&lt;br /&gt;&lt;br /&gt;이 문제를 다시 언급하는 이유는 두가지이다.&lt;br /&gt;&lt;br /&gt;1. 이 문제는 아직 리눅스 커널에서 해결되지 못하고 있다.&lt;br /&gt;2. 이 문제를 보고서도 뭐가 문제인지조차 알기 쉽지 않다는 것이다.&lt;br /&gt;&lt;br /&gt;1에 대한 comment&lt;br /&gt;&lt;br /&gt;해결되지 못하는 이유는 Linus때문이다. 이미 Nick과 Andrea는 이 문제를 풀기위한 solution을 진작에 내놓았었다. 성능을 최대한 떨어뜨리지 않으면서 이 문제를 풀기 위해 code가 다소 복잡하다.&lt;br /&gt;반면 Kosaki가 내놓은 이 &lt;a href="http://lkml.org/lkml/2009/4/14/34"&gt;패치&lt;/a&gt;는 간단하긴 하지만(하지만 아직도 fast gup에 대한 concurrency 문제와 fork에 대한 latency, 특히 이 fork의 문제는 다소 심각해질 것 같다. 오늘 날짜로 보고된 Christoph의 &lt;a href="http://lkml.org/lkml/2009/4/16/340"&gt;report&lt;/a&gt;에 따르면 fork의 overhead가 2.6.22에 비해서 2.6.29는 2배 이하로 커진 것을 알 수 있기 때문이다.) 아직 많은 지적이 있다. 하지만 Linus는 코드수의 변경이 적은 Kosaki의 패치에 손들 들어주었다. Linus는 그때까지만 해도 fork에 대한 overhead는 크지 않다고 봤다. 물론이다. fork와 O_direct가 race condition이 될 확률은 크지 않다. 하지만 direct I/O가 계속해서 발생하게 되면 fork는 starvation 문제를 가질 수도 있으며, 안 그래도 overhead가 심각한 현재 fork의 구조에서 또 다른 lock을 check하는 것은 좋은 생각이 아닐 수도 있다.&lt;br /&gt;&lt;br /&gt;2에 대한 comment&lt;br /&gt;&lt;br /&gt;이 문제에 관심을 가질수 있는 사람들을 위해 barrios는 최대한 쉽게 설명할 수 있는 그림을 그려 보았다. 여기까지가 barrios가 할 수 있는 최선이다.&lt;br /&gt;&lt;br /&gt;아래 그림은 이 &lt;a href="http://lkml.org/lkml/2009/4/14/35"&gt;패치&lt;/a&gt;의 테스트 프로그램이 왜 실패하는지에 대한 설명을 하는 그림이다. 패치의 테스트 프로그램과 함께 이 내용을 보아야 한다. &lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/__HVFGzHYaLo/SefCNbXMcrI/AAAAAAAAFpo/AQPuQIk0qac/s1600-h/DIO_COW_problem.JPG"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 400px; height: 317px;" src="http://3.bp.blogspot.com/__HVFGzHYaLo/SefCNbXMcrI/AAAAAAAAFpo/AQPuQIk0qac/s400/DIO_COW_problem.JPG" border="0" alt=""id="BLOGGER_PHOTO_ID_5325438620328030898" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-401461230468232165?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/401461230468232165/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=401461230468232165&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/401461230468232165'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/401461230468232165'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/04/cow-and-direct-io-problem.html' title='COW and Direct I/O problem'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/__HVFGzHYaLo/SefCNbXMcrI/AAAAAAAAFpo/AQPuQIk0qac/s72-c/DIO_COW_problem.JPG' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3490325514190628949</id><published>2009-04-11T18:03:00.002+09:00</published><updated>2009-04-12T20:30:52.402+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>mm: more likely reclaim MADV_SEQUENTIAL mappings</title><content type='html'>&lt;a href="http://lkml.org/lkml/2008/7/19/130"&gt;http://lkml.org/lkml/2008/7/19/130&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이번 2.6.29에 패치된 기능중의 하나이다.&lt;br /&gt;Hannes에 의해 추가되었으며, Rik과 Nick간의 다소 격양된 언쟁이 있었던 패치이기도 하다.&lt;br /&gt;어쨌든, Andrew는 이 패치의 유용성에 대해 인정하였으며, 이번 2.6.29에 반영되었다.&lt;br /&gt;&lt;br /&gt;Barrios가 2008년 7월에 언급되었던 이 패치를 지금 다시 이야기 하는 나름데로의 이유가 있다.&lt;br /&gt;&lt;br /&gt;먼저 이 패치가 이루고자 하는 목표는 Page 회수를 좀더 똑똑하게 하자는 것이며,&lt;br /&gt;리눅스 커널의 Man page의 madvise에 대한 기능을 완수하기 위한 것이기도 하다.&lt;br /&gt;&lt;br /&gt;먼저 madvise의 man page를 살펴보면 다음과 같은 언급이 있다.&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;The &lt;b&gt;madvise&lt;/b&gt;() system call advises the kernel about how to handle paging input/output in the address range beginning at address &lt;i&gt;start&lt;/i&gt; and with size &lt;i&gt;length&lt;/i&gt; bytes.&lt;br /&gt;...&lt;br /&gt;&lt;dl compact="compact"&gt;&lt;dt&gt;&lt;b&gt;MADV_SEQUENTIAL&lt;/b&gt; &lt;/dt&gt;&lt;dd&gt;Expect page references in sequential order. (Hence, pages in the given range can be aggressively read ahead, and may be freed soon after they are accessed.) &lt;/dd&gt;&lt;/dl&gt;&lt;/blockquote&gt;&lt;dl compact="compact"&gt;&lt;dd&gt;&lt;/dd&gt;&lt;/dl&gt;&lt;br /&gt;위와 같이 sequential한 access는 첫째, readahead를 보다 공격적으로 하기 시작할 것이다.&lt;br /&gt;둘째, 그리고 그  페이지들을 곧 회수될 수 있다.&lt;br /&gt;&lt;br /&gt;리눅스 커널은 현재까지 첫째에 대해서는 충실했었지만 둘째에 대해서는 충실하지 못했다.&lt;br /&gt;이번 패치는 Hannes에 의해 두번째 문제를 충족시켜주기 위한 패치이다.&lt;br /&gt;패치는 정말 간단하다.  페이지를 promotion 시키기 전, vma의 seqential access 체크를 하여&lt;br /&gt;그렇다면 promotion 시키지 않는다는 것이다.&lt;br /&gt;즉, inactive list에 있는 page들을 active list로 옮기기 위한 확률을 줄이는 것이다. 그러므로  page reclaimer는 sequential access  페이지들을 보다 빨리 회수할 수 있게 된다.&lt;br /&gt;이는 결과적으로 시스템의 working set들을 유지하는 데 도움을 주게 되므로 시스템의 전반적인 성능 또한 향상 시킬 수 있다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;많은 시스템 프로그래머들은 데이터 파일을 읽어들여본 경험이 있을 것이다.&lt;br /&gt;물론 random한 offset으로 파일을 읽어들이는 경우도 많지만, 동영상을 재생하는 경우나 파일을 복사하는 경우, 또는 파일을 읽어들여 네트워크로 전송하는 경우와 같이 데이터 파일을 sequential하게 읽어들여야 하는 경우도 많이 있다.&lt;br /&gt;&lt;br /&gt;이 블로그를 읽고 있는 사람이라면 너무나도 잘 알듯이 리눅스 커널의 메모리 관리 정책은 파일에 대한 접근을 모두 page cache에 보관하게 된다는 점을 잘 알고 있을 것이다.&lt;br /&gt;&lt;br /&gt;위와 같은 스트림 데이터들을 page cache에 보관하면 어떤 이점이 있을까?&lt;br /&gt;없다.&lt;br /&gt;&lt;br /&gt;하지만 커널에서는 유저가 스트림 데이터와 같이 한번 접근하고 나서는 불필요한 파일을 접근하는지, 아니면 두고두고 참조할 파일을 정확하게 알 수 있는 방법은 없다. 그래서 나름데로 커널은 readahead 정책을 활용하여 heuristic하게   적용한다.&lt;br /&gt;&lt;br /&gt;그러므로 파일의 사용패턴을 그 누구보다 잘 아는 것은 application 그 자신이다. &lt;br /&gt;Application은 자신이 사용할 파일이기 때문에 어떻게 그 파일을 사용할 것인지 이미 알고 있다.&lt;br /&gt;그러므로 이런 Application들이 커널에게 hint를 준다면 얼마나 고마운 일인가 ?&lt;br /&gt;&lt;br /&gt;그러면 커널은 그러한 hint가 없다면 무엇을 하는가?&lt;br /&gt;&lt;br /&gt;리눅스 커널의 page reclaim 관련 루틴들은 자주 참조되는 페이지와 그렇지 않은 페이지들을 잘 관리해보려고 애쓴다.  애는쓰되 효율적이지 못할 경우도 있다.&lt;br /&gt;커널은 최선을 다할 뿐이지 결과는 장담할 수 없다.&lt;br /&gt;&lt;br /&gt;너무 커널이 무책임하다고 생각하는가?&lt;br /&gt;&lt;br /&gt;그렇게 커널이 무책임하지는 않다.&lt;br /&gt;그래서 커널이 제공하는 시스템 콜이 mdvise, fadvise, open(O_DIRECT)와 같은  것들이&lt;br /&gt;있는 것이다.&lt;br /&gt;&lt;br /&gt;최소한 지각있는 application 개발자라면 커널에게 hint 정도는 줄 수 있는 것 아닌가?&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;내가 지금부터 이 파일을  sequential하게 읽을거야!&lt;/blockquote&gt; 정도는.&lt;br /&gt;&lt;br /&gt;응용 프로그램 개발자들은 최소한 커널이 제공하는 수준의 시스템 콜을 잘 이용할 수 있는 의무와 권리가 있다.&lt;br /&gt;이를 이행하지 않으며 모든 것을 커널에게 맡기겠다는 것은 사실 응용 어플리케이션 개발자들의 직무유기이다.&lt;br /&gt;&lt;br /&gt;꼬랑지)&lt;br /&gt;Kernel이  applictaion들을 위해 얼마나 많은 것들을 제공해주어야 하는지에 대한 논쟁은 언제나 뜨거운 감자이지만, 새로운 기능을 넣고자 하는 자는 언제나 자신의 기능에 대한 benefit이 기존의 커널에 대한 regression보다 우월하다는 쉽지 않은 증명을 해야만 할 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3490325514190628949?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3490325514190628949/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3490325514190628949&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3490325514190628949'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3490325514190628949'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/04/mm-more-likely-reclaim-madvsequential.html' title='mm: more likely reclaim MADV_SEQUENTIAL mappings'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-473147552157006917</id><published>2009-04-09T08:13:00.003+09:00</published><updated>2009-04-09T08:35:30.525+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Memory Failure Report throuth MCE</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/4/7/368"&gt;http://lkml.org/lkml/2009/4/7/368&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Intel의 앞으로 나올 CPU에 background로 memory를 check하여 error를 report해주는 기능이 들어간다고 Andi는 전하고 있다.&lt;br /&gt;Report는 기존의 x86 specific한 Machine Check Exception을 그대로 사용할 것이며, MCE register를 통해 error가 발생한 물리 주소를 얻을 수 있게 된다.&lt;br /&gt;&lt;br /&gt;그러므로 OS가 이 기능을 적절히 활용하기 위해서 Andi는 하드웨어가 나오기전 먼저 Linux OS에 대해서 상기 기능을 어떻게 활용할 것인지에 대해 RFC를 내놓았다.&lt;br /&gt;&lt;br /&gt;Andi가 이번 패치에서 주 target으로 정한 것은 KVM이다. Host에서 error정보를 전달 받아 그 내용을 KVM guest들에게 전달하기 위한 설비이다. 하지만 이 기능은 KVM에 종속되지 않으며 얼마든지 다른 응용 프로그램들도 사용할 수 있도록 generic하게 설계되었다.&lt;br /&gt;&lt;br /&gt;정보를 알리는 방식은 새로운 signal을 사용하는 방식이며, error가 발생한 page의 특성에 따라 다르게 동작한다.&lt;br /&gt;&lt;br /&gt;1. slab page&lt;br /&gt;2. reserved page&lt;br /&gt;3. page cache clean page&lt;br /&gt;4. page cache dirty page&lt;br /&gt;5. unknown page&lt;br /&gt;6. free page&lt;br /&gt;7. swap clean page&lt;br /&gt;8. swap dirty page&lt;br /&gt;9. anonymous page&lt;br /&gt;10. unevictable page&lt;br /&gt;11. huge page&lt;br /&gt;12.compound page&lt;br /&gt;&lt;br /&gt;하지만 현재는 RFC단계로 위의 모든 type에 대해 구현되어 있지 않은 상태이다.&lt;br /&gt;&lt;br /&gt;이 패치의 tricky한 part는 다른 VM 사용자들의 page에 대해 비동기적으로 접근하게 된다는 점이다. 그것은 page 동기화에 대한 rule을 해치는 일이 될 수 있기 때문에 매우 조심해야 한다. Andi가 이 패치에 대해 제일 걱정하는 부분이 바로 이 부분이다. 리눅스 커널의 page관련 lock 처리는 매우 골치아픈 부분이다.&lt;br /&gt;&lt;br /&gt;현재, mainline에서 이 패치의 기능에 대해서는 모두 수긍하는 편이며 구현 또한 RFC 단계 치고는 상당히 깖끔하다. 앞으로 남은 주제는 아직 구현되어 있지 않은 page type에 대해 어떻게 처리할 것인가와 함께 비동기적인 page에 대한 접근에서 발생할 수 있는 문제에 대한 coverage등이 될 것으로 보인다.&lt;br /&gt;&lt;br /&gt;이 패치는 하드웨어적으로  아직 들어가 있지 않은 구현에 대한 검증을 위해서 소프트웨어적으로 프로세스의 page를 poisoning할 수 있는 별도의 test 기능까지 구현되어 있다.&lt;br /&gt;&lt;br /&gt;꼬랑지)&lt;br /&gt;이 패치를 보면 Andi가 속한 Intel의 Open Source Lab이 무엇을 하는지 잘 알 수 있다.&lt;br /&gt;아직 시장에 나오지 않은 기능에 대해 OS community에 선행 학습을 시키며 앞으로 나올 자신들의 하드웨어의 판매전략을 위해 기존 OS에 미리 기능을 구현해 놓겠다는 것인데..&lt;br /&gt;&lt;br /&gt;아직까지도 하드웨어에만 목을 매는 우리나라의 몇몇 기업들의 우둔한 전략에 대해 할말이 너무나도 많지만..&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-473147552157006917?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/473147552157006917/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=473147552157006917&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/473147552157006917'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/473147552157006917'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/04/memory-failure-report-throuth-mce.html' title='Memory Failure Report throuth MCE'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6382552019786577405</id><published>2009-03-23T20:55:00.003+09:00</published><updated>2009-03-23T21:27:55.919+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH] shmem: writepage directly to swap</title><content type='html'>&lt;a href="http://www.gossamer-threads.com/lists/linux/kernel/1050286?page=last"&gt;&lt;br /&gt;http://www.gossamer-threads.com/lists/linux/kernel/1050286?page=last&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Hugh의 금일 패치이다. 한 줄의 패치이지만 이 패치를 위해서는 그의 수년간의 경험이 녹아 있다.&lt;br /&gt;&lt;br /&gt;내용은 다음과 같다.&lt;br /&gt;shmem_writepage 함수는 약간 특별한 함수이다.&lt;br /&gt;왜냐하면 일반적인 다른 file system과는 달리 shmem_writepage가 page를 바로 flush하지 않기 때문이다.&lt;br /&gt;&lt;br /&gt;shmem_writepage는 regular writeback이나 sync로부터 호출되지 않는다. 이미 backing device info에서 것을 막는다. 반면, writepage가 호출되는 것은 memory pressure에 의해 page를 swap out 할 때이다.&lt;br /&gt;&lt;br /&gt;하지만 이때 다른 파일 시스템처럼 바로 페이지를 block layer로 내려 보내는 것이 아니라,&lt;br /&gt;swap cache를 이용해 한번더 reclaim될 수 있는 기회를 준다. 그렇게 하는 이유는 일반적으로 tmpfs(shared memory를 구현하기 위해 사용된)와 같은 ramfs는(여기서는 그냥 넘어가지만 ramfs와 tmpfs는 엄연히 다른 fs이다. 비록 tmpfs가 ramfs를 모태로 하지만. 언젠가 issue가 있으면 설명할 날이 오겠지)의 목적은 일반 파일 시스템과 다르기 때문이다.&lt;br /&gt;&lt;br /&gt;메모리 파일 시스템을 사용하는 사용자의 의도는 특별한 이유가 없으면 파일들이 RAM에 상주하길 바란다는 것이다. 그러므로 shmem_writepage는 바로 회수하는 것이 아닌 한번 더 기회를 주는 것이다.&lt;br /&gt;&lt;br /&gt;하지만 문제는 여기서 부터 시작한다. 그리고 이 문제는 SLUB과 얽혀 있기도 하다.&lt;br /&gt;&lt;br /&gt;Hugh가 지적한 것이 바로 이것이다. 수년동안 지켜봤는데, shmem page들에게 한번 더 기회를 줘서 얻는 이득이 없다는 것이다. 오히려 해가 되면 해가 됐지.&lt;br /&gt;&lt;br /&gt;게다가 2.6.28에서 split lru가 merge되며, tmpfs와 shmem을 SwapBacked 페이지로 다시 분류하였고 이는 file page보다 swap out되기가 더 어렵기 때문에 그 의도는 충분히 반영되었다는 것이다. 일리가 있는 말이다.&lt;br /&gt;&lt;br /&gt;그럼 문제가 어떻게 발생했는지 살펴보자.&lt;br /&gt;테스트는 tmpfs workload에서 실험한다.&lt;br /&gt;&lt;br /&gt;문제는 shmem_inode_cache에서 부터 시작한다. SLUB을 primary SLAB으로 사용하면서 shmem_inode_cache를 위해서는 슬랩당 4개의 페이지를 사용한다. 그러므로 tmpfs의 workload를 실행하여 많은 inode를 할당하다 보면 4개의 연속된 페이지를 계속 필요로 하게  될 것이다. memory pressure가 점차 심해지자 page scanning이 되며 tmpfs 페이지들이 바로 swap out되는 것이 아니라 swap cache로 이동을 하게 될 것이다. 이때 할당된 swap entry들은 연속된 swap area로 할당될 것이다. (이는 swap file system의 특징이다. 되도록 이면 연속된 swap offset을 할당하여 disk seek을 줄이려는 의도이다.)&lt;br /&gt;부하가 점점 더 심해진다. 결국 4개의 연속된 페이지를 찾기 위해 lumpy가 동작하게 된다.&lt;br /&gt;lumpy의 회수 페이지의 패턴을 분석해보니 첫번째 페이지만 LRU의 bottom에 존재하게 되고, 나머지는 굉장히 random하게 LRU의 중간 중간에서 회수된다는 것이다.&lt;br /&gt;그러므로 swap file system이 아무리 연속된 swap offset을 할당한다 하더라도 결국, 페이지는 scatter되어 writeout되는 꼴이 되어버리고 만 것이다.&lt;br /&gt;&lt;br /&gt;이는 flash를 사용하는 장치를 swap device로 사용할 때 큰 문제가 된다. 왜냐하면 flash의 특징은 write를 위해서는 보다 큰 영역을 먼저 erase해야 하기 때문이다. 그러므로 flash의 특성상 random write의 merge는 굉장히 큰 effect를 갖게 된다. 허나 위의 문제로 인해 I/O의 merge 비율이 크게 떨어지면 엎친데 덮친격으로 random write 속도 또한 굉장히 떨어진다는 것이다.&lt;br /&gt;&lt;br /&gt;Hugh는 대략 5%의 성능향상이 있다고 말하고 있다.&lt;br /&gt;패치를 보라. 단 한줄 수정했다. (Dummy function 제외하고)&lt;br /&gt;&lt;br /&gt;이 한줄을 위해 그가 분석한 자료와 kernel에 대한 지식은 상당하다.&lt;br /&gt;커널 개발자란 적어도 이 정도의 core knowledge를 가지고 있어야 커널 개발자라고&lt;br /&gt;말할수 있지 않을까?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6382552019786577405?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6382552019786577405/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6382552019786577405&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6382552019786577405'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6382552019786577405'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/patch-shmem-writepage-directly-to-swap.html' title='[PATCH] shmem: writepage directly to swap'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-9212558575039095864</id><published>2009-03-22T23:12:00.006+09:00</published><updated>2009-03-23T10:07:13.928+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>fsblock</title><content type='html'>&lt;a href="http://lwn.net/Articles/322668/"&gt;http://lwn.net/Articles/322668/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;fsblock에 대한 기사가 LWN에 실렸다. 굉장히 기대하고 있었던 기사였는데 ..&lt;br /&gt;이번 기사 내용은 다소 실망스러웠다. 기대가 너무 컸던 것일수도 있고..&lt;br /&gt;&lt;br /&gt;Anyway, 시작한다.&lt;br /&gt;&lt;br /&gt;fsblock을 처음 접한 것은 2007년 6월 이었다. 하지만 이제서야 기사화 된 이유는&lt;br /&gt;fsblock 자체가 커널 core의 buffer layer에 대한 "완전한" 재작업이기 때문이다.&lt;br /&gt;Kernel core중 가장 변하지 않고 오래됐던 코드 들 중의 하나인 buffer layer를 incremental patching이 아닌 한번에 바꾸려는 Nick의 시도(이러는 데는 나름 이유가 있다. 이유 생략)로 인하여 mainline에서의 거부감도 있지만 많은 파일 시스템 개발자들을 혹하게 하는 feature도 가지고 있다.&lt;br /&gt;&lt;br /&gt;최근 Nick은 2007년 시도에 이어 몇번의 refactoring 및 논란의 여지가 있는 부분들은 삭제하고 최근 간단하게 5개의 패치를 통하여 minix, ext2, xfs 등을 새로운 fsblock에 포팅한 패치를 제공하였다.&lt;br /&gt;&lt;br /&gt;이 패치와 barrios는 사실 굉장한 인연을 가지고 있다.&lt;br /&gt;barrios가 본격적으로 Virtual Process Memory쪽에 집중했던 것이 바로 2007년 6월이기 때문이다. 즉, 이 패치는 barrios가 linux kernel의 memory를 들여다 보게 해준 기회를 제공하였기 때문이다.&lt;br /&gt;&lt;br /&gt;사실, buffer layer 를 보다 정확히 이해하려면 메모리에 대한 이해가 선행되어야 한다. 그 이유는 buffer layer가 리눅스에서는 page cache의 위에 구현되어지며, memory와 block간의 연결을 담당하고 있기 때문이다. 그러므로 buffer layer의 instance인 struct buffer_head는 struct page와 많은 부분 sync가 되어야 한다. 그 말은 page에 대한 많은 operation들이 buffer_head들을 care해야 한다는 말이기도 하다. 그러므로 page를 커널이 어떻게 care하는지 먼저 정확히 알지 못하면 커널이 buffer_head를 어떻게 care하는지 또한 정확히 이해한다고 볼 수 없기 때문이다.&lt;br /&gt;&lt;br /&gt;하지만 그게 다가 아니다. 이 layer를 이해하려면 inode에 대한 커널의 handling 또한 명확히 이해하고 있어야 하며, file system들이 어떻게 buffer_head들을 handling 하는지, page와의 Sync를 어떻게 care해야 하는지 모두 알고 있어야 한다. 휴~&lt;br /&gt;&lt;br /&gt;결국 이것을 정확히 이해한다는 것은 커널의 core를 정확히 이해한다는 것이다.&lt;br /&gt;그러므로 barrios는 아직 fsblock에 장,단점에 대해 code level에서 명확하게 이해하지 못하고 있다.  아직 넘어야 할 산이 많다.&lt;br /&gt;&lt;br /&gt;말이 샜다.&lt;br /&gt;&lt;br /&gt;Nick이 말하고 있는 fsblock(음..먼저 이 이름부터 명확히 하고 넘어가자. 왜 이름을 fsblock이라고 지었을까?? file system과 block layer를 연결한다고 해서 그렇게 했덴다. 그 전에 buffer_head는 이름이 너무 모호하지 않았던가..) 의 장점은 다음과 같은 것들이 있다.&lt;br /&gt;&lt;br /&gt;1. 기존의 buffer_head에 비해서 작은 size&lt;br /&gt;2. 기존에는 한 page에 대한 buffer_head들의 연결 리스트였지만, fsblock은 연속된 페이지 상에 위치함으로 cache footprint를 줄일 수 있음&lt;br /&gt;3. per-inode lock을 더 이상 사용하지 않고 lookup과 locking을 위해 page cache를 사용함. 이는 곧 lockless page cache와 함께 lock의 사용을 없앨 수 있음(하지만 약간의 문제가 아직 남아 있음)&lt;br /&gt;4. page cache와 buffer_head간의 중복된 플래그를 제거. 이는 fsblock이 page와 fsblock의 동기화에 대한 신경을 많이 쓰고 있음을 반증.&lt;br /&gt;5. larget block support - 페이지 보다 훨씬 큰 size의 block 을 지원함. 현재 32M 까지를 지원함.&lt;br /&gt;6. 코드 사이즈를 기존 대비 2/3로 줄임.&lt;br /&gt;&lt;br /&gt;이 밖에도 barrios가 설명하기 힘든 많은 장점들을 가지고 있다고 한다.&lt;br /&gt;Barrios는 조만간 다시 이 코드들을 review하기 시작할 예정이다.&lt;br /&gt;&lt;br /&gt;왜냐하면 fsblock은 Nick이 진행하고 있는 것이니 만큼 결국 mainline에 merge가 될 것이며, 그때 kernel에 끼치는 effect이 꽤 될 것이고, kernel core를 이해하기 위해서는 꼭 필요한 지식이 될 것이라 생각하기 때문이다. Good Luck.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-9212558575039095864?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/9212558575039095864/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=9212558575039095864&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/9212558575039095864'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/9212558575039095864'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/fsblock.html' title='fsblock'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2387906200339384701</id><published>2009-03-15T21:47:00.003+09:00</published><updated>2009-03-15T22:08:52.104+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>Barrios Junior</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://lh3.ggpht.com/__HVFGzHYaLo/Sa6Anizi-PI/AAAAAAAAEb8/5Gj3eDfzjwc/s640/IMG_0084.JPG"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer; width: 380px; height: 285px;" src="http://lh3.ggpht.com/__HVFGzHYaLo/Sa6Anizi-PI/AAAAAAAAEb8/5Gj3eDfzjwc/s640/IMG_0084.JPG" alt="" border="0" /&gt;&lt;/a&gt;요즘 게시물의 수가 매우 적다.&lt;br /&gt;&lt;br /&gt;여러 이유가 있지만 오른쪽에 사진을 올렸듯이 큰 이유 중 하나는 이 친구 때문이기도 하다.&lt;br /&gt;&lt;br /&gt;Barrios를 쏘옥 빼닮은 이 친구는 barrios의 junior이다. 지난 달 태어난 이 친구가 자꾸 눈 앞에 아른아른 거려 barrios의 시간 관리는 완전히 변했다.&lt;br /&gt;&lt;br /&gt;다행히도 눈은 green-mail의 눈을 닮아 아주 크고 똘망똘망한 것이, 것을 빼고는 나의 어릴 적과 똑같다. 태어나자마자 구렛나루를 지니고 태어난 것까지 말이다.&lt;br /&gt;&lt;br /&gt;이 친구는 틈만 나면 나의 부성을 자극하기 때문에 당분간 barrios는 많은 시간을 이 친구와 보내게 될 것이다.&lt;br /&gt;&lt;br /&gt;지금 이 글을 쓰는 이유 또한 4시건 전 마지막으로 본 이 친구의 모습이 곰실곰실 되기 때문이다.  다시 보려면 또 한주가 지나야 하니 시간아 어서 가라~&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2387906200339384701?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2387906200339384701/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2387906200339384701&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2387906200339384701'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2387906200339384701'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/barrios-junior.html' title='Barrios Junior'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://lh3.ggpht.com/__HVFGzHYaLo/Sa6Anizi-PI/AAAAAAAAEb8/5Gj3eDfzjwc/s72-c/IMG_0084.JPG' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2217650387556015482</id><published>2009-03-15T20:54:00.005+09:00</published><updated>2009-03-15T21:31:30.805+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Checkpoint/restart tries to head towards the mainline</title><content type='html'>&lt;a href="http://lwn.net/Articles/320508/"&gt;http://lwn.net/Articles/320508/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Checkpoint/restart가 벌써 v13이다.&lt;br /&gt;barrios가 처음 이 패치를 review했던 것이 08년 9월이니 벌써 6달이 지났다.&lt;br /&gt;그 후로 몇번의 review요청이 왔었으나 다른 일들로 follow up하지 못하고 있었다.&lt;br /&gt;&lt;br /&gt;그동안 Oren은 Hansen과 함께 이 패치를 계속해서 improve시켜왔다.&lt;br /&gt;하지만 Checkpoint/restart는 결코 가벼운 패치가 아니다. 제대로 동작하기 위해서는 커널 전반에 걸쳐 많은 core function들의 수정이 불가피하다.&lt;br /&gt;&lt;br /&gt;Oran은 이 패치가 mm에 merge되기를 바라고 있지만, Andrew는 여러 이유로 그것을 받아들이지 않고 있다.&lt;br /&gt;&lt;br /&gt;첫째로, 아직까지 toy 수준의 이러한 패치를 merge하게 된다면, 결곡 non-toy로 만들기 위해 받아들일 수 없을 정도로 비용이 큰 패치들을 계속해서 받아들여아 하거나.&lt;br /&gt;돌째로, 그러한 패치를 받아들이지 않아서 계속해서 toy로 남게 하거나,&lt;br /&gt;셋째로, 현재 빠져 있는 기능들에 대해서 그것들을 어떻게 구현하여 해결할지에 대해서 논의되지 않았다는 이유이다.&lt;br /&gt;&lt;br /&gt;현재 Checkpoint/restart는 매우 제한된 app에서만 동작할 수 있다.&lt;br /&gt;프로세스는 single thread여야 하며, fd operation은 open, lseek 정도만 restore될 수 있고, Shared memory, hugetlbfs, VM_NONLINEAR 등은 지원하지 못하고 있는 수준이다.&lt;br /&gt;이 밖에도 Dave Hansen은 여러 문제들을 자세히 나열하였다.&lt;br /&gt;&lt;br /&gt;하지만, 현재 어떤 기능이 구현되어 있느냐보다 더욱 중요한 문제는 현재로서 어떤 해결책도 없는 문제이거나 커널을 많이 고쳐야만 풀릴 수 있는 잠재적인 문제들이 있다는 것이다.&lt;br /&gt;&lt;br /&gt;기술적인 문제를 하나 소개하자면, 다음과 같은 문제가 있다.&lt;br /&gt;프로세스들이 어떻게 자신의 state가 checkpointable 한지를 결정하냐는 것이다.&lt;br /&gt;Ingo는 이 문제에 대해서  LSM security checks를 overloading하여 checkpointable 여부를 결정할 수 있는 flag를 사용하자는 것이다. 이 flag는 해당 app나  checkpoint시키길 원하는 프로세스들에게 노출시킬 수 있다는 것이다. 하지만 많은 사람들은 LSM의 많은 hook에 대한 overhead를 걱정하고 있다.&lt;br /&gt;&lt;br /&gt;이에 대한 또 다른 concern은 이 flag의 setting을 one-way로 하는 것이 바람직하냐는 것이다. 이 문제는 현재의 LSM hook의 문제이다. 현재의 LSM hook은 open은 검사하지만 close는 검사하지 않는 다는 것이다. 그러므로 다시 checkpointable 한 state가 되는 것을 알 수 없다는 것이다. 이에 대해 Ingo는 one-way flag가 맞는 방향이라고 얘기하고 있다. 그래서 Checkpoint를 사용하는 많은 user들로 하여금 커널의 uncheckpointable한 operation들에 대해 압력을 행사하도록 하여 수정을 유도하는 것이 좋다는 것이다.&lt;br /&gt;&lt;br /&gt;Checkpoint를 구현한 Opensource 프로젝트들이 다수 있지만 Oran과 Hansen은 그러한 오픈 소스 프로젝트들을 잘 이용하면 자신들의 구현이 훨씬 뛰어날 수 있다고 말하고 있으며, 반면, 커널 전반에 많은 수정을 가하게 될 이 패치를 Andrew는 아직 걱정하고 있다.&lt;br /&gt;&lt;br /&gt;계속해서 노력한다면 언젠가 merge가 되겠지만, barrios의 생각은 이 패치의 merge여부를 떠나 앞으로 이 패치를 지켜보면 커널 전반을 이해하기 위한 좋은 예제가 되지 않을까 하는 것이다.  ^^&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2217650387556015482?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2217650387556015482/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2217650387556015482&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2217650387556015482'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2217650387556015482'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/checkpointrestart-tries-to-head-towards.html' title='Checkpoint/restart tries to head towards the mainline'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6648808721946204502</id><published>2009-03-09T22:54:00.004+09:00</published><updated>2009-03-09T23:20:17.398+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Guitar'/><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>Encouragement</title><content type='html'>'99년 5월 전역하자마자, 부랴부랴 준비해 연주회에 올렸던 곡이다. &lt;br /&gt; &lt;br /&gt;Sor의 곡 답게 기교가 많은 곡이며, first와 second의 주고 받는 부분들과 마지막 변주에서의 빠른 스케일이 압권이다. &lt;br /&gt;&lt;br /&gt;기억에 남는 것이 높은 '미'가 굉장히 중요한 부분이었는 데, 그만 '레#'으로 쳐서 얼굴을 붉혔던 기억이 아직도 남아있다. 사실 그때 우리에게 있어, 연주회의 의미는 얼마나 멋지게 연주를 하느냐는 것은 개 개인의 욕심일 뿐, 더 중요했던 것은 연주자 한 사람 한사람으로 이루어진 합주단과 동아리 회원들간의 친목도모였다. &lt;br /&gt;&lt;br /&gt;합주연습이나 중주 연습이 끝나고 나면 언제나 학교 앞, 술집에 모여앉아 재미있게, 유익하게 보냈던 시간들이 아직도 내겐 너무 소중하다. &lt;br /&gt;&lt;br /&gt;그날 있었던 연습얘기부터 시작해서 음악얘기, 학업 얘기, 다시 동아리 얘기, 임원단 얘기, 또 동아리 얘기, 동아리 선배 얘기, 다시 동아리 얘기, 동아리에서 좋아하는 친구 얘기&lt;br /&gt;, 또 동아리 얘기.. 이야기에 묻혀 묻혀...하다하다 차 다 끊기고, 돈 떨어지고.... 가까운 선배들한테 SOS해서 얹혀 자고.. &lt;br /&gt;&lt;br /&gt;지금 어려운 시기에 이런 모습을 후배들에게 바라는 것은 선배들의 욕심일 뿐이겠지만,&lt;br /&gt;이런 경험을 가지고 있는 사람으로서 그렇지 못한 사람을 볼때에 가슴에서 끌어나오는&lt;br /&gt;열정을 느낄수가 없어 가끔은 답답하기 그지 없다. &lt;br /&gt;&lt;br /&gt;그때 그렇게 공부안하고 이야기에 묻혔던 그 친구들, 그 선배들, 그 후배들 다들 잘 살고 있는 것을 보면 우리가 그렇게 쓸데없이 등록금을 갖다 버린 것은 아닌 것 같다. &lt;br /&gt;&lt;br /&gt;이미 다 지난가버린 기억이 나이 먹은 아저씨의 쓸데없는 감성을 또 자극하는 구나. &lt;br /&gt;눈물나기 전에 얼른 오늘 하루 마무리하고 자야지~&lt;br /&gt;&lt;br /&gt;&lt;object width="425" height="264"&gt;&lt;param name="movie" value="http://www.youtube.com/v/bL7y0sNcyvs&amp;hl=ko&amp;fs=1&amp;color1=0x5d1719&amp;color2=0xcd311b"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/bL7y0sNcyvs&amp;hl=ko&amp;fs=1&amp;color1=0x5d1719&amp;color2=0xcd311b" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="264"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;br /&gt;&lt;br /&gt;&lt;object width="425" height="264"&gt;&lt;param name="movie" value="http://www.youtube.com/v/8neYwv99AEM&amp;hl=ko&amp;fs=1&amp;color1=0x5d1719&amp;color2=0xcd311b"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/8neYwv99AEM&amp;hl=ko&amp;fs=1&amp;color1=0x5d1719&amp;color2=0xcd311b" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="264"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6648808721946204502?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6648808721946204502/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6648808721946204502&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6648808721946204502'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6648808721946204502'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/encouragement.html' title='Encouragement'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3479536945753469834</id><published>2009-03-06T13:05:00.003+09:00</published><updated>2009-03-06T13:41:31.302+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[patch] fs: new inode i_state corruption fix</title><content type='html'>역시 이런 core 쪽의 BUG는 언제나 Nick이 해결한다.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://patchwork.kernel.org/patch/9984/"&gt; http://patchwork.kernel.org/patch/9984/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;문제는 inode-&gt;i_state의 I_NEW state에 대한 race condition문제이다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;void unlock_new_inode(struct inode *inode)&lt;br /&gt;{&lt;br /&gt;#ifdef CONFIG_DEBUG_LOCK_ALLOC&lt;br /&gt; if (inode-&gt;i_mode &amp;amp; S_IFDIR) {&lt;br /&gt;   struct file_system_type *type = inode-&gt;i_sb-&gt;s_type;&lt;br /&gt;&lt;br /&gt;   /* &lt;br /&gt;    * ensure nobody is actually holding i_mutex&lt;br /&gt;    */&lt;br /&gt;   mutex_destroy(&amp;amp;inode-&gt;i_mutex);&lt;br /&gt;   mutex_init(&amp;amp;inode-&gt;i_mutex);&lt;br /&gt;   lockdep_set_class(&amp;amp;inode-&gt;i_mutex, &amp;amp;type-&gt;i_mutex_dir_key);&lt;br /&gt; }&lt;br /&gt;#endif&lt;br /&gt; /*&lt;br /&gt;  * This is special!  We do not need the spinlock&lt;br /&gt;  * when clearing I_LOCK, because we're guaranteed&lt;br /&gt;  * that nobody else tries to do anything about the&lt;br /&gt;  * state of the inode when it is locked, as we&lt;br /&gt;  * just created it (so there can be no old holders&lt;br /&gt;  * that haven't tested I_LOCK).&lt;br /&gt;  */&lt;br /&gt; inode-&gt;i_state &amp;amp;= ~(I_LOCK|I_NEW);&lt;br /&gt; wake_up_inode(inode);&lt;br /&gt;}&lt;/blockquote&gt;주석에서 보는 것과 같이 kernel은 의도적으로 inode의 state를 변경함에도 불구하고 spinlock을 잡지 않았다. 왜냐하면&lt;br /&gt;1. 새로 생성되는 inode의 state에는 I_LOCK|I_NEW가 걸리게 되며, 새로 생성된 inode이기 때문에 이전에 이 inode에 대해서 I_LOCK을 test하지 않고 inode를 잡고 있는 녀석도 없을 테고,&lt;br /&gt;2. inode가 lock되어 있을 때는 inode의 state를 바꾸기 위한 어떤 시도도 이루어질 수 없음으로&lt;br /&gt;&lt;br /&gt;이 곳에서 spinlock이 굳이 필요 없다는 것이다.&lt;br /&gt;&lt;br /&gt;하지만 패치에 명시된 문제가 발생한 것이다. CPU0과 CPU1이 unlock_new_inode와 __sync_single_inode를 패치에 명시된 순서대로 실행 되었을 경우, 해지된 I_NEW state가 다시 지정되어 결국 wake_up_inode가 프로세스를 깨우지 않게 되는 문제이다. &lt;br /&gt;&lt;br /&gt;이 문제를 해결하기 위해서  Nick은 __sync_single_inode에서 I_NEW state를 기다리는 것 보다는 해당 inode를 queue에 다시 넣고 일단 skip하는 방법을 택했다. 합리적인 결정이다.&lt;br /&gt;&lt;br /&gt;왜냐하면 동시에 막 생성되고 있는 inode들은 data integrity operation의 대상이 아니며 dirty memory에도 별로 영향을 미치지 않을 것이라는 이유에서이다.&lt;br /&gt;&lt;br /&gt;역시 Nick, Good job!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3479536945753469834?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3479536945753469834/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3479536945753469834&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3479536945753469834'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3479536945753469834'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/patch-fs-new-inode-istate-corruption.html' title='[patch] fs: new inode i_state corruption fix'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3082859753769589294</id><published>2009-03-04T18:59:00.004+09:00</published><updated>2009-03-04T19:04:55.659+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>미국인 barrios</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_x1T3vyNglZo/Sa5RnD8F-eI/AAAAAAAAAH0/AT7VjLM3wi8/s1600-h/kernelhacker.JPG"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer; width: 320px; height: 198px;" src="http://2.bp.blogspot.com/_x1T3vyNglZo/Sa5RnD8F-eI/AAAAAAAAAH0/AT7VjLM3wi8/s320/kernelhacker.JPG" alt="" id="BLOGGER_PHOTO_ID_5309270742230497762" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://wiki.livedoor.jp/linuxfs/d/Linux_hackers_M"&gt;http://wiki.livedoor.jp/linuxfs/d/Linux_hackers_M&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;일본의 한 사이트이다. 웹검색하다 걸렸는데..&lt;br /&gt;뭐하는 사이트인지는 잘 모르겠지만..&lt;br /&gt;kernel hacker들의 정보를 수집해 놓았는데 linux kernel관련 사이트로 보인다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Minchan Kim - U.S ?? 나야 보내주면 좋겠지만...&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3082859753769589294?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3082859753769589294/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3082859753769589294&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3082859753769589294'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3082859753769589294'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/barrios.html' title='미국인 barrios'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_x1T3vyNglZo/Sa5RnD8F-eI/AAAAAAAAAH0/AT7VjLM3wi8/s72-c/kernelhacker.JPG' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5885352233728868155</id><published>2009-03-03T05:36:00.005+09:00</published><updated>2009-03-03T05:51:20.400+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Oops analysis in ARM</title><content type='html'>&lt;div&gt;&lt;table id="q8bz" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;이 글은 barrios의 좋지 않은 기억력을 보강하기 위해 2008년 1월에 작성된 글이다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Unable to handle kernel NULL pointer dereference at virtual address 00000000&lt;br /&gt;pgd = c1c58000&lt;br /&gt;[00000000] *pgd=10360031, *pte=00000000, *ppte=00000000&lt;br /&gt;Internal error: Oops: &lt;span style="color: rgb(153, 255, 255);"&gt;817&lt;/span&gt; [&lt;span style="color: rgb(153, 51, 0);"&gt;#1&lt;/span&gt;]&lt;br /&gt;Modules linked in: overflow&lt;br /&gt;CPU: 0&lt;br /&gt;PC is at read_overflow+0x38/0x4c [overflow]&lt;br /&gt;LR is at 0x1&lt;br /&gt;pc : [&lt;&lt;span style="color: rgb(153, 153, 255);"&gt;bf0000c0&lt;/span&gt;&gt;]    lr : [&lt;00000001&gt;]    Tainted: P&lt;br /&gt;sp : c035baf0  ip : 60000093  fp : c035befc&lt;br /&gt;r10: 00066178  r9 : 00000000  r8 : c1f25000&lt;br /&gt;r7 : 00000c00  r6 : 00002000  r5 : 00000000  r4 : 00000000&lt;br /&gt;r3 : 00000003  r2 : 00000000  r1 : 00001517  r0 : 00000000&lt;br /&gt;Flags: nZCv  IRQs on  FIQs on  &lt;span style="color: rgb(255, 102, 102);"&gt;Mode SVC_32&lt;/span&gt;  &lt;span style="color: rgb(255, 153, 0);"&gt;Segment user&lt;/span&gt;&lt;br /&gt;Control: 5317F&lt;br /&gt;Table: 11C58000  DAC: 00000015&lt;br /&gt;Process cat (pid: 31, stack limit = 0xc035a258)&lt;br /&gt;Stack: (0xc035baf0 to 0xc035c000)&lt;br /&gt;bae0:                                                        00000000 00000000 00000000 00000000&lt;br /&gt;bb00: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bb20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bb40: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bb60: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bb80: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bba0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bbc0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bbe0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bc00: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bc20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bc40: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bc60: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bc80: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bca0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bcc0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bce0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bd00: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bd20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bd40: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bd60: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bd80: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bda0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bdc0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bde0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;be00: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;be20: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;be40: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;be60: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;be80: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bea0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bec0: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000&lt;br /&gt;bee0: 00000000 00000000 00000000 00000000 c035bf4c c035bf00 c00b24a4 bf000098&lt;br /&gt;bf00: c035bf1c 00000000 00000021 c035bf78 c1fc4920 c035a000 00000000 00000000&lt;br /&gt;bf20: c035bf3c c0dc5b40 00066178 c035bf78 00002000 c0023f88 c035a000 00000000&lt;br /&gt;bf40: c035bf74 c035bf50 c00804c8 c00b2374 c035bfb0 00000000 00000000 00000000&lt;br /&gt;bf60: c0dc5b40 00000003 c035bfa4 c035bf78 c0080ba0 c0080424 00000000 00000000&lt;br /&gt;bf80: c002a4d8 00000000 c035bfa4 bed0aeb4 00002000 00066178 00000000 c035bfa8&lt;br /&gt;bfa0: c0023de0 c0080b6c bed0aeb4 00002000 00000003 00066178 00002000 00000001&lt;br /&gt;bfc0: bed0aeb4 00002000 00066178 00000003 00000001 ffffffff 00000003 00000000&lt;br /&gt;bfe0: 00000003 bed0ab50 00048a24 40119b7c 60000010 00000003 00000000 00000000&lt;br /&gt;Backtrace:&lt;br /&gt;[&lt;bf000088&gt;] (read_overflow+0x0/0x4c [overflow]) from [&lt;c00b24a4&gt;] (proc_file_read+0x140/0x2bc)&lt;br /&gt;[&lt;c00b2364&gt;] (proc_file_read+0x0/0x2bc) from [&lt;c00804c8&gt;] (vfs_read+0xb4/0x18c)&lt;br /&gt;[&lt;c0080414&gt;] (vfs_read+0x0/0x18c) from [&lt;c0080ba0&gt;] (sys_read+0x44/0x70)&lt;br /&gt;r7 = 00000003  r6 = C0DC5B40  r5 = 00000000  r4 = 00000000&lt;br /&gt;[&lt;c0080b5c&gt;] (sys_read+0x0/0x70) from [&lt;c0023de0&gt;] (ret_fast_syscall+0x0/0x2c)&lt;br /&gt;r6 = 00066178  r5 = 00002000  r4 = BED0AEB4&lt;br /&gt;&lt;span style="color: rgb(0, 102, 0);"&gt; Code: e59f0018 eb40fbc4 e3a00000 e3a03003 (e5803000) &lt;/span&gt;&lt;br /&gt;Segmentation fault&lt;br /&gt;&lt;br /&gt;&lt;/c0023de0&gt;&lt;/c0080b5c&gt;&lt;/c0080ba0&gt;&lt;/c0080414&gt;&lt;/c00804c8&gt;&lt;/c00b2364&gt;&lt;/c00b24a4&gt;&lt;/bf000088&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td width="100%"&gt;&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;1. pgd = c1c58000 값은 fault 시점에서의 current의 mm_struct 구조체 안에 들어있는 pgd 값이다. 즉 pgd가 저장되어 있는 가상 주소이다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="x5k8" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt; [00000000] *pgd=10360031, *pte=00000000, *ppte=00000000&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;2. 위의 첫번째 [00000000]은 fault를 일으킨 주소이며&lt;br /&gt;3. *pgd 값은 pgd에 저장되어 있는 값이다.&lt;br /&gt;4. pgd에 저장되어 있는 값을 통해 fault가 난 주소로 reslove한 *pte, *ppte또한 각각이 저장되어 있는 값이다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="ck09" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt; Internal error: Oops: 817 [#1]&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;5. 817은 fsr(Fault Status Register, data sheet 참조)의 값, 즉 error 값이며 #1은 die counter이다. 즉 die가 연속적으로 호출되거나 루프를 돌며 호출될 때 제일 중요하고 의미 있는 것은 첫번째 로그이다. 그것을 구별하도록 해준다.&lt;br /&gt;&lt;br /&gt;6. 다음 현재 시스템에 로드되어 있는 모듈의 이름을 print하여 준다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="kx88" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt; CPU: 0&lt;br /&gt;PC is at read_overflow+0x38/0x4c [overflow]&lt;br /&gt;LR is at 0x1&lt;br /&gt;pc : [&lt;bf0000c0&gt;]    lr : [&lt;00000001&gt;]    Tainted: P&lt;br /&gt;sp : c035baf0  ip : 60000093  fp : c035befc&lt;br /&gt;r10: 00066178  r9 : 00000000  r8 : c1f25000&lt;br /&gt;r7 : 00000c00  r6 : 00002000  r5 : 00000000  r4 : 00000000&lt;br /&gt;r3 : 00000003  r2 : 00000000  r1 : 00001517  r0 : 00000000&lt;br /&gt;Flags: nZCv  IRQs on  FIQs on  Mode SVC_32  Segment user&lt;br /&gt;Control: 5317F&lt;br /&gt;Table: 11C58000  DAC: 00000015&lt;/bf0000c0&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;7. 현재 수행중이었던 CPU를 출력하며&lt;br /&gt;8. fault가 난 시점에서의 register에 저장되어 있던 값들을 출력한다.&lt;br /&gt;&lt;br /&gt;9. mode는 드라이버에서 fault를 일으켰음으로 SVC_32 모드이며&lt;br /&gt;10. Segment user가 의미하는 것은 current가 kernel thread가 아닌 user thread에서 일어났다는 것이다. 이것을 아는 코드는 다음과 같다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="k39y" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;get_fs() == get_ds() ? "kernel" : "user");&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;get_fs()는 current의 thread_info구조체에 들어 있는 addr_limit 값을 가져온다. 반면 get_ds()는 커널의 DS 값을 가져온다.&lt;br /&gt;일반적으로 커널 쓰레드들은 user memory(0x0 ~ 0xc0000000)에 접근할 필요가 없기 때문에 ds 값이&lt;br /&gt;&lt;br /&gt;11. 그 위쪽으로는 현재의 stack pointer부터&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="l7d2" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="50%"&gt; 43 00000088 &lt;read_overflow&gt;:&lt;br /&gt;44   88: e1a0c00d  mov ip, sp&lt;br /&gt;45   8c: e92dd800  stmdb sp!, {fp, ip, lr, pc}&lt;br /&gt;46   90: e24cb004  sub fp, ip, #4  ; 0x4&lt;br /&gt;47   94: e24ddb01  sub sp, sp, #1024 ; 0x400&lt;br /&gt;48   98: e24b0b01  sub r0, fp, #1024 ; 0x400&lt;br /&gt;49   9c: e3a01b01  mov r1, #1024 ; 0x400&lt;br /&gt;50   a0: e240000c  sub r0, r0, #12 ; 0xc&lt;br /&gt;51   a4: ebfffffe  bl  0 &lt;__memzero&gt;&lt;br /&gt;52   a8: e59f001c  ldr r0, [pc, #28] ; cc &lt;.text+0xcc&gt;&lt;br /&gt;53   ac: ebfffffe  bl  0 &lt;printk&gt;&lt;br /&gt;54   b0: e59f0018  ldr r0, [pc, #24] ; d0 &lt;.text+0xd0&gt;&lt;br /&gt;55   b4: ebfffffe  bl  0 &lt;printk&gt;&lt;br /&gt;56   b8: e3a00000  mov r0, #0  ; 0x0&lt;br /&gt;57   bc: e3a03003  mov r3, #3  ; 0x3&lt;br /&gt;58   &lt;span style="color: rgb(255, 0, 0);"&gt;c0: e5803000  str r3, [r0]&lt;/span&gt;&lt;br /&gt;59   c4: e24bd00c  sub sp, fp, #12 ; 0xc&lt;br /&gt;60   c8: e89da800  ldmia sp, {fp, sp, pc}&lt;br /&gt;61   cc: 00000040  .word 0x00000040&lt;br /&gt;62   d0: 0000005c  .word 0x0000005c&lt;br /&gt;&lt;br /&gt;&lt;/printk&gt;&lt;/printk&gt;&lt;/read_overflow&gt;&lt;/td&gt;&lt;td width="50%"&gt;int read_overflow( char *page, char **start, off_t off,int count,int *eof, void *data_unused )&lt;br /&gt;{&lt;br /&gt;char stack_overflow[OVERFLOW_STACK];&lt;br /&gt;int *die = NULL;&lt;br /&gt;unsigned long fp;&lt;br /&gt;memset(stack_overflow, 0, OVERFLOW_STACK);&lt;br /&gt;&lt;br /&gt;printk("!!!!happen overflow!!!!\n");&lt;br /&gt;printk("!!!!wakeup!!!!\n");&lt;br /&gt;&lt;br /&gt;asm("mov %0, fp" : "=r" (fp) : : "cc");&lt;br /&gt;&lt;span style="color: rgb(255, 0, 0);"&gt;*die = 3;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;return 0;&lt;br /&gt;&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;12.  이 함수의 call path는 ret_fast_syscall부터 시작되었으며 ret_fast_syscall의 entry point가 위치하는 주소는 0xc0023de0이다.&lt;br /&gt;sys_read 함수가 호출되었으며 이때 다음의 값들은 r6 = 00066178  r5 = 00002000  r4 = BED0AEB4 sys_read의 인수가 아니라 ret_fast_syscall에서 사용된 r5,r6,r7의 값이 sys_read 함수에서 값이 바뀌기 때문에 sys_read 의 entry에 저장되어 있는 값들이다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;13. fault를 일으킨 코드는 test module의 read_overflow 함수의 빨간 색 라인이다. 위의 backtrace &lt;span style="color: rgb(0, 102, 0);"&gt;초록색&lt;/span&gt; 라인은 fault를 일으킨 코드를 ()로 둘러싸고 있고 그 이전 코드들을 4개 더 보여주고 있다.&lt;br /&gt;다음 backtrace 정보를 보여주고 있다. fault를 일으킨  함수는 read_overflow이며 fault를 일으킨 함수의 가상 주소는 0xbf000088이다. (이는 모듈이기 때문에 그 쪽 주소에 매핑된 것이다.)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;저장하는 코드는 아래의 표와 같다. &lt;span style="color: rgb(255, 0, 0);"&gt;주의해야 할 것이 이 값들이 마치 함수의 인수라고 착각하는 것이다. &lt;/span&gt;&lt;br /&gt;나머지 함수들도 마찬가지로 해석하면 된다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table id="a88:" class="zeroBorder" width="100%" border="0" cellpadding="3" cellspacing="0"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;127033 c0080b5c &lt;sys_read&gt;:&lt;br /&gt;127034 c0080b5c: e1a0c00d  mov ip, sp&lt;br /&gt;127035 c0080b60: e92dd870  stmdb sp!, {&lt;span style="color: rgb(204, 0, 0);"&gt;r4, r5, r6&lt;/span&gt;, fp, ip, lr, pc}&lt;br /&gt;&lt;/sys_read&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;br /&gt;14.  Control: 5317F 이것은 ARM processor의 control register 정보이다. 이곳에는 MMU, cache등과 관련된 현제 세팅 정보가 들어가 있다.&lt;br /&gt;&lt;br /&gt;15.   Table: 11C58000 은 Translation Table Base Register의 정보이다.&lt;br /&gt;Translation table base 0 UNP/SBZ RGN P S C 값들이 들어가 있다.&lt;br /&gt;&lt;br /&gt;16 DAC: 00000015은 Domain Access Control Register이다.&lt;br /&gt;&lt;br /&gt;D15 D14 D13 D12 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0&lt;br /&gt;&lt;br /&gt;17.  Tip&lt;br /&gt;&lt;br /&gt;PC에 저장되어 있는 주소가 현재 fault를 일으킨 명령이다. 그럼 그 명령은 C 소스의 어느 line에 해당할까?&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;addr2line 0xc30210c0 -e vmlinux -f&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5885352233728868155?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5885352233728868155/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5885352233728868155&amp;isPopup=true' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5885352233728868155'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5885352233728868155'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/oops-analysis-in-arm.html' title='Oops analysis in ARM'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6191586883888006508</id><published>2009-03-01T20:30:00.006+09:00</published><updated>2009-03-01T22:50:47.611+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[RFC PATCH 00/19] Cleanup and optimise the page allocator V2</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/2/24/81"&gt;http://lkml.org/lkml/2009/2/24/81&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;오랜만의 출사다. &lt;br /&gt;어쩐지 Mel이 한동안 조용하다 했었다. &lt;br /&gt;그동안 그가 했었던 일은 page allocator의 성능개선이다. &lt;br /&gt;문제는 그 동안의 page allocator에 여러 patch들이 들어가면서 page allocator가 비정상적으로 느려지기 시작한 것이다. 그래서 심지어는 SLUB과 같은 경우는 page allocator를 회피하기 위하여 tricky한 방법까지 사용하고 있는 상황이다. &lt;br /&gt;&lt;br /&gt;비록 x86_64 기준으로 kernel의 text size가 180 byte 증가하긴 하였지만(text size가 증가한 것은 몇몇 core page allocator function들을 inline했기 때문이다), page zeroing을 제외하고 allocation cost는 25%, free cost는 12%가 향상되었다. Page zeroing을 제외하고의 대부분의 overhead는 counters, debugging check, interrupt disable등에서 기인하였다. &lt;br /&gt;&lt;br /&gt;Mel은 이러한 부분들을 줄이기 위해 무려 19개의 패치를 던졌다. 사실 v1에서는 20개였다. &lt;br /&gt;마지막 패치는 hot/code page를 없애는 패치였는데, 없애기 전, 더 확실한 검증이 필요하여 현재는 drop된 상태다. &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;1. 전체적으로 반복적인 일들의 수를 줄였으며, &lt;br /&gt;2. anti-fragmentation으로 인해 allocator fast path에서 수행되던 list search를 migraion 별 per_cpu_pages로 해결하였으며, &lt;br /&gt;3. page free마다 두번씩 호출되는 get_pageblock_migratetype을 한번으로 줄이고, &lt;br /&gt;4. free_page_mlock에서의 irq_disable overhead를 smart하게 delay시켜 해결하였다. &lt;br /&gt;5. alloaction fast path에서 사용되는 gfp_zone에서 수행되는 많은 branch를 해결하기 위해 lookup table을 사용한다. &lt;br /&gt;&lt;br /&gt;이밖에도 allocation의 fast path와 slow path에 대한 code를 clean up하였으며 여러 stupid sanity check들도 없앴다. 하지만 아직까지 TODO가 몇몇 남아 있다. &lt;br /&gt;v3를 기대해보자.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6191586883888006508?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6191586883888006508/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6191586883888006508&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6191586883888006508'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6191586883888006508'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/03/rfc-patch-0019-cleanup-and-optimise.html' title='[RFC PATCH 00/19] Cleanup and optimise the page allocator V2'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6870796235556127983</id><published>2009-02-17T23:42:00.004+09:00</published><updated>2009-02-18T00:11:02.577+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[patch] vmscan: initialize sc.order in indirect shrink_list() users</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/2/10/231"&gt;http://lkml.org/lkml/2009/2/10/231&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Hannes의 패치이다. &lt;br /&gt;얼마전 Hannes는 offline mail을 통해서 barrios에게 유익한 정보를 알려주었다. &lt;br /&gt;이는 다음 기회에 소개하기로 하고, 지금은 이 패치의 내용에 대해 살펴보자. &lt;br /&gt;&lt;br /&gt;Hannes가 패치한 내용은 memory 회수 루틴 중 2곳에서 현재 메모리 requestor의 order가 반영되지 않았다는 것이다. 첫번째 장손는, 명시적으로 0을 지정할 필요가 없다는 것을 얼마전 Andrew가 친절히 설명해 주었었다. &lt;br /&gt;이번 issue는 두번째인 zone_reclaim 함수에서의 order값 지정의 생략이다. &lt;br /&gt;&lt;br /&gt;zone_reclaim 함수의 목적은 page를 할당하기 전, early reclaim을 하는 것이다. early reclaim의 대상은&lt;br /&gt;slab 페이지들과 unmapped file backed page들이다. 즉, read와 같은 system call을 통해서 읽혀진 페이지나, mapped file backed page들 중에, 현재는 unmapped되어 있는 페이지들이다. &lt;br /&gt;&lt;br /&gt;이 함수에서 order를 requestor의 order로 지정하지 않은 것이 문제의 시작이다. &lt;br /&gt;하지만 이 쓰레드의 Hannes와 Mel의 대화 속에는 약간의 오해가 있다. &lt;br /&gt;&lt;br /&gt;먼저, Hannes가 order를 의도적으로 0으로 지정하지 않았다고 생각하는 이유는 다음과 같다. &lt;br /&gt;&lt;br /&gt;Page allocator는 page를 할당하려고 할 때 몇 단계를 거치며 할당자에 pressure를 가한다. &lt;br /&gt;그 pressure는 다음의 flag들로 지정된다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;#define ALLOC_NO_WATERMARKS     0x01 /* don't check watermarks at all */&lt;br /&gt;#define ALLOC_WMARK_MIN         0x02 /* use pages_min watermark */&lt;br /&gt;#define ALLOC_WMARK_LOW         0x04 /* use pages_low watermark */&lt;br /&gt;#define ALLOC_WMARK_HIGH        0x08 /* use pages_high watermark */&lt;br /&gt;#define ALLOC_HARDER            0x10 /* try to alloc harder */&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;NO_WATERMARK 쪽으로 갈 수록 memory pressure가 심한 것이다. &lt;br /&gt;Page allocator의 첫번째 try는 ALLOC_WMARK_LOW를 사용하게 된다. Hannes가 생각한 것은&lt;br /&gt;WMARK_LOW에서 order를 지정하게 되면, 현재 memory pressure가 별로 없는 상태에서 결국 lumpy reclaim을&lt;br /&gt;하게 되어, 불필요하게 working set page들이 evict되어 버린다는 것이다. 그래서 의도적으로 order를 지정하지 않았다고 생각한다. &lt;br /&gt;&lt;br /&gt;이에 대해, Mel은 분명히 잘못된 것이라고 지적하고 있다. 즉 Hannes의 패치가 맞다는 것이다. &lt;br /&gt;그것으로 인해 어떤 차이가 생길지는 알기 어렵지만, zone_reclaim의 semantics상 order를 지정하는 것이 make sense하다는 것이다. 또한 Mel은 Hannes가 걱정한 working set page의 evict에 대해서 high order reclaim에 대한 어쩔수 없는 cost라고 말하고 있다. &lt;br /&gt;&lt;br /&gt;마지막 쓰레드의 Hannes와 Mel의 대화를 다시 보면, Mel은 Hannes의 말을 여전히 오해하고 있다. Hannes가 의도한 것은 low watermark에서 굳이 lumpy reclaim까지는 하지 않아도 upcoming allocation은 성공할 것이기 때문에 그렇게 했을 거라는 말이고, Mel은 그 말을 오해하고, 이렇게 언급하며 쓰레드를 끝낸다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;I think I get you now. You are saying that reclaiming order-0 pages increases&lt;br /&gt;the free count so we might get over the watermarks and the allocation would&lt;br /&gt;succeed. Thing is, watermarks calculated in zone_watermark_ok() take order&lt;br /&gt;as a parameter and has this in it.&lt;br /&gt;&lt;br /&gt;        for (o = 0; o &lt; order; o++) {&lt;br /&gt;                /* At the next order, this order's pages become * unavailable */&lt;br /&gt;                free_pages -= z-&gt;free_area[o].nr_free &lt;&lt; o;&lt;br /&gt;So, to reach the low watermarks for a high-order allocation, we still&lt;br /&gt;need lumpy reclaim.&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;즉, Mel은 "order-0 page를 reclaim하는 것이 전체 free page의 수를 증가시킬 것이며 이는 watermark 이상이 될수 있기 때문에 allocation이 성공할 것이다" 라고 Hannes가 말하고 있다고 생각한다. 하지만 앞서 언급한 바와 같이 Hannes의 의도는 그렇지는 않다. Anyway, Mel로부터 배울 것이 있다. order-0 page를 아무리 reclaim하더라도 결국 zone_watermark_ok는 위와 같이 계산하기 때문에 requestor의 order를 만족시킬 수는 없게 된다는 것이다. 결국 allocation이 성공할 수 없다는 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6870796235556127983?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6870796235556127983/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6870796235556127983&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6870796235556127983'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6870796235556127983'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/02/patch-vmscan-initialize-scorder-in.html' title='[patch] vmscan: initialize sc.order in indirect shrink_list() users'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8438840459243929591</id><published>2009-02-14T19:18:00.004+09:00</published><updated>2009-02-15T15:57:15.837+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Taming the OOM killer</title><content type='html'>&lt;a href="http://lwn.net/Articles/317814/"&gt;http://lwn.net/Articles/317814/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;OOM killer도 역시 embedded에서 hot issue 중의 하나이다. &lt;br /&gt;현재 Linux system의 OOM killer의 가장 큰 문제는 유연성의 부재이다. &lt;br /&gt;&lt;br /&gt;Linux kernel은 Out of Memory 상황이 오면 몇가지 heuristic을 사용하여 비교적 시스템에 해가 적게가며, 많은 메모리를 반환할 수 있는 프로세스를 kill하게 된다. 하지만 그 결정은 kernel의 생각이지, 시스템을 운영하는 admin이나 사용하는 user의 의견이 반영된 결정은 아니다. &lt;br /&gt;&lt;br /&gt;그렇게 까지 얘기하면 너무 심한가? &lt;br /&gt;사실, User들도 커널의 결정을 거들수는 있다. 그것이 /proc/pid/oom_adj란 knob이다.&lt;br /&gt;이 값은 커널의 여러 heuristic과 같이 각 프로세스의 oom_score의 값을 결정하는 데 기여한다. 커널은 결국 가장 큰 oom_score를 가진 프로세를 kill하게 되므로 사용자의 의견이 어느 정도 반영이 될 수는 있다. &lt;br /&gt;&lt;br /&gt;이러한 설비들이 있긴 하지만, 시스템을 admin하는 입장에서 그러한 설비만으로 OOM policy를 구현하기가 그리 만만치가 않다. 생각을 해보아라. 그러한 설비만으로 시스템에 생성되는 모든 프로세스들의 oom_adj를 runtime에 조절하는 것이 과연 얼마나 수월할까? 여러 사람들의 서버로 사용되는 server computer를 생각해보자. 그 안에서 어떤 user가, 어떤 time에, 어떤 job을 어떤 order로 얼마나 많은 memory를 필요로 하며 실행될지...&lt;br /&gt;&lt;br /&gt;그러므로 효율적인 OOM policy를 구현하기 위해서는 그 이상의 유연한 설비가 보다 OOM policy를 결정하는데 도움을 줄 것이다. &lt;br /&gt;&lt;br /&gt;얼마전 LKML에서는 Alan Cox의 제안에 의해  Nikanth Karthikesan가 cgroup controller를 base로 oom_killer controller를 구현하였었다. cgroup을 사용하였기 때문에 기존보다는 OOM priority별 task들을 grouping하기가 수월해졌다. 하지만 이 approach는 CPU set을 고려하지 않았다. &lt;br /&gt;CPU set A, B가 있다고 가정하자. CPU set A의 한 프로세스가 더 높은 oom.priority를 가지고 있을 경우, CPU set B가 OOM 상황을 만나게 되더라도 결국, CPU set A의 그 프로세스가 죽게 되는 것이다. 여러 토의 끝에, 결국 OOM 상황을 user space에 다루자는 얘기가 나왔다. 커널은 user space로 notify만 해주고 application들이 각자 자신의 cache를 drop한다거나 해서 OOM 상황에 대처하자는 것이다. Application들의 action이 충분한 free memory를 확보하는데 실패하였을 경우에만 커널이 마지막으로 기존의 OOM killer policy를 사용한다는 것이다. &lt;br /&gt;&lt;br /&gt;2008년 초 Kosaki-san이 구현했던 mem_notify가 그러한 policy를 구현하기 위한 첫 발걸음이었다. 하지만 이 패치는 현재 mainline에 반영되지 못했다. 그 이유는 여러 이유가 있지만 그 중에서도 가장 큰 것은 2.6.28에서 memory reclaiming이 크게 변경되었기 때문이다. 그 패치의 notify 시점은 커널의 memory reclaim 루틴과 굉장히 밀접하게 관련되어 있었기 때문에 memory reclaiming이 많이 변하게 되면서 mem_notify가 동작할 수 없는 환경이 되버린 것이다. Memory reclaiming을 같이 작업한 Rik과 Kosaki 그리고 약간의 도움을 준 barrios는 이 상황에 대해서 잘 알고 있으며, barrios는 mem_notify 패치의 마지막 메일 또한 기억하고 있다. &lt;br /&gt;&lt;br /&gt;마지막 토론에서의 문제는 실제 mem_notify가 필요할 때 notify를 해주지 못한다는 것이다. 즉, user가 notify를 받은 시점은 user가 어떤 action을 취하기에 늦어버렸다는 것이다. 그것은 현재 linux kernel의 문제이기도 하며, android가 별도의 low memory killer를 구현한 이유이기도 하다. 하지만 지금도 mem_notify의 design과 goal들은 여전히 유효하다.&lt;br /&gt;&lt;br /&gt;한동안 Android의 Low memory killer가 staging tree에 들어간 것에 대해서 여로 토의가 있었다(&lt;a href="http://lkml.org/lkml/2009/1/13/558"&gt;http://lkml.org/lkml/2009/1/13/558&lt;/a&gt;). barrios 또한 staging tree에 반영되었던 low memory killer의 소스를 보았지만 사실 너무 specific하게 구현되어 있어 질타를 받기 딱 좋은 코드였다. OOM issue는 embedded뿐만이 아닌 server에서도 필요한 이슈이다. 하지만 android 팀의 코드는 embedded 중에서도 자신들의 android 플랫폼만을 위한 specific한 코드를 구현하였고, Greg은 그것을 stating tree에 반영한 것이다. Staging tree의 특성상 앞으로 더욱 발전시키면 되지, staging tree에 들어가질 못할 정도는 아니었음에도 불구하고, barrios의 생각으론 다국적을 가진 사람들이 토의하다보니 영어를 약간 잘못 해석하여 분쟁이 일어나 결국 code를 다시 revert하라는 말까지 나올 정도로 좀 소란스러웠었던 issue이다. &lt;br /&gt;&lt;br /&gt;커널 트리에는 low_memory killer만 있고, 그 신호를 어떻게 user에서 처리하는지 잘 몰랐는데 LWN에 쉽게 잘 설명이 되어 있다. 첫번째 threshold에서는 background process들이 자신들의 state를 save하고, 점점 memory pressure가 심해지면 backgroud process 중 state를 save한 critical하지 않은 프로세스들을 kill하고, 마지막으론 foreground process들마저도 kill한다는 것이다. Android 팀이 이러한 설비가 필요했던 것 또한, 현재 linux kernel의 OOM killer의 반응은 너무 늦으며(Android팀은 보다 이른 신호가 필요하였다. 그래서 사전에 application에서 할 수 있는 일을 하려고 했던 것이다) 또한 그리 똑똑하지 못하다는 것을 반증하고 있다. &lt;br /&gt;&lt;br /&gt;지금이다. Linux kernel의 OOM killer구조가 재설계되야 할 때는!!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8438840459243929591?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8438840459243929591/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8438840459243929591&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8438840459243929591'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8438840459243929591'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/02/taming-oom-killer.html' title='Taming the OOM killer'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-708589281865172270</id><published>2009-02-08T13:37:00.005+09:00</published><updated>2009-02-08T14:19:51.578+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>lru_add_drain_all problem</title><content type='html'>&lt;a href="http://lkml.org/lkml/2008/10/21/205"&gt;http://lkml.org/lkml/2008/10/21/205&lt;/a&gt;&lt;br /&gt;&lt;a href="http://lkml.org/lkml/2008/11/5/347"&gt;http://lkml.org/lkml/2008/11/5/347&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;또 다시 circulary dependency problem이다. &lt;br /&gt;문제의 원인은 lru_add_drain_all이 mmap_sem을 hold한 채로 worqueue를 사용하기 때문이다. 이 문제는 작년 10월 처음으로 보고 되었고, 쓰레드를 읽어 보면 알수 있는 바와 같이,&lt;br /&gt;문제를 해결하려는 시도는 2가지의 방향으로 시도 되었다. &lt;br /&gt;&lt;br /&gt;첫번째는 keventd가 아닌 별도의 workqueue를 만들어 schedule_on_each_cpu를 keventd가 아닌 별도의 workqueue안에서 호출하자는 것이다. &lt;br /&gt;&lt;br /&gt;이렇게 한 이유는, 이미 많은 드라이버들이 keventd를 이용한 workqueue를 사용하고 있는 상황에서 그 driver들이 어떤 lock을 hold한채로 workqueue 사용하고 있는지를 알 수 없기 때문에, 비교적 적게 사용되는 schedule_on_each_cpu로 하여금 별도의 workqueue를 사용하자는 주장이다. &lt;br /&gt;&lt;br /&gt;하지만 이 방법에 대해서는 Peter가 별로 달가워하지 않았다. &lt;br /&gt;&lt;br /&gt;그 이유는 이미 커널에는 수많은 커널 쓰레드들이 있다는 것이다. 그 상황을 더욱 악화시키지 말자는 것이다. barrios의 생각도 마찬가지이다. 비록 지금은 schedule_on_each_cpu를 호출하는 것이 pagevec을 drain하는 lru_add_drain_all 함수 하나이지만, 그러한 함수들은 얼마든지 더 생길 수 있고 그럴때마다 새로운 workqueue를 만드는 것은 시스템의 커널 쓰레드들의 수를 증가시키게 된다.&lt;br /&gt;&lt;br /&gt;하지만 이 상황은 지금은 더 나아질 수도 있을 것 같다. 왜냐하면 이전에 소개했던 기사 처럼 Arjan의 An asynchronous function call infrastructure가 mainline에 merge될 것이기 때문이다. 이 설비를 이용하게 되면 worker function을 새로운 쓰레드에서 실행하게 할 수 있으며, 해당 쓰레드는 필요 없을 때 종료될 수 있기 때문이다. 하지만 생성된 쓰레드를 재활용하는 Arjan의 패치에 약간의 개선이 필요하다. 모든 함수가 새로운 쓰레드에서 호출되며, 그 쓰레드는 다른 함수를 호출하지 않고 종료되게 끔 되어야 ciculary locking problem이 발생하지 않기 때문이다. &lt;br /&gt;이와 함께 이 패치 또한 고려되어야 한다. 이는 비동기 함수 호출이 아닌 커널 쓰레드 자체에 관하여 비동기적으로 생성하자는 패치이다. 하지만 Arjan의 패치와 역할이 많이 겹치고 있다. &lt;a href="http://lkml.org/lkml/2009/1/27/410"&gt;http://lkml.org/lkml/2009/1/27/410&lt;/a&gt;)&lt;br /&gt;&lt;br /&gt;두번째는 lru_add_drain_all을 호출하는 path에서 mmap_sem를 hold하지 않은 채로 호출하자는 것이다. Christoph는 migration중 mmap_sem을 hold하는 문제의 패치를 만들어 제출하였고, Kosaki 또한 munlockpath에서 lru_add_drain_all을 호출하지 않아도 시스템의 mlocked page memory leak이 발생하지 않는다는 문제에 agree하였고, 결국 다시 패치를 만들어 제출하였다. &lt;br /&gt;&lt;br /&gt;barrios가 이 문제를 언급하는 이유는 작년 11월에 반영된 kosaki의 패치가 아직 반영되지 않았기 때문이다. 그러므로 barrios는 28-rc2-mm1의 테스트 중 그러한 circulary dependency locking report를 받았기 때문이다. &lt;br /&gt;&lt;br /&gt;이 문제에 대해서 차주 kosaki와 얘기를 좀 더 해볼 필요가 있으며, 필요하다면 Arjan의 패치에 새로운 기능을 넣어 해결 할 수도 있을 것 같다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-708589281865172270?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/708589281865172270/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=708589281865172270&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/708589281865172270'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/708589281865172270'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/02/lruadddrainall-problem.html' title='lru_add_drain_all problem'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-1487702841783561142</id><published>2009-02-01T12:27:00.006+09:00</published><updated>2009-02-01T13:29:12.639+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>An asynchronous function call infrastructure</title><content type='html'>&lt;a href="http://lwn.net/Articles/314808/"&gt;http://lwn.net/Articles/314808/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;2.6.29-rc3가 몇일전 release되었지만 이제서야 2.6.29-rc1에 들어간 기능을 review한다. &lt;br /&gt;그 동안 some bug를 digging 하느라 정신이 없었다. 사실 아직도 debugging 중이다. &lt;br /&gt;&lt;br /&gt;kernel compile을 하는 동안 LWN 기사를 하나 review한다. &lt;br /&gt;&lt;br /&gt;Intel의 Arjan이 시도하는 fastboot project의 일부이다. &lt;br /&gt;Fastboot은 많은 사람들이 관심을 가지고 있는 주제중의 하나이며, 그 동안 많은 시도들이 있었다.&lt;br /&gt;특히 embedded guy들이 많은 관심을 가지고 있던 주제중의 하나이다. &lt;br /&gt;하지만 Arjan은 embedded가 아닌 desktop을 위해 Fastboot을 진행중이다. 물론 몇몇 기술들은&lt;br /&gt;embedded에도 유용할 것이다. 하지만 오늘 소개하는 이 patch는 embedded와는 별로 관계가 없다. &lt;br /&gt;&lt;br /&gt;사실, device probing을 parallel하게 하자는 시도는 예전부터 있어왔었다. 하지만 device ordering,&lt;br /&gt;concurrent access등과 같은 문제들로 인하여 system stability의 문제가 있어 general하게 &lt;br /&gt;적용되지 못해왔다. &lt;br /&gt;&lt;br /&gt;이 문제를 Arjan은 모든 device들을 한번에 해결하려는 시도보다는 libata subsystem과 SCSI로 국한하여&lt;br /&gt;parallel probing을 시도하였으며(그래서 barrios는 embedded와는 현재로선 거리가 멀다고 얘기한 것이다. 하지만 이 비동기 framework 자체는 fastboot뿐만이 아니라 여러면에서 도움이 될 것으로 생각된다.), API를 잘 추상화하여 나머지 subsystem들은 아무 영향을 받지 않도록 설계하였다. &lt;br /&gt;&lt;br /&gt;실제 동작 원리는 복잡하지 않다. 비동기 함수를 관리하는 async_pending list와 async_running list를 두어, &lt;br /&gt;비동기 함수의 실행을 요청하는 async_schedule을 호춢하게 되면 callback function을 async_pending list에 넣고, 그 함수를 실행시키기 위해 async_manager_thread를 깨우게 된다. async_manager_thread는 새로운 async_thread를 생성하여 pending list에 있는 비동기 함수를 실행하게 된다. async_thread는 1초 async_pending list에 pending된 비동기 함수들이 없을 경우 스스로 소멸되게 된다. &lt;br /&gt;또한, 한꺼번에 많은 비동기 함수들의 요청이 들어올 경우, kernel thread는 갑자기 많아 질 수 있다. &lt;br /&gt;현재는 kernel thread를 MAX_THREAD(256)개로 제한하고 있다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;static async_cookie_t __async_schedule(async_func_ptr *ptr, void *data, struct list_head *running)&lt;br /&gt;{&lt;br /&gt;  struct async_entry *entry;&lt;br /&gt;  unsigned long flags;&lt;br /&gt;  async_cookie_t newcookie;&lt;br /&gt;  &lt;br /&gt;&lt;br /&gt;  /* allow irq-off callers */&lt;br /&gt;  entry = kzalloc(sizeof(struct async_entry), GFP_ATOMIC);&lt;br /&gt;&lt;br /&gt;  /*  &lt;br /&gt;   * If we're out of memory or if there's too much work&lt;br /&gt;   * pending already, we execute synchronously.&lt;br /&gt;   */&lt;br /&gt;  if (!async_enabled || !entry || atomic_read(&amp;entry_count) &gt; MAX_WORK) {&lt;br /&gt;    kfree(entry);&lt;br /&gt;    spin_lock_irqsave(&amp;async_lock, flags);&lt;br /&gt;    newcookie = next_cookie++;&lt;br /&gt;    spin_unlock_irqrestore(&amp;async_lock, flags);&lt;br /&gt;&lt;br /&gt;    /* low on memory.. run synchronously */&lt;br /&gt;    ptr(data, newcookie);&lt;br /&gt;    return newcookie;&lt;br /&gt;  }&lt;br /&gt;  entry-&gt;func = ptr;&lt;br /&gt;  entry-&gt;data = data;&lt;br /&gt;  entry-&gt;running = running;&lt;br /&gt;&lt;br /&gt;  spin_lock_irqsave(&amp;async_lock, flags);&lt;br /&gt;  newcookie = entry-&gt;cookie = next_cookie++;&lt;br /&gt;  list_add_tail(&amp;entry-&gt;list, &amp;async_pending);&lt;br /&gt;  atomic_inc(&amp;entry_count);&lt;br /&gt;  spin_unlock_irqrestore(&amp;async_lock, flags);&lt;br /&gt;  wake_up(&amp;async_new);&lt;br /&gt;  return newcookie;&lt;br /&gt;}&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;하지만 아직까지 이 patch는 많은 문제를 가지고 있는 것 같다. 2.6.29-rc1에 들어가자마자 많은 문제들이 보고되기 시작했으며, 현재 Arjan은 Linus에게 이 기능을 disable 시켜달라고 요청한 상태이다. &lt;br /&gt;&lt;br /&gt;이번주 LWN의 기사가 다시한번 이 주제를 다루고 있기 때문에, 몇일 뒤 무료로 기사를 볼 수 있게 될 경우, 이 문제가 어떻게 풀려나가고 있는지 다시한번 review를 하도록 하자.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-1487702841783561142?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/1487702841783561142/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=1487702841783561142&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1487702841783561142'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1487702841783561142'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/02/asynchronous-function-call.html' title='An asynchronous function call infrastructure'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2833069738651587587</id><published>2009-01-30T22:47:00.008+09:00</published><updated>2009-02-01T16:21:30.788+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Guitar'/><title type='text'>사슴농장의 추억</title><content type='html'>이 곡을 접한 것은 96년 이었다. &lt;br /&gt;정박으로 딱 떨어지는 이 곡은 러쎌의 연주가 일품이다. (러쎌의 연주가 동영상으로 있으면 좋았으련만...)&lt;br /&gt;&lt;br /&gt;이 곡을 떠올리면 한 선배의 사슴농장에서의 연주가 생각난다. 비가 부슬부슬 내리는 날 사슴 농장에서의 &lt;br /&gt;연주는 많은 사람들에게 어필할 수 밖에 없는 아름다운 연주였을 것이다. 게다가 그 선배의 연주 실력이야 이미 &lt;br /&gt;준 프로 수준이라고 해도 과언이 아닐 정도로 훌륭하였다. &lt;br /&gt;&lt;br /&gt;운지가 결코 쉽지 않다. 그래서 빠른 곡은 아니어서 오른손은 여유롭지만 왼손의 기민함을 요구한다. &lt;br /&gt;그 만큼 왼손의 유연함과 정확성을 기를 수 있는 곡이다. &lt;br /&gt;중간 중간 나오는 슬러와 하이 플랫의 포지션은 정말 정확하게 운지를 짚지 못하면 &lt;br /&gt;좋은 소리를 내지 못한다.&lt;br /&gt; &lt;br /&gt;barrios는 아직도 그 연습을 하고 있지만 뜻대로 되지 않는 운지 중 하나이다. &lt;br /&gt;&lt;br /&gt;정말 오랜만에 맥주를 한잔했다. 항상 술이 있으면 음악이 떠오르는 것처럼...&lt;br /&gt;기타가 치고 싶어진다. &lt;br /&gt;이 취기에 얼마나 앉아 연주할 수 있을지는 모르겠지만(아쉽게도 새로운 악보를 일터에 놓고 왔다. 이게 &lt;br /&gt;있었으면 나를 boost시켜줄 수 있었을 텐데) &lt;br /&gt;&lt;br /&gt;마음가는데로.... 연주하다 오늘 하루는 편안하게 잠들어야지&lt;br /&gt;정말이지, 클래식 기타의 소리는 너무 부드럽다 :)&lt;br /&gt;&lt;br /&gt;꼬랑지)&lt;br /&gt;&lt;br /&gt;러쎌을 흉내냈지만 프로의 수준은 아니다. 하지만 연주자 뒤의 background가 인상적이다. ^^;&lt;br /&gt;저건 madrigal 악보가 아닌데.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;object width="425" height="344"&gt;&lt;param name="movie" value="http://www.youtube.com/v/OiIByohPJ60&amp;hl=en&amp;fs=1"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/OiIByohPJ60&amp;hl=en&amp;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2833069738651587587?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2833069738651587587/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2833069738651587587&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2833069738651587587'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2833069738651587587'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/96.html' title='사슴농장의 추억'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2802300736526690159</id><published>2009-01-21T22:15:00.007+09:00</published><updated>2009-02-06T13:48:10.959+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[RESEND][PATCH] cpuset: fix possible deadlock in async_rebuild_sched_domains</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/1/19/564"&gt;http://lkml.org/lkml/2009/1/19/564&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이 버그는 lockdep를 사용하여 발견된 버그이다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;=======================================================&lt;br /&gt;[ INFO: possible circular locking dependency detected ]&lt;br /&gt;2.6.29-rc1-00224-ga652504 #111&lt;br /&gt;-------------------------------------------------------&lt;br /&gt;bash/2968 is trying to acquire lock:&lt;br /&gt;(events){--..}, at: [&lt;ffffffff8024c8cd&gt;] flush_work+0x24/0xd8&lt;br /&gt;but task is already holding lock:&lt;br /&gt;(cgroup_mutex){--..}, at: [&lt;ffffffff8026ad1e&gt;] cgroup_lock_live_group+0x12/0x29&lt;br /&gt;which lock already depends on the new lock.&lt;br /&gt;&lt;/ffffffff8026ad1e&gt;&lt;/ffffffff8024c8cd&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;보는 것과 같이 circular locking deadlock 상황이 발생할 수 있음을 탐지하였다.&lt;br /&gt;그럼 살펴보자. 어떻게 그런 deadlock이 발생할 수 있을지..&lt;br /&gt;먼저, cgroup_mutex를 소유하고 있는 task가 있다고 말해주고  있다.&lt;br /&gt;이 mutex는 cgroup_lock_live_group에서 소유하였다. 코드를 살펴보자.&lt;br /&gt;&lt;br /&gt;cgroup_tasks_write&lt;br /&gt;-&gt;cgroup_lock_live_group을 호출하여 cgrup_mutex를 소유한다.&lt;br /&gt; -&gt;attach_task_by_pid&lt;br /&gt;    -&gt;cpuset_attach&lt;br /&gt;         -&gt;do_migrate_pages&lt;br /&gt;              -&gt;migrate_prep&lt;br /&gt;                   -&gt;lru_add_drain_all&lt;br /&gt;                        -&gt;schedule_work_on&lt;br /&gt;                             -&gt;flush_work&lt;br /&gt;                                  -&gt;lock_map_acuire&lt;br /&gt;&lt;br /&gt;반면, async_rebuild_sched_domains에서 호출한 run_workqueue를 살펴보자.&lt;br /&gt;&lt;br /&gt;async_rebuild_sched_domains&lt;br /&gt;-&gt;schedule_work  (이것은 결국 eventd의 run_workqueue에 의해 실행되게 된다.)&lt;br /&gt;   -&gt;run_workqueue&lt;br /&gt;        -&gt;lock_map_acquire&lt;br /&gt;     -&gt;do_rebuild_sched_domains&lt;br /&gt;               -&gt;cgroup_lock&lt;br /&gt;                    -&gt;cgroup_mutex 소유&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;위에서 보는 것과 같이 workqueue와 cgroup_mutex에 대해 circular lock이 형성된다.&lt;br /&gt;이 얘기는 flush_work에 의해 완료되야 하는 worker function이 do_rebuild_sched_domains을 실행시킨 run_workqueue에 의해 lock되며 do_rebuild_sched_domains는 cgroup_mutex를 소유하기 위해 cgroup_tasks_write와 race하게 된다.&lt;br /&gt;&lt;br /&gt;lockdep는 이와 같이 여러 deadlock 상황을 발견하기 위해 만들어진 설비이다.&lt;br /&gt;하지만 false positive를 만들어내는 상황도 있기 때문에 무조건 lockdep를 믿는 것도 좋지 않다.&lt;br /&gt;많은 분들이 lockdep가 어떻게 동작하는지, 어떻게 사용하는지, 보고된 내용을 어떻게 해석해야 하는지 잘 알지 못하는 것 같다. &lt;br /&gt;barrios는 조만간 lockdep에 대한 내용을 한번 다룰 예정이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2802300736526690159?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2802300736526690159/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2802300736526690159&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2802300736526690159'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2802300736526690159'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/resendpatch-cpuset-fix-possible.html' title='[RESEND][PATCH] cpuset: fix possible deadlock in async_rebuild_sched_domains'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5188247958939371080</id><published>2009-01-18T19:25:00.003+09:00</published><updated>2009-01-19T08:47:43.858+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH] Avoid lost wakeups in lock_page_killable()</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/1/17/195"&gt;http://lkml.org/lkml/2009/1/17/195&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이 패치는 lock_page_killable 함수의 버그를 패치하는 함수이다. &lt;br /&gt;lock_page_killable 함수는 Matthew Wilcox에 의해 추가된 함수이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://lkml.org/lkml/2007/10/18/424"&gt;http://lkml.org/lkml/2007/10/18/424&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;NFS-mounted file system의 파일에 대하여 'cat' 명령어시 중간에 명령을 멈출 수가 없었던 문제를 해결하기 위하여,&lt;br /&gt;page lock에 대하여 task들을 TASK_KILLABLE 상태로 signal에 반응하며 lock을 대기할 수 있게 해준 패치이다.&lt;br /&gt;&lt;br /&gt;하지만 이 패치는 문제를 가지고 있다. &lt;br /&gt;다음과 같은 경우를 생각해보자. &lt;br /&gt;&lt;br /&gt;1) Task A가 lock을 소유하고 있다.&lt;br /&gt;2) Task B와 Task C가 lock을 대기하고 있다.&lt;br /&gt;3) Task A가 lock을 unlock하고 Task B를 깨운다.&lt;br /&gt;4) 이때 마침 administator는 Task B를 kill한다.&lt;br /&gt;5) 깨어난 Task B는 lock을 소유하지 않고, kill된다.&lt;br /&gt;6) Task C는 아무도 잡지 않고 있는 lock을 누군가가 unlock하길 기다리며, 끝까지 기다린다!!!&lt;br /&gt;&lt;br /&gt;이 버그가 여태까지 보고되지 않았던 이유는, 누구나 참을성을 가지고 ctrl + C를 하면 hang한 프로세스들을 kill할 수 있기 때문에 대부분 application의 버그라고 생각한 것 같다. &lt;br /&gt;&lt;br /&gt;이 문제는 oracle의 Chris Mason(현재 btrfs의 maintainer)에 의해 패치되었다. 하지만 __lock_page_killable을 패치한 Chris의 아이디어 보다는, __wait_on_bit_lock을 패치한 Johannes Weiner의 아이디어가 더욱 make sense하다. Johannes는 다음과 같이 언급하고 있다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;__wait_on_bit_lock() employs exclusive waiters, which means that every&lt;br /&gt;contender has to make sure to wake up the next one in the queue after&lt;br /&gt;releasing the lock.&lt;br /&gt;&lt;br /&gt;If the passed in action() returns a non-zero value, the lock is not&lt;br /&gt;taken but the next waiter is not woken up either, leading to endless&lt;br /&gt;waiting on an unlocked lock.&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;즉,__wait_on_bit_lock이 next wake up을 보장해 주어야 한다는 것이다. 그러므로 이것은 &lt;br /&gt;상위 layer에서 풀 문제가 아니라 __wait_on_bit_lock에서 푸는 것이 더욱 좋다는 것이다. &lt;br /&gt;또한 Peter Zijlistra는 Chris의 패치에 대해서 spurious wakeup이 우려되긴 하나, &lt;br /&gt;영원히 wake up을 읽어버리는 것 보다는 좋다고 말하고 있다. spurious wakeup문제는 Johannes의 패치에서도&lt;br /&gt;여전히 나타날 수 있다. 단지 가능성을 약간 줄였을 뿐이다. (test_bit operation을 중간에 추가함으로써.. barrios는 이 부분의 패치에 대해서는 별로 agree하지 않는다. 단지 가능성을 줄일 뿐이지, spurious 문제는 여전히&lt;br /&gt;발생할 수 있기 때문이다. 쓸데 없이 test_bit operation을 낭비하는 것이 될 것 같다.)&lt;br /&gt;아직 Johannes는 패치는 peter에 의해 ack되진 않았다. &lt;br /&gt;과연 이 패치가 spurious wakeup을 피할 수 있게 될지 좀더 주목해 볼 필요가 있다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5188247958939371080?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5188247958939371080/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5188247958939371080&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5188247958939371080'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5188247958939371080'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/patch-avoid-lost-wakeups-in.html' title='[PATCH] Avoid lost wakeups in lock_page_killable()'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4108190141912214992</id><published>2009-01-15T18:56:00.009+09:00</published><updated>2009-01-20T08:06:30.011+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>flush_dcache_page와 kmap_atomic</title><content type='html'>왜 file system code들 중 kmap_atomic과 flush_dcache_page가 있을까?&lt;br /&gt;아는 분의 도움으로 이 문제에 대해서 생각해 볼 기회가 생겼다.&lt;br /&gt;&lt;br /&gt;먼저, flush_dcache_page 함수의 용도를 먼저 알아야 한다. &lt;br /&gt;David Miller가 작성한 문서에는 다음과 같이 되어 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;  void flush_dcache_page(struct page *page)&lt;br /&gt;&lt;br /&gt;    Any time the kernel writes to a page cache page, _OR_&lt;br /&gt;    the kernel is about to read from a page cache page and&lt;br /&gt;    user space shared/writable mappings of this page potentially&lt;br /&gt;    exist, this routine is called.&lt;br /&gt;&lt;br /&gt;    NOTE: This routine need only be called for page cache pages&lt;br /&gt;          which can potentially ever be mapped into the address&lt;br /&gt;          space of a user process.  So for example, VFS layer code&lt;br /&gt;          handling vfs symlinks in the page cache need not call&lt;br /&gt;          this interface at all.&lt;br /&gt;&lt;br /&gt;    The phrase "kernel writes to a page cache page" means,&lt;br /&gt;    specifically, that the kernel executes store instructions&lt;br /&gt;    that dirty data in that page at the page-&gt;virtual mapping&lt;br /&gt;    of that page.  It is important to flush here to handle&lt;br /&gt;    D-cache aliasing, to make sure these kernel stores are&lt;br /&gt;    visible to user space mappings of that page.&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;즉, 커널이 page cache page에 write를 하는 경우, 또는 user space로 shared/writable로 매핑된 페이지를 읽으려고 하는 경우, 이 함수가 호출된다는 것이다. 또한 이 함수는 user-space로 매핑된 페이지 캐시의 경우에만 호출된다는 것이다. D-cache aliasing 문제를 막기 위함이다. ( cache aliasing 문제에 대해서는 James Bottomley가 작성한 다음 페이지에 잘 설명되있다. &lt;a href="http://www.linuxjournal.com/article/7105"&gt;http://www.linuxjournal.com/article/7105&lt;/a&gt;)&lt;br /&gt;&lt;br /&gt;D-cache aliasing 문제란, PIPT(Physical Index Physical Tag)가 아닌 VIVT(Virtual Index Virtual Tag) 또는 VIPT(Virtual Index Virtu Tag) cache 구조에서 발생하는 문제이다. cache의 서로 다른 line에 다른 virtual address로 인하여 같은 physical ram의 데이터가 들어가 있는 경우이다. D-cache aliasing이 발생하는 경우는, user application이 mmap 시스템 콜을 통하여 하나의 파일을 자신의 주소 공간 여러 virtual address에 매핑하는 경우, 또는 서로 다른 프로세스가 하나의 파일에 대해서 writable/shared 상태로 mapping을 서로 다른 virtual address를 통해서 같은 영역을 접근하는 경우 발생할 수 있다. &lt;br /&gt;&lt;br /&gt;그럼 위의 flush_dcache_page 함수의 호출 경로 두 곳을 생각해보자. &lt;br /&gt;&lt;br /&gt;1. page cache의 page 대하여 write operation을 호출하는 경우&lt;br /&gt;&lt;br /&gt;이 경우는 당연히 flush_dcache_page를 호출해야 한다 왜냐하면 해당 page cache의 페이지는 다른 프로세스 또는 같은 프로세스의 다른 virtual address에 매핑되어 있을 수 있다. 그러므로 해당 page에 대한 write와 동시에 해당 page를 매핑하고 있는 모든 cache들을 flush해주어야 한다. 그렇지않은 경우 해당 page를 접근하는 다른 프로세스나 같은 프로세스의 다른 쓰레드는 stale한 데이터를 보게 될 수 있다.  &lt;br /&gt;&lt;br /&gt;2. shared/writable한 영역의 페이지를 커널이 읽을 때,  &lt;br /&gt;&lt;br /&gt;커널이 읽고 있는 페이지가 다른 프로세서에서 수행되고 있는 어플리케이션에 의해 write가 될 수 있기 때문에, 읽기 전 flush_dcache_page를 호출하여 cache를 먼저 flush 시킨 후 읽어야 한다.&lt;br /&gt;&lt;br /&gt;Cache aliasing문제가 발생하는 것은 user application의 virtual address들로 인하여 하나의 물리 페이지가 여러 다른 virtual address space에 매핑된 경우에사 발생한다는 것을 유념하자. &lt;br /&gt;&lt;br /&gt;자 그럼 squashfs_readpage를 이용해서 살펴보자. &lt;br /&gt;&lt;br /&gt;다음과 같은 루틴이 있다. &lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;452   for (i = start_index; i &lt;= end_index &amp;&amp; bytes &gt; 0; i++,&lt;br /&gt;453       bytes -= PAGE_CACHE_SIZE, offset += PAGE_CACHE_SIZE) {&lt;br /&gt;454     struct page *push_page;&lt;br /&gt;455     int avail = sparse ? 0 : min_t(int, bytes, PAGE_CACHE_SIZE);&lt;br /&gt;456 &lt;br /&gt;457     TRACE("bytes %d, i %d, available_bytes %d\n", bytes, i, avail);&lt;br /&gt;458 &lt;br /&gt;459     push_page = (i == page-&gt;index) ? page :&lt;br /&gt;460       grab_cache_page_nowait(page-&gt;mapping, i);&lt;br /&gt;461 &lt;br /&gt;462     if (!push_page)&lt;br /&gt;463       continue;&lt;br /&gt;464 &lt;br /&gt;465     if (PageUptodate(push_page))&lt;br /&gt;466       goto skip_page;&lt;br /&gt;467 &lt;br /&gt;468     pageaddr = kmap_atomic(push_page, KM_USER0);&lt;br /&gt;469     squashfs_copy_data(pageaddr, buffer, offset, avail);&lt;br /&gt;470     memset(pageaddr + avail, 0, PAGE_CACHE_SIZE - avail);&lt;br /&gt;471     kunmap_atomic(pageaddr, KM_USER0);&lt;br /&gt;472     flush_dcache_page(push_page);&lt;br /&gt;473     SetPageUptodate(push_page);&lt;br /&gt;474 skip_page:&lt;br /&gt;475     unlock_page(push_page);&lt;br /&gt;476     if (i != page-&gt;index)&lt;br /&gt;477       page_cache_release(push_page);&lt;br /&gt;478   }&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;이 함수의 인수로 넘어온 page에 대해서 먼저, kmap_atomic을 실행하여 operation을 한후, flush_dcache_page를 호출하는 것을 볼 수 있다. page가 인수로 넘어온 페이지는 새로 할당된 페이지 이기 때문에 굳이 flush_dcache_page를 호출할 필요는 없지만, grab_cache_page_nowait를 통해 반환된 페이지는 page cache의 페이지일수도 있기 때문에  flush_dcache_page를 호출하는 것이다. 의심의 여지가 없다. flush_dcache_page의 문서 내용대로 page cache 페이지에 write를 했으니 flush_dcache_page를 호출하는 것이다.  &lt;br /&gt;&lt;br /&gt;다음, kmap_atomic을 왜 호출 했는지 살펴보자. &lt;br /&gt;그러기 위해선 kmap_atomic이 어떤 함수인지 먼저 알아야 한다. 이 함수는 커널에게 direct mapping되지 못한 메모리 공간에 커널이 접근하기 위해 필요한 함수이다. 대부분의 config설정 변경을 하지 않은 시스템에서는 커널은 1G의 메모리 주소를 갖는다. 그러므로 램의 1G 까지가 커널의 1G에 direct로 매핑될 수 있다고 생각할 수 있다. 하지만 그렇지는 않다. x86과 같은 경우 896M의 물리 램만이 direct mapping될 수 있다. 그 이유는 많은 서적들에서 얘기하고 있음으로 설명을 생략한다. 그럼 상위 1G 이상의 물리 램의 영역들은 어떻게 접근 할 것인가? 그것을 하기 위한 설비가 kmap_xxx 설비이다. atomic의 postfix가 붙은 것은 해당 매핑중 sleep되어서는 안되기 때문이다. &lt;br /&gt;&lt;br /&gt;커널이 접근할 수 있는 1G 중, 896M를 제외한 나머지 영역은 여러 용도로 나누어져 예약이 되어 있다. 그 중 한 영역이 kmap_을 하기 위한 영역이다. 즉, 1G 이상의 메모리 영역을 일시적으로 (896M &lt; x &lt; 1G )주소에 매핑시켜(정확한 값은 아니다. 정확한 값은 arch마다 틀리며 지금 그거까지 찾아보기는 귀찮다. 적당히 하고 넘어가자) opeartion을 수행하고 다른 사용자를 위해 매핑을 끊어 버리는 것이다. &lt;br /&gt;&lt;br /&gt;그렇다면 squashfs_readpage에 인수로 넘어온 page가 high memory의 page일 수 있다는 것인가? &lt;br /&gt;=&gt; 그렇다. &lt;br /&gt;&lt;br /&gt;그렇다면 왜 high memory일 수 있을까? &lt;br /&gt;&lt;br /&gt;=&gt; 이것까지 생각해 봤다면 당신은 kernel newbie는 아니다.&lt;br /&gt;그 이유는 page cache page들은 커널에게 있어서 있어도 그만, 없어도 그만인 페이지이다. &lt;br /&gt;해당 페이지가 없다고 해서 시스템이 동작하는 데 문제가 있는 것은 아니다. 단순히 성능이 좀 떨어지겠지만.. 하지만 low memory(0~896M)의 메모리들은 커널의 동작에 있어 꼭 필요한 자료구조들과 데이터들을 관리하기 위해서 사용된다. 지금과 같이 데스크탑이 램 4G를 꼽는 경우를 생각해보면, 커널이 내부 수행을 위해 관리하는 자료구조들과 데이터들은 더욱 많은 low memory를 사용하게 된다. 그러므로 쓸데 없이 low memory를 낭비하는 것은 커널의 memory pressure를 높이는 꼴이 된다. 이는 시스템의 성능을 크게 저하시키게 된다. &lt;br /&gt;&lt;br /&gt;이런 이유로 page cache 페이지들은 가능하면 high memory에 할당을 하려고 하는 것이다. 그러면 어떻게 그것을 알 수 있을까? 그것을 알기 위해서는 squashfs_readpage에 인수로 넘어오는 page 인수가 어떻게 어디서 할당이 되었느냐를 알아야 한다. &lt;br /&gt;&lt;br /&gt;자, 찾아보자. &lt;br /&gt;&lt;br /&gt;아까 얘기했었다. filemap_fault를 통해 호출이 되었을 것이라고. &lt;br /&gt;아니나 다를까. 가보면 다음과 같은 code가 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;error = mapping-&gt;a_ops-&gt;readpage(file, page);&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;저 인수로 넘어가는 page는 과연 누가 할당했을까?&lt;br /&gt;그 페이지는 page_cache_read 함수 안에서 page_cache_alloc_cold를 통해 할당되었음을 알 수 있다. 이때 인수로 넘어가는 address_space와 그 함수안에 mapping_gfp_mask를 보면, 결국 address_space의 flags에 어떤 값이 들어가 있느냐에 따라 페이지 할당 위치가 결정된다. &lt;br /&gt;&lt;br /&gt;그러면 address_space의 flags에는 어떤 값이 들어가 있는지는 어떻게 아는가?&lt;br /&gt;page_cache_read 함수를 보면 address_space를 구하기 위해서 file-&gt;f_mapping을 구해오는 것을 볼 수 있다. 그러므로 file의 f_mapping이 언제 어떻게 설정되느냐를 찾아 봐야 한다. &lt;br /&gt;&lt;br /&gt;__dentry_open함수를 살펴보면, inode-&gt;i_mmaping 필드로 f-&gt;f_mapping을 지정하는 것을 볼 수 있다. 그러면 이번에는 inode-&gt;i_mapping 필드가 누가 언제 어떻게 지정하느냐를 또 찾아봐야 한다. 생각해보면 금방 알 수 있다. inode가 만들어질 때 하지 않겠는가!&lt;br /&gt;&lt;br /&gt;그렇다면 squshfs 파일 시스템에서 inode를 어떻게 만드는지 살펴보아야 한다. &lt;br /&gt;suqashfs_iget 함수를 살펴보니 알 수 있을 것 같다. iget_locked 함수를 통해서 해당 inode를 찾아보고 시스템에 없다면 get_new_inode_fast 함수를 통해 할당하는 것을 볼 수 있다. get_new_inode_fast 함수는 alloc_inode를 통해 inode를 할당하고 있다. &lt;br /&gt;alloc_inode 함수는 squshfs의 경우에는 kmem_cache_alloc을 통해서 할당받게 되며 inode_init_always 함수를 통해 초기화 하는 것을 알 수 있다. 짐작할 수 있다. 저 함수안에서 초기화 할 것이라고...&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;   mapping-&gt;flags = 0;&lt;br /&gt;   mapping_set_gfp_mask(mapping, GFP_HIGHUSER_MOVABLE);&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;위와 같이 초기화 하는 것을 알 수 있다. GFP_HIGHUSER_MOVABLE 함수는 __GFP_HIGHMEM을 포함하고 있다. 결국 해당 페이지는 high memory를 통해서 할당 받을 수 있다는 것이다. &lt;br /&gt;&lt;br /&gt;마지막으로 간단히 GFP_HIGHUSER_MOVABLE에 대해서 설명하면, user가 사용하는 페이지들을 주로 high memory에 할당하는 memory fragementation avoidance 메커니즘이다. 즉, 시스템의 huge page 할당을 위해 연속된 큰 order의 페이지가 필요할 때, movable zone의 페이지들을 swap out시키거나 pageout 시켜, 연속된 메모리 공간을 할당하고자 하는 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4108190141912214992?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4108190141912214992/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4108190141912214992&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4108190141912214992'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4108190141912214992'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/flushdcachepage-kmapatomic.html' title='flush_dcache_page와 kmap_atomic'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5386578203225804405</id><published>2009-01-14T19:20:00.003+09:00</published><updated>2009-01-14T19:42:42.642+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Add support for IO CPU affinity</title><content type='html'>&lt;a href="http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=c7c22e4d5c1fdebfac4dba76de7d0338c2b0d832"&gt;http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=c7c22e4d5c1fdebfac4dba76de7d0338c2b0d832&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이번에 살펴볼 패치는 IO CPU affinity이다. x86의 server side 제품군들이 NUMA로 간지는 오래다. NUMA는 멀티 프로세서 시스템의 공유 메모리에 대한 FSB(Front-Side Bus) bottleneck을 줄이기 위한 시도였다. 하지만 NUMA로 인해 수면위로 드러났던 문제는 cache-miss 문제이다. cache-miss 문제야 이미 오래전 부터 많이 연구되었던 문제지만 NUMA에서는 cache-miss로 인한 cost가 보다 훨씬 크기 때문에 더욱 중요해 졌다. remote node로부터의 cache-to-cache transfer는 시스템의 성능 저하에 큰 요소로 작용한다. 결국, 시스템의 cache hit을 높이는 것이 갈수록 중요해지고 있는데, 이의 일환으로 이번 2.6.28에 들어간 패치 중의 하나가 IO CPU affinity이다. 이미 CPU affinity와 IRQ affinity는 이미 mainline kernel에 들어가 있는 상태이다. 이번에 추가된 IO CPU affinity는 착각하면 IRQ affinity처럼 생각할 수 있지만, IRQ와는 달리 IO를 submit한 CPU에서 IO complete routine도 처리하고자 하는 것이다. 이는 시스템의 cache hit을 높여, 성능측정 결과 20~40%의 성능 향상을 보였다고 한다. 하지만 arch에 따라 지원 여부가 결정된다는 단점이 있다. 해당 arch가 CONFIG_USE_GENERIC_SMP_HELPERS를 지원해야만 사용할 수 있다는 단점이 있다. 지원하지 않는다면 기존과 마찬가지로 여느 CPU에서나 동작하게 될 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5386578203225804405?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5386578203225804405/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5386578203225804405&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5386578203225804405'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5386578203225804405'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/add-support-for-io-cpu-affinity.html' title='Add support for IO CPU affinity'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5748022290513344823</id><published>2009-01-11T20:28:00.003+09:00</published><updated>2009-01-11T20:35:24.010+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Justifying FS-Cache</title><content type='html'>&lt;a href="http://lwn.net/Articles/312708/"&gt;http://lwn.net/Articles/312708/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;David Howells은 오랫동안 이 작업을 진행해왔다. FS-Cache의 목적은 원격의 remote disk로의 읽기가 매우 느리니, 자신의 local disk에 데이터를 캐시하기 위한 generic cache mechanism을 두겠다는 것이다. 그러므로 네트워크 파일 시스템이 주요 고객층이 될 것이다. 네트워크 파일 시스템은 원격지의 데이터와 로컬 데이터의 consistency 문제 때문에 리눅스 커널의 generic page cache mechanism으로 page를 캐시하기 어려워왔다. &lt;br /&gt;&lt;br /&gt;이 패치들은 기존의 VFS layer에 대한 많은 수정을 요하는 조금은 파격적인 패치들이라고 말하고 있다. Andrew는 이와 같이 파격적인 패치를 요하는 user들의 목소리나, 어떤 benmark자료들에 대해 요구했고, David는 그에 대한 benchmark 자료와 이미 redhat에서는 이 패치를 적용하고 있고, entertainment industry의 사용자의 목소리 또한 전해주었다. 이것으로 Andrew의 concern은 어느정도 해결이 된 것 같다. &lt;br /&gt;&lt;br /&gt;하지만 앞으로 또 어떤 concern들이 나오게 될지는 더 두고 봐야 할 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5748022290513344823?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5748022290513344823/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5748022290513344823&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5748022290513344823'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5748022290513344823'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/justifying-fs-cache.html' title='Justifying FS-Cache'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6339605797735975029</id><published>2009-01-11T20:10:00.003+09:00</published><updated>2009-01-11T20:37:42.622+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Btrfs and Squashfs merged for 2.6.29</title><content type='html'>&lt;a href="http://lwn.net/Articles/314325/"&gt;http://lwn.net/Articles/314325/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;2.6.29에 btrfs가 merge될 것으로 보인다.&lt;br /&gt;btrfs는 지난 번 Jonathan Corbet의 세미나에서와 마찬가지로(Jonathan 뿐만 아니라 mainline에서는 이미 공공연한 사실이다), 앞으로 ext 파일 시스템을 대치하는 Linux의 future default file system이 될 수 도 있을 정도로 issue가 되는 file system이다. 기본 concept부터가 기존의 filesystem과는 많이 다르다고 알고 있다. 애석하게도 아직 barrios는 btrfs의 코드를 제대로 분석해보지 못했다. 앞으로 굉장히 linux vm에 많은 패치들을 불러올 수 있는 파일 시스템이어서 조만간 이 파일 시스템에 대해 한번 다뤄야 겠다. 참고로 이 파일시스템은 oracle에 의개 개발되어 open된 파일 시스템이며, maintainer는 Chris Mason이다. &lt;br /&gt;&lt;br /&gt;다음으로, Squashfs 또한 드디어 2.6.29에 merge될 예정이다. 참 긴 여정이었다. &lt;br /&gt;이미 많은 배포판들에 의해 탑재되어 그 성능과 안정성을 입증받은 Squashfs가 coding style과 약간 기형적인 자신만의 캐시 정책들을 수정하여 마지막으로 mainline 입봉에 성공하였다. Linus 마저 OK 했음으로, Andrew는 더 이상 반론의 여지가 별로 없어 보였다. :)&lt;br /&gt;앞으로 임베디드 개발자들이 조금 더 편해질 것으로 보인다.&lt;br /&gt;&lt;br /&gt;Squashfs에 대한 몇몇 개발자들의 말이 재미있다. &lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;Andrew Morton put it: "We've long needed a filesystem named after a vegetable."&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;Harvey Harrison said: "I always preferred my squash with butter, it appears 2.6.30 will be a very tasty kernel."&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;Alan Cox adds:&lt;br /&gt;And vegetables are much [healthier] than FAT ...&lt;br /&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6339605797735975029?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6339605797735975029/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6339605797735975029&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6339605797735975029'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6339605797735975029'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/btrfs-and-squashfs-merged-for-2629.html' title='Btrfs and Squashfs merged for 2.6.29'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4074281766554770848</id><published>2009-01-09T15:25:00.003+09:00</published><updated>2009-01-09T22:32:47.805+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH -v4][RFC]: mutex: implement adaptive spinning</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/1/8/322"&gt;http://lkml.org/lkml/2009/1/8/322&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;현재 mainline에서는 adaptive mutex의 대한 토론이 굉장히 뜨겁다.&lt;br /&gt;정확히 우리나라 시간을 기준으로 어제 오전부터 이슈가 되기 시작해서 현재 시각 기준으로, 약 100개에 가까운 reply가 달려 있으며, reply 또한 당대의 최고의 kernel expert들이다. 내용을 간단히 요약하면 다음과 같다. &lt;br /&gt;&lt;br /&gt;먼저, 간단히 커널의 mutex 구현을 overview하자면, 다음과 같다. &lt;br /&gt;Mutex의 lock path는 두 가지가 있다. fast path와 slow path. &lt;br /&gt;fast path는 lock을 소유하고 있는 프로세스가 없는 경우, lock을 소유하기 위하여 &lt;br /&gt;최소한의 instruction만을 생성하게끔 되어있다.&lt;br /&gt;반면, slow path는 fast path에 대한 시도가 실패하였을 경우, 흔히 아는 일반적인 경우처럼, lock의 wait_list에 자신을 FIFO 형태로 넣어 놓고 sleep 상태로 들어가게 된다.&lt;br /&gt;물론 예외가 있긴 하다. lock에 대한 요청이 TASK_UNINTERRUPTIBLE 상태의 요청이 아니라면 signal latency를 보장하기 위해 sleep으로 들어가지 않고  signal을  먼저 처리하고 &lt;br /&gt;mutex는 error를 반환할 수도 있다. (이 mutex는 application이 사용하는 mutex와는 상관이 없다. 즉 pthread_mutex와 같은 library function은 error를 반환할 일이 없으니 신경쓰지 않기를. 나중에 기회가 되면 futex에 대해서도 한번 다룰 예정이다)&lt;br /&gt;&lt;br /&gt;Adaptive mutex spinning의 아이디어는 특정 task가 소유하려는 lock을 다른 task가 이미 소유하고 있으며, lock을 소유한 task가 현재 실행중이라면(SMP환경에서), 그리고 wait_list에 아무도 그 lock을 기다리지 않고 있다면(starvation 문제가 발생할 수 있기 때문에), context_switching을 2번 이상 발생시키면서, 또 그에 따른 TLB flush와 같이 시스템의 scalability가 커지면 커질수록 비용이 큰 operation들을 처리하지 말고, 차라리 spinning을 하자는 거다. &lt;br /&gt;&lt;br /&gt;이는 lock을 소유하고 있는 프로세스가 현재 수행 중이라면 곧 그 작업은 끝날 것이라는 가정에서 출발한다. 물론 커널의 mutex를 사용하는 code들은 이미 충분히 review되고 있어, critical section이 크지 않다는 가정을 전제로 하기도 한다.&lt;br /&gt;&lt;br /&gt; Linus와 당대 최고의 kernel expert(Linus, Peter, Ingo, Andrew, Steven, David, Andi등)들이 현재시각 기준 2009-01-09.03시15분 98개의 쓰레드로 토론을 하고 있다.&lt;br /&gt;&lt;br /&gt;물론 mutex는 커널에서 굉장히 빈번한 operation중의 하나이고, 성능에 심각한 영향을 초래할 수 있는 core 설비중의 하나이긴 하지만, 이렇게 simple한 idea를 가지고도 그와 관련된 side effect 및 nice implement을 고려하기 위하여 많은 guru급 kernel 개발자들이 실시간 토론을 가능하게 해주는 OpenSource development의 힘에 새삼 놀라며, Linux kernel development process에 매료될 수 밖에 없게 만드는 좋은 예가 될 것 같아 posting한다. &lt;br /&gt;&lt;br /&gt;끝으로 이 패치가 반영되기 전 mutex의 동작구조에 대한 간단한 문서를 첨부한다.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.box.net/shared/ms2s335itx"&gt;mutex&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4074281766554770848?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4074281766554770848/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4074281766554770848&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4074281766554770848'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4074281766554770848'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/patch-v4rfc-mutex-implement-adaptive.html' title='[PATCH -v4][RFC]: mutex: implement adaptive spinning'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-1752032369337376989</id><published>2009-01-08T23:00:00.003+09:00</published><updated>2009-01-08T23:11:56.555+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>한스밴드의 '오락실'</title><content type='html'>오늘은 불현듯 이 친구들이 생각난다.&lt;br /&gt;&lt;br /&gt;IMF 시절에 다양한 악기에 대한 뛰어난 연주실력과  돈벌이에 급급하지 않으며,&lt;br /&gt;자극적이지 않은 가사, 이 시대의 아픔을 노래했던 '오락실'이라는 곡의 한스밴드. &lt;br /&gt;&lt;br /&gt;그리 화려하지 않은 외모지만, 교복을 입고 나와 꽤나 풋풋함을 강조했었던 신선한 밴드였으며, &lt;br /&gt;외국의 다른 밴드처럼 실제 자매들로 이루어진 밴드였다. 4번째 막내도 뒤늦게 조인했었던 것으로 기억한다. 하지만 소속사와의 노예계약으로 결국 소송에 휘말리게 되고, 지금은 CCM만을 하는 것으로 알고 있다. 그녀들의 아버지 또한 목사님이었던 것으로 기억한다. &lt;br /&gt;&lt;br /&gt;안타깝지만, 실력있는 어린 친구들은 그렇게 대중에게 잊혀지고 있다.&lt;br /&gt;하지만, 요즘 다시 세상이 각박해지며, IMF 때보다 더 심하다는 기사 내용들이 &lt;br /&gt;다시 한스밴드의 이 노래가 생각나게 한다. &lt;br /&gt;&lt;br /&gt;&lt;object width="425" height="344"&gt;&lt;param name="movie" value="http://www.youtube.com/v/exCpGsGFkVM&amp;hl=en&amp;fs=1"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/exCpGsGFkVM&amp;hl=en&amp;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-1752032369337376989?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/1752032369337376989/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=1752032369337376989&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1752032369337376989'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1752032369337376989'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/blog-post.html' title='한스밴드의 &apos;오락실&apos;'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4935173914152988346</id><published>2009-01-08T20:08:00.006+09:00</published><updated>2009-01-08T20:48:23.917+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Increase dirty_ratio and dirty_background_ratio?</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/1/7/278"&gt;http://lkml.org/lkml/2009/1/7/278&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;금일 Jan Kara라는 suse개발자에 의해 kernel의 default dirty_ratio와 dirty_background_ratio를 바꾸고자 하는 질문이 들어왔다. 요는 기존의 40,10으로 각각 설정되어 있던 값을 10,5로 2007 4월에 Linus에 의해 바뀌어 테스트를 해보니 performance regression이 발생했다는 것이다. 테스트는 Berkeley DB를 사용한 workload였다. 이러한 workload들은 write io를 많이 발생시키기 때문에 io bottleneck이 생기며 pdflush가 굉장히 aggressive하게 동작하기 시작한다. 그래서 질문은 과연 그때 어떤 target을 위해 값을 그렇게 변경했냐는 것이다. 또한 이렇게 값을 다시 올리는 것이 negative impact이 없다면 SLES11 kernel의 default 값을 바꾸려고 한다는 것이다. &lt;br /&gt;&lt;br /&gt;이에 대해 Peter, Linus, Andrew 정말 재야의 고수들이 다 답을 달아 주었다.&lt;br /&gt;Peter의 답이 부족하여 Linus가 명확한 답을 달아 주었으며, &lt;br /&gt;마지막으로 David Miller의 revert에 찬성하는 조의 발언에 Andrew가 인상적인 말을 남겼다. &lt;br /&gt;&lt;br /&gt;"커널은 그런 일을 바르게 처리할 수 없다. 커널은 patters/workloads들의 사용을 알지 못한다.&lt;br /&gt;배포판들이 이것 뿐만 아니라 다른 knob들도 알맞은 값으로 셋팅하기 위한 노력이 거의 없는 것 같아 실망스럽다."&lt;br /&gt;&lt;br /&gt;Andrew는 initscripts들을 가지고도 시스템의 memory size, disk speed, workload등을 가지고 충분히 처리할 수 있다는 것이다. &lt;br /&gt;&lt;br /&gt;맞는 말이기도 하고.. 한편으론 다른 부분들은 그러한 노력들이 있으니... Linus의 답변 중에도 다음과 같은 말이 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt; (b) scale it dynamically by your IO performance. No, current -git does&lt;br /&gt;    _not_ support this.&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt; 뿐만 아니라, 커널의 readahead와 page reclaiming의 stream data를 먼저 회수하기 위한 노력들 또한 같은 선상에 있다. 문제는 그러한 노력들이 workload에 따라 약이 될 수도 있고 독이 될 수도 있다는 점이다. 그래서 mainline에 merge되기 또한 매우 어렵다는 것이다. &lt;br /&gt;&lt;br /&gt;임베디드 업계에서 커널을 하는 사람들에게서 흔한 일이다. 특정 기능을 바로 커널에 넣어버리려는.. barrios는 그렇게 특정환경에 specific한 feature들을 별로 좋아하지 않는다. 유지보수 면에 있어서 어려움이 발생하고, code quality면에 있어서도 많은 부분을 놓치고 지나갈 수 있기 때문이며 무엇보다 side effect을 고려하지 못하는 짧은 생각에서 기인하는 경우가 흔하기 때문이다. &lt;br /&gt;&lt;br /&gt;커널이 항상 능사는 아니다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4935173914152988346?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4935173914152988346/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4935173914152988346&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4935173914152988346'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4935173914152988346'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/increase-dirtyratio-and.html' title='Increase dirty_ratio and dirty_background_ratio?'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6601563261810925310</id><published>2009-01-06T20:23:00.005+09:00</published><updated>2009-01-07T22:57:03.965+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>RCU에 대한 이해</title><content type='html'>RCU를 다룬 문서들이 많이 있다. Paul은 이미 많은 paper들을 작성해 왔으며, 많은 잡지의 기사들이 RCU에 대해 다뤄왔다. 그럼에도 불구하고 많은 사람들이 RCU를 정확히 이해하지 못하고 있다. 그것은 지금까지 우리가 자료구조 자체와 자료구조에 의해 관리되고 있는 데이터의 대한 동기화를 함께 생각하는 습관을 가지고 있기 때문이다.즉, 데이터를 보호하지 않고 항상 Code를 보호하는 습관을 들여왔기 때문이다. &lt;br /&gt;&lt;br /&gt;RCU를 통해 보호되는 자료구조들은 자료 구조 자체에 있어서 well-define되어 있지만, 자료 구조에 의해 관리되는 데이터 중, stale한 데이터는 알고리즘에 의해 cover되어야 한다. RCU는 단연, stale한 데이터를 생성한다. 하지만 여러 알고리즘들은 이러한 데이터를 극복하고 있다. &lt;br /&gt;&lt;br /&gt;아래 첨부는 그나마 RCU를 가장 쉽게 잘 설명한 LWN의 글을 의역한 것이다. &lt;br /&gt;이 기사 또한 stale data에 대한 처리는 언급하지 않고 있다. &lt;br /&gt;그러므로 읽는 사람들은 계속해서 혼동스러울 수 있다. &lt;br /&gt;&lt;br /&gt;barrios는 앞으로 stale데이터에 대한 처리를 실제 kernel에서 구현된 예를 가지고 설명하려고 한다. &lt;br /&gt;이 역시 시간이 있다면.. 하지만 이에 대한 이해 없이는 RCU를 절대 소화해 낼 수 없을 것이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.box.net/shared/x5r7ugx6o6"&gt;RCU에 대한 이해&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6601563261810925310?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6601563261810925310/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6601563261810925310&amp;isPopup=true' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6601563261810925310'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6601563261810925310'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/rcu.html' title='RCU에 대한 이해'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-336325458191022272</id><published>2009-01-06T08:43:00.003+09:00</published><updated>2009-01-07T08:14:48.273+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[patch] mm: fix lockless pagecache reordering bug (was Re: BUG: soft lockup - is this XFS problem?</title><content type='html'>&lt;a href="http://lkml.org/lkml/2009/1/5/282"&gt;http://lkml.org/lkml/2009/1/5/282&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;오늘 report된 버그이다. 이 문제는 Linus가 쓰레드에 참여할 만큼 쉽지 않은 문제이며, 심각한 문제이기도 하다. &lt;br /&gt;Nick이 오랫동안 작업해서 mainline에 merge시킨 lockess pagecache의 버그가 발생하였다. 하지만 문제를 더 깊게 파고 내려가면 lockess pagecache의 bug라기 보다는 근본적인 원인은 lockless radix tree의 버그일 수도 있다. &lt;br /&gt;&lt;br /&gt;현재 Linux와 Nick의 주장은 합의점을 찾지 못하고 있으며, 좀더 추이를 지켜봐야 할 듯 하다. 쓰레드에 Paul과 Peter까지 참여하였다. 당대 최고의 커널 expert들이 토론을 하고 있으니, 이 문제의 난위도가 어떨지는 쉽게 생각해 볼 수 있을 것이다. 문제는 굉장히 간단하다. &lt;br /&gt;&lt;br /&gt;find_get_pages의 page_cache_get_speculative가 실패한 이후, 다시 radix_tree_deref_slot을 하는 과정에서 page의 _count값을 읽어오기 위해 memory로부터 값을 읽어오는 것이 아니라, 이미 register에 저장되어 있는 값을 계속 사용하기 때문에, page가 radix tree에서 제거되고 _count가 0이 되었음에도, page_cache_get_speculative가 보는 page의 _count는 0이 아니어서 또 실패하고, 다시 radix_tree_defef_slot을 실행하고.. .  해당 cache가 invalid될 때까지는 lockup이 되는 것이다. 아래는 find_get_pages의 컴파일 결과이다. &lt;br /&gt;&lt;br /&gt;역어셈 코드 참조&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;.L220:&lt;br /&gt;       movq    (%rbx), %rax    #* ivtmp.1162, tmp82&lt;br /&gt;       movq    (%rax), %rdi    #, prephitmp.1149&lt;br /&gt;.L218:&lt;br /&gt;       testb   $1, %dil        #, prephitmp.1149&lt;br /&gt;       jne     .L217   #,&lt;br /&gt;       testq   %rdi, %rdi      # prephitmp.1149&lt;br /&gt;       je      .L203   #,&lt;br /&gt;       cmpq    $-1, %rdi       #, prephitmp.1149&lt;br /&gt;       je      .L217   #,&lt;br /&gt;       movl    8(%rdi), %esi   # &lt;variable&gt;._count.counter, c&lt;br /&gt;       testl   %esi, %esi      # c&lt;br /&gt;       je      .L218   #,&lt;br /&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;그래서 Nick은 간단히, repeat의 다음 라인에 barrier를 추가하여 해결하려고 했으나, Linus는 Nick의 그런 제안에 문제점을 지적하였다. Linus의 주장은 그 문제는 lockess pagecache의 버그라기 보다는 RCU를 사용하여 lockless radix tree를 사용할 때 이미 근본적인 문제점을 가지고 있는 것이 아니냐는 것이다. Linus는 RCU를 사용하여 데이터를 보호할 때 RCU 사용하에서 변경될 수 있는 데이터의 필드들은 rcu_dereference를 사용하여 fetch해야 한다는 것이다. 하지만 이 의견에 대해 Nick과의 의견이 상충하고 있고, Paul은 이 문제에 대해 명확한 답을 주지 못하고, 지금부터 주의깊게 살펴볼 듯 하다.&lt;br /&gt;&lt;br /&gt;결국 위의 코드는 패치로 인하여 다음과 같이 바뀌었다. &lt;br /&gt;코드를 보면 rdi의 값을 rbx와 rax 레지스터를 이용하여 memory에서 직접 읽어오는 것을 볼 수 있다. &lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;.L212:&lt;br /&gt;       movq    (%rbx), %rax    #* ivtmp.1109, tmp81&lt;br /&gt;       movq    (%rax), %rdi    #, ret&lt;br /&gt;       testb   $1, %dil        #, ret&lt;br /&gt;       jne     .L211   #,&lt;br /&gt;       testq   %rdi, %rdi      # ret&lt;br /&gt;       je      .L197   #,&lt;br /&gt;       cmpq    $-1, %rdi       #, ret&lt;br /&gt;       je      .L211   #,&lt;br /&gt;       movl    8(%rdi), %esi   # &lt;variable&gt;._count.counter, c&lt;br /&gt;       testl   %esi, %esi      # c&lt;br /&gt;       je      .L212   #,&lt;br /&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-336325458191022272?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/336325458191022272/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=336325458191022272&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/336325458191022272'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/336325458191022272'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/patch-mm-fix-lockless-pagecache.html' title='[patch] mm: fix lockless pagecache reordering bug (was Re: BUG: soft lockup - is this XFS problem?'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6327202103628171542</id><published>2009-01-04T08:56:00.004+09:00</published><updated>2009-01-05T22:06:26.615+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>mm:rewrite vmap layer</title><content type='html'>2.6.28에서 Memory Scalability를 위해 추가된 split lru말고도 우리가 주목해야 할 patch는 vmap이다. Nick이 제안한 이 패치가 mm tree에서 드디어 mainline으로 merge되었다. &lt;br /&gt;&lt;br /&gt;Nick이 주목한 문제는 vmalloc의 scalability이다. 정확하게는 vmap의 scalability이다. 더 정확하게는 vunmap의 scalability이다. vmalloc으로 할당한 주소를 해지하는 이 함수는 당연히 IPI를 통한 TLB flush를 해야만 하기 때문이다. 이는 processor가 많아지면 많아질 수록 overhead가 커질 수 밖에 없다. 그리고 vmalloc의 address space를 관리하는 자료구조가 linked list이고 global lock 하나였다는 것이다. Scalability에 치명적일 수 밖이 없는 구조였다. &lt;br /&gt;&lt;br /&gt;세상에 multicore가 일반화되며 부각된 문제이다. 그러므로 Nick은 먼저 linked list를 없애기 위하여 red-block tree로 대치하였다. 다음 global lock을 없애기 위하여 작은 주소 공간을 각 per_cpu로 cache하여 관리하게끔 바꾸었다. per_cpu list는 32bit에서는 32개, 64bit에서는 64개까지 page를 cache할 수 있다. &lt;br /&gt;&lt;br /&gt;마지막으로 lazy tlb flush를 제안하였다. 해지된 vmalloc의 address space는 시스템으로 회수되기 때문에 다시 할당되기 전까지는 사용될 수 없다. 결국, 어떤 code들도 이미 해지된 그 주소를 다시 사용할 수 없다(Bug가 아니고서야 :)). 하지만 우리가 보장해줘야 할 것은 다시 그 주소 영역이 할당되는 경우이다. 이때는 반드시 TLB consistency를 보장해줘야만 한다. 그러므로 Nick은 해지된 영역들을 충분히 쌓아두었다가 한번에 flush 하자는 것이다. 아이디어가 간단하고 이미 시스템 프로그래밍의 여러 부분에서 사용되고 있는 방법인 반면에, Linux core를 속속들이 이해하지 못하는 경우 생각할 수 없는 좋은 아이디어라고 생각한다. 좀 인위적인 테스트이긴 하지만 대략 기존보다 25배나 빨라진 것을 알 수 있다. &lt;br /&gt;&lt;br /&gt;아직 많이 미진하지만 분석 문서를 첨부한다. &lt;br /&gt;이 문서는 앞으로 보다 세심히 업데이트 할 것이다. &lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.box.net/shared/bss1x8cq5x"&gt;vmalloc 문서&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=db64fe02258f1507e13fe5212a989922323685ce"&gt;mm:rewrite vmap layer&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6327202103628171542?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6327202103628171542/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6327202103628171542&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6327202103628171542'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6327202103628171542'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/mmrewrite-vmap-layer.html' title='mm:rewrite vmap layer'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-503643313433405719</id><published>2009-01-02T10:49:00.003+09:00</published><updated>2009-01-02T11:09:08.178+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH 0/2] pdflush fix and enhancement</title><content type='html'>&lt;a href="http://lkml.org/lkml/2008/12/30/245"&gt;http://lkml.org/lkml/2008/12/30/245&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Novell의 &lt;span style="color: rgb(0, 0, 0);" class="HcCDpe"&gt;&lt;span email="pmorreale@novell.com" class="EP8xU"&gt;Peter W Morreale&lt;/span&gt;&lt;/span&gt; 는 현재 min, max가 2와 8로 고정되어 있는 pdflush의 갯수를  admin이 fine tuning할 수 있게끔 패치를 올렸다. 또한 SMP 시스템에서 동기화 문제로 인하여 pdflush 쓰레드의 갯수가 시스템이 정해놓은 boundary를 넘어가는 경우도 패치하였다. (이것이 point는 아니다.)&lt;br /&gt;&lt;br /&gt;패치 자체는 굉장히 간단하다. 반면, 많은 것을 생각하고 고려했던 패치이다. Andi의 "그러한 knob들을 늘려가는 것은 결국 커널이 self-tuning을 포기하는 것이기 때문에 rationale이 명확해야 한다"는 comment에서 시작하여 굉장히 길게 토론되었다.&lt;br /&gt;&lt;br /&gt;이 쓰레드의 포인트는 현재 pdflush 생성과 소멸의 시점에 문제이다. 현재 구현은 단순히 얼마나 pdflush 쓰레드들이 바쁘냐, 한가하냐만을 가지고 pdflush 스스로 자신의 갯수를 늘리거나 줄인다. 하지만 &lt;span style="color: rgb(0, 0, 0);" class="HcCDpe"&gt;&lt;span email="pmorreale@novell.com" class="EP8xU"&gt;정말 중요한 문제는 pdflush의 쓰레드의 boudary magic value들, 즉 2와 8 또는 &lt;/span&gt;&lt;/span&gt;one pass 에 writeout 할 dirty page들의 갯수인 MAX_WRITEBACK_PAGES(1K) 값들이 문제이다. 이런 static magic value가 모든 경우를 cover할 수 없는 것이다. 컴퓨터 시스템은 다양한 block device들을 가지고 있다. RAID, IDE disk, SSD 등 .. 또한 다양한 device들은 서로 다른 bandwidth를 가지고 있다. 그러므로 500MB/s이 나오는 SSD의 block device에 더 많은 쓰레드를 할당하는 것이 IDE에 하는 것보다 좋지 않겠냐??. 또는 일반적으로 하나의 disk를 가지고 하나의 filesystem을 갖는 small system에서 8개의 쓰레드를 경쟁시키는 것이 과연 좋겠냐는 것이다. 반대로 많은 block device와 file system을 갖는 large server 환경에서 pdflush 쓰레드를 8개로 제한을 하는 것이 효율적일까?? pdflush는 block device들의 특성을 전혀 반영하지 못하고 있다.&lt;br /&gt;&lt;br /&gt;또 다른 문제는 pdflush의 worker function인 background_writeout에서 발생한다. 이 함수는 filesystem을 traverse하며 super block들을 역순으로 writeout하기 시작한다. 즉 file system들의 dirty page들의 불균형이 올 수 있다는 것이다. 가장 마지막의 filesystem의 dirty page들이 우선적으로 고려되기 때문이다.&lt;br /&gt;&lt;br /&gt;그러므로 이번에 올린 패치와는 무관하게 pdflush의 근본적인 redesign이 필요하다는 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-503643313433405719?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/503643313433405719/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=503643313433405719&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/503643313433405719'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/503643313433405719'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2009/01/patch-02-pdflush-fix-and-enhancement.html' title='[PATCH 0/2] pdflush fix and enhancement'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6312394451162477908</id><published>2008-12-31T22:13:00.008+09:00</published><updated>2009-01-02T16:19:25.849+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Guitar'/><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>EOF of 2008</title><content type='html'>한해, 한해는 정말 바쁘기만 하다.&lt;br /&gt;&lt;br /&gt;늘상, 집, 회사만을 오가면서도 이렇게 한해가 바쁠 수 있었던 것은&lt;br /&gt;지키려는 것들이 늘어만 가기 때문일 것이다. 지켜야 할 것들과 미련한 소유욕이 한해 동안 여러 득실을 가져다 주었다.&lt;br /&gt;&lt;br /&gt;여러 기억에 남을 일들이 있는 한해지만 무엇보다 인상깊었던 일은 다시 기타를 잡았다는 것일 것이다. 손 놓은 지 거의 5년 만에 다시 잡은 기타다. 예전 연주했던 곡과 악보를 마주할 때는 그 추억들에 혼자 센치해지곤 했다. 이번에 다시 잡은 기타는 다시 놓지 않게 될 것 같다. 녀석들과 소주 한잔 해야 하는데... 저울이 기울어지지가 않으니.&lt;br /&gt;&lt;br /&gt;여러 사람들이 떠나고, 새로 들어오고 했던 한 해이기도 하다. 눈에서 멀어진 사람도 있고 마음에서 멀어진 사람도 있고... 나는 언제가부터 과감히 금을 긋기 시작했다. 말이란 것이 비뚤어지기 시작하면 결국 그 속내가 드러나기 마련이다. 오히려 있는 듯, 없는 듯, 자신을 과장해서 낮추거나 광대가 되는 편이 더 낫다. 물론 오해가 있는 경우도 있지만, 한번 소원해진 관계는 한계가 있기 때문이다. 이러한 일들이 점점 나를 가두는 일일지언정.&lt;br /&gt;&lt;br /&gt;하고자 하는 일에 초석을 세운 한해 이기도 하다. 그 일에 대한 두려움 보다는 해나가과는 과정이 재밌기만 하다. 아직 갈길이 멀지만 언제나처럼 시간은 부족하다. 호기심이 절정에 달한 이 시기가 매우 중요하다. 내년 한 해는 올해보다 더 중요한 시기가 될 것이다.&lt;br /&gt;&lt;br /&gt;언제나 드는 생각이지만 Zero Sum 게임이다. 얻는 것이 있으면 잃는 것도 있는 것이 당연지사. 귀차니즘에 편승한 그러한 생각들이 가끔은 삶을 윤택하게 하기도 한다.&lt;br /&gt;&lt;br /&gt;끝으로, 감정표현이 서투른 탓에 항상 잘해주지 못해도, 끝까지 참아주고 믿어주는 이 친구에게도 감사의 말을 전한다.&lt;br /&gt;&lt;br /&gt;Adios 2008&lt;br /&gt;&lt;br /&gt;꼬랑지)&lt;br /&gt;&lt;br /&gt;Greenmail은 항상 불평이다. 내가 연주하는 이 곡이 맘에 안든다는 것이다.&lt;br /&gt;사람을 우울하게 만든다고. 그래도 가끔 콧노래로 따라 부르는 것을 보면 그렇게 맘에 들지 않는 것도 아닌가 보다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;object height="344" width="425"&gt;&lt;param name="movie" value="http://www.youtube.com/v/Y956uzH86XQ&amp;amp;hl=en&amp;amp;fs=1"&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;embed src="http://www.youtube.com/v/Y956uzH86XQ&amp;amp;hl=en&amp;amp;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" height="344" width="425"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6312394451162477908?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6312394451162477908/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6312394451162477908&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6312394451162477908'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6312394451162477908'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/2008.html' title='EOF of 2008'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-1278137689049016858</id><published>2008-12-31T08:25:00.002+09:00</published><updated>2008-12-31T08:38:41.300+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH] cpuset,mm: fix allocating page cache/slab object on the unallowed node when memory spread is set</title><content type='html'>&lt;a href="http://lists-archives.org/linux-kernel/19778435-cpuset-mm-fix-allocating-page-cache-slab-object-on-the-unallowed-node-when-memory-spread-is-set.html"&gt;&lt;br /&gt;http://lists-archives.org/linux-kernel/19778435-cpuset-mm-fix-allocating-page-cache-slab-object-on-the-unallowed-node-when-memory-spread-is-set.html&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;크리스마스 징검다리 연휴가 들어가기전 report되었던 버그이다.&lt;br /&gt;Miao라는 중국 fujitsu 개발자이다.&lt;br /&gt;문제는 memory_spread_page가 set되어 cupset's mem이 변경되었을 때 slab이 바로 그 사항을 반영하지 못하여 old mem에서 메모리를 할당한다는 것이다.&lt;br /&gt;&lt;br /&gt;것도 문제이지만 더 큰 문제는 해당 패치가 kernel's hot path에서 polling하는 루틴을 넣었다는 것이다. 이에 대해 다른 개발자들은 모라고 할 것인지 그 추이를 지켜보고 있었는데 아니나 다를까 Andrew는 다음과 같은 문제를 제기했다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;c) These are two of the kernel's hottest code paths.  We really&lt;br /&gt;   really really really don't want to be polling for some dopey&lt;br /&gt;   userspace admin change on each call to __cache_alloc()!&lt;br /&gt;&lt;br /&gt;d) How does slub handle this problem?&lt;/blockquote&gt;&lt;br /&gt;C는 barrios와 같은 의견이고 D에 대해 Christoph가 모라고 답변을 할지 기대된다. 그 추이를 지켜보자.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-1278137689049016858?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/1278137689049016858/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=1278137689049016858&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1278137689049016858'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/1278137689049016858'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/patch-cpusetmm-fix-allocating-page.html' title='[PATCH] cpuset,mm: fix allocating page cache/slab object on the unallowed node when memory spread is set'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7609704789357226748</id><published>2008-12-28T17:24:00.002+09:00</published><updated>2008-12-28T17:54:47.155+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>SLQB - and then there were four</title><content type='html'>&lt;a href="http://lwn.net/Articles/311502/"&gt;http://lwn.net/Articles/311502/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;요즘 관심을 가지고 있는 것이 SLQB이다. SLQB는 기억으론 5개월 전쯤 이미 한번 RFC가 올라왔었다. 하지만 그 때 mm guys들은 별다른 반응을 보이지 않았었다. 그 때는 이미 SLUB에 대해 막판 다듬기가 한참이었던 것으로 기억한다. 그래서 다들 SLUB에 신경을 곤두세우고 있어서 일지도 모르겠다. 어쨌든 Nick은 두번째 제안을 해왔다.&lt;br /&gt;&lt;br /&gt;SLQB의 특징은 구조가 굉장히 간단하면서 기존의 다른 allocator들에 크게 뒤지지 않는다. 그 이유는 per-CPU 형태를 취하고 있기 때문에 lock이 많이 줄어들었다. 또한 SLQB는 가능한한 high order allocation들을 피하려고 한다. high order allocation은 memory pressure의 가장 큰 범인이기도 하다. 그러므로 단편화를 줄이기 위해서라도 one order allocation이 바람직하다.&lt;br /&gt;&lt;br /&gt;SLQB는 freelist, rlist, remote_free list로 object들의 list를 나누어 관리한다. 그 이유는 cache bouncing을 줄이기 위함이다. long running object들은 할당한 CPU가 아닌 다른 CPU에 의해서 해지될 가능성이 높다. 그러므로 cache line bouncing을 줄이기 위해 해지되는 object들은 처음 할당한 CPU로 옮겨주는 작업을 하여 cache hit을 최대한 높이겠다는 의지인데, 과연 long running한 object들이 할당된 CPU의 cache에 아직 남아 있을까?? 좀더 생각해 볼 필요가 있다.&lt;br /&gt;&lt;br /&gt;SLQB의 전반적인 성능은  slab에 비하여 다소 떨어진다. 그 이유는 명확하지 않다. object들을 array 형태가 아닌 list 형태로 구현하면서 object cacheline layout의 변화에 기인한 것일 수도 있다.  어쨌든 Nick은 계속해서 이 allocator의 성능을 높일 것이며 barrios 또한 계속해서 이 코드에 대해 review 할 것이다.  코드에 사소한  bug와 naive한 code가 있으나 review가 다소 늦어서 이번에 comment하진 않을 것이다.&lt;br /&gt;&lt;br /&gt;SLQB를 테스트 하는 동안 기존의 mainline kernel에서 bug가 발견되었다.  SLQB를 사용했을 때 그 문제가 나타나게 된 원인은 SLQB는 object안에 metadata를 함께 관리하고 있기 때문이다. 그러므로 object의 크기 이상으로 메모리를 write하였을 경우, object list가 붕괴된다. 그 문제는 POISON을 가지고 알 수 있다. 바로 mainline에 report하려 했으나, rc 버젼이었고 SLQB 또한 review가 끝나지 않은 상태라서 보고 하지 않았다. 2.6.28이 나왔으니 SLQB를 시험해보고 문제가 동일하게 다시 발생한다면 그 때 보고할 예정이다.&lt;br /&gt;&lt;br /&gt;꼬랑지)&lt;br /&gt;시간이 되면 POISON과 RED_ZONE도 문서에 추가하고 싶긴한데.. 사람들이 일반적으로 잘 모르는 기능이라.. 시간이 될지 모르겠다. 다른 할일이 많아..&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;끝으로 간단히 분석한 문서를 첨부한다.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.box.net/shared/bn6nz5zer6"&gt; SLQB 문서&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7609704789357226748?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7609704789357226748/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7609704789357226748&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7609704789357226748'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7609704789357226748'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/slqb.html' title='SLQB - and then there were four'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8777098638794163322</id><published>2008-12-25T19:13:00.002+09:00</published><updated>2008-12-25T19:21:04.707+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>The 2.6.28 kernel is out</title><content type='html'>&lt;a href="http://lwn.net/Articles/312786/"&gt;http://lwn.net/Articles/312786/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;2.6.28이 release 되었다. 몇가지 살펴봐야 할 주요한 패치들이 있다.&lt;br /&gt;시간이 되고 정리가 되면 그 때 다시 살펴보기로 한다.&lt;br /&gt;&lt;br /&gt;Linus의 말이 재미있다.   크리스마스 답게 산타의 선물에 빗댄 2.6.28 release.&lt;br /&gt;과연 아이들이 그 선물을 좋아할까? ^^&lt;br /&gt;&lt;br /&gt;각설하고 이번 2.6.28의 릴리즈는 나에게는 그 이상의 의미가 있다.&lt;br /&gt;한동안 작업했던 메모리 회수의 성능 향상을 위한 split LRU가 mainline에 정식으로 merge되었다.&lt;br /&gt;그로 인해 몇건의 mainline contribution이 더 추가되었다.&lt;br /&gt;&lt;br /&gt;작은 fix또한 &lt;span class="signoff"&gt;Signed-off-by&lt;/span&gt;를 추가해준 Rik에게 감사의 마음을 전한다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8777098638794163322?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8777098638794163322/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8777098638794163322&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8777098638794163322'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8777098638794163322'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/2628-kernel-is-out.html' title='The 2.6.28 kernel is out'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7592350846287766629</id><published>2008-12-22T23:30:00.003+09:00</published><updated>2008-12-22T23:40:27.809+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Guitar'/><title type='text'>Vals No. 4 Op. 8</title><content type='html'>근래 연습중인 곡이다. &lt;br /&gt;망고레의 왈츠 4번. &lt;br /&gt;&lt;br /&gt;2003년 이었던 것으로 기억한다. 후배 한 녀석이 오랫만에 찾은 동아리방에서 연주하고 &lt;br /&gt;있던 곡이 이 곡 이었다. 그 전까지는 사실 별로 연주하고 싶은 맘이 들던 곡은 아니었다.&lt;br /&gt;딱히, 그 후배가 이 곡을 연습하게 해준 동기는 아니더라도, &lt;br /&gt;나도 이 곡을 연주 할 수 있게 구나 하는 정도의 동기는 유발해준 것이 사실이다. &lt;br /&gt;&lt;br /&gt;이 곡의 하이라이트는 중간의 연속되는 아르페지오와 함께 상승 베이스, &lt;br /&gt;다시 하강 베이스 바하의 대위법은 아니지만 서정적이면서도 멋있는 곡의 &lt;br /&gt;분위기를 살려준다. &lt;br /&gt;&lt;br /&gt;특히 마지막 부분에 고조감을 느끼게 연주하여 끝을 맺는 부분을 잘 살려서 연주해야 한다. &lt;br /&gt;&lt;br /&gt;아래 동영상은 실제 CD 연주보다는 다소 천천히 친 감이 있다. &lt;br /&gt;망고레 연주의 대가 러쎌의 연주를 감상할 수 있는 여유가 있을 때 이 곳을 들를 수 있기를.&lt;br /&gt;&lt;br /&gt; - 2008년 두번째 눈이 내리던 날 - &lt;br /&gt;&lt;br /&gt;&lt;object width="425" height="344"&gt;&lt;param name="movie" value="http://www.youtube.com/v/oRXFsYsEmcI&amp;hl=ko&amp;fs=1"&gt;&lt;/param&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;/param&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;/param&gt;&lt;embed src="http://www.youtube.com/v/oRXFsYsEmcI&amp;hl=ko&amp;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7592350846287766629?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7592350846287766629/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7592350846287766629&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7592350846287766629'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7592350846287766629'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/vals-no-4-op-8.html' title='Vals No. 4 Op. 8'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2031539826710133473</id><published>2008-12-22T09:52:00.002+09:00</published><updated>2008-12-22T10:00:40.341+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>all about documentation</title><content type='html'>&lt;a href="http://lwn.net/Articles/310569/"&gt;http://lwn.net/Articles/310569/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;커널 개발자들은 documentation에 대하여 굉장히 회의적이다.&lt;br /&gt;Andrew의 말이 인상적이다.&lt;br /&gt;&lt;br /&gt;"코드를 clear하게 만드는 것 보다는, 아무생각없이 단지&lt;br /&gt;여기에 주석을 넣기로 되어 있으니...."&lt;br /&gt;&lt;br /&gt;이미 TDD와 같은 방법론에서는 주석을 Andrew와 같은 이유로 주석을 금기시하기도 한다.&lt;br /&gt;하지만, 어디까지나 저건 이미 guru의 반열에 오른 커널 developer들의 이야기이다.&lt;br /&gt;&lt;br /&gt;사실, 커널 code를 exploration할 때 중간중간 주석이 없으면 굉장히 이해하기 어려운 부분들이 많이 있다. 물론 obsolete한 주석들도 많이 있긴하다. 하지만 그런 주석들로 인하여 긴 항해에서 방향을 잃지 않을 수 있을 때가 더 많이 있다는 것이 내 경험이다. 특히 kernel core 쪽은 단순한 logic이 아닌, 특정 machine에서 발생했던 regression들로 인하여, 이상한 magic code들이 들어가 있기도 하다. 이것은 커널 patch history를 follow up하지 않고 있으면 logic 상으로는 도저히 이해할 수 없는 코드들이다.&lt;br /&gt;&lt;br /&gt;요즘은 Andrew를 비롯한 많은 kernel developer들이 git의 log의 중요성을 강조하고 있어, 문제를 보다 명확하게 logging을 하려고 하고 있어 대체적으로 만족할 만한 수준이다.&lt;br /&gt;&lt;br /&gt;어쩌면, 나와 같은 kernel newbie들도 그런 주석에 고마워해야 할 게 아니라, 주석들로 인하여 clear되지 않고 있는 코드들에 질타를 던져야 하나...&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2031539826710133473?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2031539826710133473/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2031539826710133473&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2031539826710133473'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2031539826710133473'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/all-about-documentation.html' title='all about documentation'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2296283037339355355</id><published>2008-12-11T11:37:00.005+09:00</published><updated>2008-12-11T13:52:04.962+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>2002 kernel trap Ingo Molnar Interview</title><content type='html'>2002년 인터뷰 내용중 관심 있는 부분들만...&lt;br /&gt;&lt;br /&gt;&lt;a href="http://kerneltrap.org/node/517"&gt;http://kerneltrap.org/node/517&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;hr /&gt; &lt;p&gt;&lt;i&gt;Jeremy Andrews&lt;/i&gt;: When did you get started with Linux?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; i think i first heard &lt;/span&gt;&lt;a id="publishButton" class="cssButton" href="javascript:void(0)" onclick="if (this.className.indexOf(&amp;quot;ubtn-disabled&amp;quot;) == -1) {var e = document['stuffform'].publish;(e.length) ? e[0].click() : e.click(); if (window.event) window.event.cancelBubble = true; return false;}"&gt;&lt;div class="cssButtonOuter"&gt;&lt;div class="cssButtonMiddle"&gt;&lt;div class="cssButtonInner"&gt;&lt;br /&gt;&lt;/div&gt;&lt;/div&gt;&lt;/div&gt;&lt;/a&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;about Linux around 1993, but i truly got hooked on kernel development in 1995 when i bought the german edition of the 'Linux Kernel Internals' book. It might sound a bit strange but i installed my first Linux box for the sole purpose of looking at the kernel source - which i found (and still find) fascinating. So i guess i'm one of the few people who started out as a kernel developer, later on learned their way to be a Linux admin and then finally learned their way around as a Linux user ;-) &lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: What was your first contribution to the kernel?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; my very first contribution was a trivial #ifdef bugfix to the networking code, which was reviewed and merged by Alan Cox. At that point i've been lurking on the kernel mailing list for a couple of months already. My first bigger patch was to arch/i386/kernel/time.c, i implemented timestamp-counter based gettimeofday() on Pentiums (which sped up the gettimeofday() syscall by a factor of ~4) - that code is still alive in current kernels. This patch too was first reviewed by Alan Cox.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;I strongly believe that a positive 'first contact' between kernel newbies and kernel oldbies is perhaps the single most important factor in attracting new developers to Linux. Besides having the ability to code, kernel developers also need the ability to talk and listen to other developers.&lt;/p&gt;&lt;p&gt;JA: Did you base the design on any existing scheduler implementations or research papers?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; this might sound a bit arrogant, but i have only read (most of the) research papers after writing the scheduler. This i found to be a good approach in the area of Linux - knowing about too many well-researched details can often confuse the real direction we have to take. I like writing new code, and i prefer to approach things from the physics side: take a few elementary rules and build up the 'one correct' solution, no compromises. This might not be as effective as first reading all the available material and then cherry-picking a few ideas and thinking up the remaining things, but it sure gives me lots of fun :-)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;[ One thing i always try to ensure: i take a look at all existing kernel patches that were announced on the linux-kernel mailing list in the same area, to make sure there's no duplication of effort or NIH syndrome. Since such kernel mailing-list postings are progress reports of active research, it can be said that i read alot of bleeding-edge research. ]&lt;/p&gt;&lt;p&gt;JA: How do JVMs trigger an inefficiency in the old scheduler?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; the Java programming model prefers the use of many 'threads' - which is a valid and popular application programming model. So JVMs under Linux tend to be amongst the applications that use the most processes/threads, which are interacting in complex ways. Schedulers usually have the most work to do when there are more tasks in the systems, so JVMs tend to trigger scheduler inefficiencies sooner than perhaps any other Linux application.&lt;/span&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;JA: You're also the author of the original kernel preemption patch. How did your patch differ from the more recent work Robert Love has done in this area?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; it was a small concept-patch from early 2000 that just showed that a preemptible kernel can indeed be done by using SMP spinlocks. The patch, while it booted and appeared to work to a certain degree, had bugs and did not handle the many cases that need special care, which Robert's patches and the current 2.5 kernel handles correctly.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;otherwise the base approach is IMO very similar, it has things like:&lt;/p&gt; &lt;pre&gt;+               preempt_on();&lt;br /&gt;            clear_highpage(page);&lt;br /&gt;&lt;br /&gt;+               preempt_off();&lt;/pre&gt;&lt;p&gt;and:&lt;/p&gt; &lt;pre&gt;+               atomic_inc_local(&amp;amp;current-&gt;may_preempt);        \&lt;/pre&gt;&lt;p&gt;which is quite similar to what we have 2.5 today, with the difference that&lt;br /&gt;Robert and the kernel developer community actually did the other 95% of the work :-)&lt;/p&gt; &lt;p&gt;JA: Are you also actively working on 2.5 preemptible kernel development?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; The maintainer is Robert - i do tend to send smaller preempt related patches (and even a larger one, the 'IRQ lock removal' patch centered around the use of the preemption count). I'm obviously interested in the topic, and i'm happy that all the seemingly conflicting concepts as lowlatency and preemption are now properly merged into 2.5 and that we have really good kernel latencies. Other pressing topics like the scheduler and the threading code still keep me busy most of the time.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Your IRQ rewrite and Robert's preemptible kernel work have resulted in a unified per-task atomic count (the preempt_count) and a lot of code being cleaned up. Do you have plans to do more work in this area?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; not at the moment - right now i think that the IRQ code could hardly be any cleaner than it is today :-)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: What other kernel projects are you currently working on?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; mainly the scheduler, plus these days i'm working on enhancing the handling of 'threads' under Linux, utilized by the NPTL project done by glibc maintainer Ulrich Drepper. This has a high number of components that are in the 2.5 kernel already. &lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Can you further describe the components that have already been merged into the 2.5 kernel?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; TLS stands for 'Thread Local Storage'. You can find the first announcement of the patch at:&lt;/span&gt;&lt;/p&gt; &lt;blockquote&gt;&lt;p&gt; &lt;a linkindex="16" href="http://lwn.net/Articles/5851/" target="new"&gt;http://lwn.net/Articles/5851/&lt;/a&gt;&lt;/p&gt;&lt;/blockquote&gt; &lt;p&gt;a number of followup patches were posted, and it all got eventually merged&lt;br /&gt;into 2.5.31.&lt;/p&gt; &lt;p&gt;Plus there were a few other things related to threading:&lt;/p&gt; &lt;blockquote&gt;&lt;p&gt; &lt;a linkindex="17" href="http://lwn.net/Articles/8131/" target="new"&gt;http://lwn.net/Articles/8131/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a linkindex="18" href="http://lwn.net/Articles/8034/" target="new"&gt;http://lwn.net/Articles/8034/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a set="yes" linkindex="19" href="http://lwn.net/Articles/7618/" target="new"&gt;http://lwn.net/Articles/7618/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a linkindex="20" href="http://lwn.net/Articles/7617/" target="new"&gt;http://lwn.net/Articles/7617/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a linkindex="21" href="http://lwn.net/Articles/7603/" target="new"&gt;http://lwn.net/Articles/7603/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a linkindex="22" href="http://lwn.net/Articles/7411/" target="new"&gt;http://lwn.net/Articles/7411/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a linkindex="23" href="http://lwn.net/Articles/7408/" target="new"&gt;http://lwn.net/Articles/7408/&lt;/a&gt;&lt;/p&gt;&lt;/blockquote&gt; &lt;p&gt;(note that most of the above patches got reworked significantly before they&lt;br /&gt;got into the 2.5 kernel, but the concepts were all preserved.)&lt;/p&gt;&lt;br /&gt;&lt;p&gt;JA: What other Linux kernel related projects have you worked on in the past?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; here's a probably incomplete list of the bigger pieces that made it into the kernel: software-RAID support, 3-level paging on x86 (and highmem), the recent IRQ handling rewrite in 2.5 (which also removed the 'big IRQ lock'), the timer scalability patch, kernel workqueues, the CPU affinity syscalls, the initial SMP pagecache scalability code in 2.3, and i also wrote the original 'writeback pagecache' patch for 2.3, wrote various fixes and enhancements to the 'old' scheduler, wrote the 'wake one' support patch for 2.4, wrote the original zoned allocator, bootmem and mempool subsystems. Ie. all across the spectrum.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;One project that is not in the 2.5 kernel is the Tux webserver (and now FTP server as well). If you want to see a Tux/FTP server that can serve 10,000 users then do:&lt;br /&gt;&lt;/p&gt;&lt;blockquote&gt; ftp &lt;a href="ftp://ftp.rpmfind.net/" target="new"&gt;ftp.rpmfind.net&lt;/a&gt;&lt;/blockquote&gt; &lt;p&gt;some smaller but interesting patches: the NMI watchdog, the ability of the 2.4 kernel to create more than ~4000 processes on x86 (ie. the removal of per-thread TSS), netconsole/netdump, 'big reader locks', and one older patch from 2.2 times i'm particularly proud of: i wrote the original 'current task pointer' implementation, which uses the stack pointer to get to the 'current task pointer' on SMP systems. I also wrote the 'memleak' and 'ktrace' debugging helper tools, which have been picked up by other projects.&lt;/p&gt; &lt;p&gt;JA: Your list of contributions is staggering!&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; well, it's just that i've been around long enough, and that i'm interested in many different areas. So a colorful mix of contributions piled up.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Are you still working on the Tux webserver?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; occasionally yes, but other things take precedence currently. But life has not stopped, eg. Anton Blanchard has ported Tux to 2.5, and Arjan van de Ven keeps the 2.4 patch uptodate.&lt;/span&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;JA: What still needs to be modified in the generic kernel?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; it's mainly two VFS changes, an exit()-time cleanup function and one new TCP event callback. All the 'big' features that were induced by TUX are in the 2.5 kernel already, zerocopy and the scalability work, so TUX for 2.5 is a really unintrusive patch.&lt;/span&gt;&lt;/p&gt;&lt;p&gt;JA: Of all these many impressive accomplishments, which are you the most proud?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; well, perhaps the scheduler, it manages to solve a few really hard conceptual problems in a pretty critical piece of code that already got called a couple of thousand times while eg. reading this article on a Linux box! :-)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: What is your background in programming prior to getting involved with Linux?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; well, like many others, i grew up on programming all possible (and even some impossible) aspects of Commodore micro-computers, since age 11. Completely knowing a greatly simplified but fully functional computer architecture helped alot in kernel development.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;I think kids today have a harder time, since hardware vendors are much more tightlipped about computer internals, and the complexity of computer systems skyrocketed as well. Linux perhaps helps here too, as a central 'documentation' and reference implementation for "all computer internals that matter".&lt;/p&gt; &lt;p&gt;JA: Much of your work seems to be focused on improving the performance and scalability of the 2.5 kernel. Is this the result of RedHat's product requirements, or your own interests?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; well, i'm in the fortunate position that the two are a perfect match.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Can you describe your development environment, including the hardware and software tools you typically use?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; i use all the normal text based kernel development tools: vim, gcc/make/etc., i use a serial line to a test-system to debug kernels, and that's all. I like it simple when reading kernel code: i use text consoles (on an LCD screen) to do most of my development work. Occasionally i drop into X for tools that make sense only there, such as ethereal or some of the BK tools.&lt;/span&gt;&lt;br /&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;&lt;/i&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Have you worked with any other open source kernels?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; not really. I occasionally take a look at FreeBSD - some things they do right, some things they dont, in the areas i'm most interested in the Linux kernel is currently ahead both design-wise and implementation-wise. Finally we caught up in the VM subsystem as well, with Andrea's big and important 2.4 rewrite, Rik's great rmap code and Andrew's fantastic integration work. But what other answer would one expect from a Linux kernel developer? :-)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: FreeBSD 5.0 is due to be released around December of this year, with some significant changes to the kernel. Have you followed this development?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; not really. The things i sometimes do is to look at their code. Also, when i search for past discussions regarding some specific topic, sometimes there's a FreeBSD hit and then i read it. That's all what i can tell. But i do wish their kernel gets better just as much as the Linux kernel gets better, there needs to be competition to drive both projects forwards. (the Windows kernel is closed up enough so that it does not create any development stimulus for Linux (and vice versa). Rarely do any Windows features get discussed.)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: What areas of the Linux kernel do you think still lags behind FreeBSD?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; there were two areas where i think we used to lag, the VM and the block IO subsystem - both have been significantly reworked in 2.5. Whether the VM got better than FreeBSD's remains to be seen (via actual use), but the Linux VM already has features that FreeBSD does not have, eg. support for more than 4 GB RAM on x86 (here i guess i'm biased, i wrote much of that code). But FreeBSD's core VM logic itself, ie. the state machine that decides what to throw out under memory pressure, how to swap and how to do IO, is top-notch. I think with Andrew Morton's and Jens Axobe's latest VM and IO work we are top-notch as well (with a few extras perhaps).&lt;/span&gt;&lt;/p&gt; &lt;p&gt;There's also an interesting VM project in the making, Arjan van de Ven's O(1) VM code. [without doubt i do appear to have a sweet spot for O(1) code :-) ] Rik van Riel has merged Arjan's code a couple of days ago. The code converts every important VM algorithm (laundering, aging) to a O(1) algorithm while still keeping the fundamentals - this is quite nontrivial for things like page aging. It's in essence the VM overhead reduction work that Andrea Arcangeli has started in 2.4.10, brought to the extreme. I have run Arjan's O(1) VM under high memory pressure, and it's really impressive - kswapd (the central VM housekeeping kernel thread), which used to eat up lots of CPU time under VM load, has almost vanished from the CPU usage chart.&lt;/p&gt; &lt;p&gt;I do have the impression that the Linux VM is close to a conceptual breakthrough - with all the dots connected we now have something that is the next level of quality. The 2.5 VM has merged all the seemingly conflicting VM branches that fought it out in 2.4, and the many complex subsystems involved suddenly started playing in concert and produce something really nice.&lt;/p&gt; &lt;p&gt;JA: A much earlier version of the rmap code was originally in the 2.4 kernel, but got ripped out. Do you feel it has improved enough that this won't happen again?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; this most definitely wont happen. We already rely on rmap for some other features, so it's not just a matter of undoing one patch. Rmap is essential to the new VM, without rmap the VM would be like a ferrari with an old diesel motor - looks good but is pretty unusable.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;the problem of rmap in 2.4 was simply its complexity, relative youth as a project and the relative low number of people that tested it. So in 2.4 it would have been quite a stretch to keep it in. But it was a fair game for 2.5, and with Andrew's simplification/robustization/speedup of Rik's rmap code it was very manageable.&lt;/p&gt;&lt;br /&gt;&lt;p&gt;JA: What other major improvements have gone into 2.5, beyond the scheduler and VM rewrites?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; the block IO rewrite, lots of VFS changes, a rework of the module code and (plug) the new threading implementation. The block IO rewrite was long overdue and that's the one i'm most happy about.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Do you feel the changes are significant enough to call the next major kernel 3.0 instead of 2.6?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; well, i do think they are significant enough to be called 3.0 - on the other hand it might not matter much whether it's called 2.6 or 3.0, after all what ordinarily people know about is this new shiny Linux 9.0 release, right? ;)&lt;/span&gt;&lt;/p&gt; &lt;p&gt;JA: Looking into the future, what do you see in store for the next development kernel, version 2.7?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; no idea, really, i dont think trying to look into the future brings many fruits, the kernel needs to handle what is available here and today. Sometimes we are lucky and create stuff that happens to work for years :-) Perhaps something like OpenMosix would be nice to have in the kernel. Plus even better (native) support for User Mode Linux. Things like this.&lt;/span&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;JA: Do you have any advice to offer those aspiring to become productive kernel developers?&lt;/p&gt; &lt;p&gt;&lt;span style="color: rgb(102, 102, 102);"&gt;&lt;i&gt;Ingo Molnar:&lt;/i&gt; only the old mantra: to read the source and the mailing lists. And take it easy - do what you like doing most.&lt;/span&gt;&lt;/p&gt; &lt;p&gt;&lt;br /&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2296283037339355355?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2296283037339355355/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2296283037339355355&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2296283037339355355'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2296283037339355355'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/2002-kernel-trap-ingo-molar-interview.html' title='2002 kernel trap Ingo Molnar Interview'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3541375506196889216</id><published>2008-12-11T07:52:00.003+09:00</published><updated>2008-12-11T11:45:37.361+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>[PATCH] fix mapping_writably_mapped()</title><content type='html'>&lt;a href="http://lkml.org/lkml/2008/12/10/344"&gt;http://lkml.org/lkml/2008/12/10/344&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;이 문제는 &lt;span email="Lee.Schermerhorn@hp.com"&gt;Lee Schermerhorn&lt;/span&gt;에 의해 보고된 문제이다.&lt;br /&gt;shared 속성의 vma를 counting하는  i_mmap_writable가 fork시에 정상적으로 counting이 되지 않고 있는 문제였다. 심지어는 음수로 가기도 한다.&lt;br /&gt;&lt;br /&gt;이것은 Hugh가 2.6.7에서 패치하였던 __vma_link_file의 문제였다.&lt;br /&gt;__vma_link_file에서 counting을 해주지 않아 발생하였던 문제이다.&lt;br /&gt;&lt;br /&gt;어떻게 이 문제가 이제야 발견되었을까? 문제는 assert와 같은 루틴이 없었다는 것이다.&lt;br /&gt;count가 음수로 가도 시스템이 계속해서 수행되었다는 것이다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;아래는 Lee가 테스트했던 방법이다.&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;root@dropout(root):memtoy&lt;br /&gt;memtoy pid:  3301&lt;br /&gt;memtoy&gt;file /tmp/zf1&lt;br /&gt;memtoy&gt;map zf1 shared&lt;br /&gt;&lt;br /&gt;console:__vma_link_file:  vma: ffff8803fdc090b8 - mapping-&gt;i_mmap_writable: 0 -&gt; 1&lt;br /&gt;&lt;br /&gt;memtoy&gt;child c1&lt;br /&gt;memtoy:  child c1 - pid 3302&lt;br /&gt;&lt;br /&gt;me: I would have expected to see i_mmap_writable incremented again here, but&lt;br /&gt;me: saw no console output from my instrumentation.&lt;br /&gt;&lt;br /&gt;memtoy&gt;unmap zf1        # unmap in parent&lt;br /&gt;&lt;br /&gt;console:__remove_shared_vm_&lt;div id=":m4" class="ArwC7c ckChnd"&gt;&lt;wbr&gt;struct:  vma: ffff8803fdc090b8 - mapping-&gt;i_mmap_writable: 1 -&gt; 0&lt;br /&gt;console:__remove_shared_vm_&lt;wbr&gt;struct:  vma: ffff8803fdc090b8 - removed last shared mapping&lt;br /&gt;&lt;br /&gt;memtoy&gt;/c1 show&lt;br /&gt; _____address______ ____length____ ____offset____ prot  share  name&lt;br /&gt;f 0x00007f000ae68000 0x000001000000 0x000000000000  rw- shared  /tmp/zf1&lt;br /&gt;&lt;br /&gt;me:  child still has zf1 mapped&lt;br /&gt;&lt;br /&gt;memtoy&gt;/c1 unmap zf1    # unmap in child&lt;br /&gt;&lt;br /&gt;console:__remove_shared_vm_&lt;wbr&gt;struct:  vma: ffff8803fe5d3170 - mapping-&gt;i_mmap_writable: 0 -&gt; -1&lt;br /&gt;&lt;br /&gt;--------&lt;br /&gt;&lt;br /&gt;So, the file's i_mmap_writable goes negative.  Is this expected?&lt;br /&gt;&lt;br /&gt;If I remap the file, whether or not I restart memtoy, I see that it's&lt;br /&gt;i_mmap_writable has remained negative:&lt;br /&gt;&lt;br /&gt;-------&lt;br /&gt;memtoy&gt;map zf1          # map private [!shared] - no change in i_mmap_writable&lt;br /&gt;&lt;br /&gt;console:__vma_link_file:  vma: ffff8805fd0590b8 - mapping-&gt;i_mmap_writable: -1 -&gt; -1&lt;br /&gt;&lt;br /&gt;memtoy&gt;unmap zf1        # unmap:  no change in i_mmap_writable&lt;br /&gt;&lt;br /&gt;console:__remove_shared_vm_&lt;wbr&gt;struct:  vma: ffff8805fd0590b8 - mapping-&gt;i_mmap_writable: -1 -&gt; -1&lt;br /&gt;&lt;br /&gt;memtoy&gt;map zf1 shared   # mmap shared, again&lt;br /&gt;&lt;br /&gt;console:__vma_link_file:  vma: ffff8805fd0590b8 - mapping-&gt;i_mmap_writable: -1 -&gt; 0&lt;/div&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3541375506196889216?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3541375506196889216/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3541375506196889216&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3541375506196889216'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3541375506196889216'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/patch-fix-mappingwritablymapped.html' title='[PATCH] fix mapping_writably_mapped()'/><author><name>Minchan Kim</name><uri>http://www.blogger.com/profile/12485540816188493984</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://3.bp.blogspot.com/__HVFGzHYaLo/SV17q31gQJI/AAAAAAAAEMk/1-X2dsJyXUM/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-974986437864690920</id><published>2008-12-04T11:05:00.004+09:00</published><updated>2008-12-04T11:31:59.198+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Corruption with O_DIRECT and unaligned user buffers</title><content type='html'>좀 지난 얘기이긴 하지만..&lt;br /&gt;현재 multiple thread의 O_DIRECT의 사용에 문제가 있다.&lt;br /&gt;좀더 정확하게, multiple thread가 page 단위의 unaligned된 user buffer를 사용하게 되면&lt;br /&gt;fork와 엉켜 발생하게 되는 문제이다.&lt;br /&gt;&lt;br /&gt;예를 들어, 2개 이상의 쓰레드중 첫번째 쓰레드는 unaligned buffer의 512 offset부터 4096 byte만큼 데이터를 읽고, 2번째 쓰레드는 그 다음 4096 byte 만큼의 데이터를, 그 다음 쓰레드는 ... 차례데로 이렇게 읽어들이는 쓰레드들이 있다고 가정하자.&lt;br /&gt;&lt;br /&gt;모든 buffer들이 512byte 만큼씩 bias되어 있다.&lt;br /&gt;&lt;br /&gt;다음과 같은 sequence를 고려해보자.&lt;br /&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Thread 1이 get_user_pages를 호출했고 I/O를 issue했다. &lt;/li&gt;&lt;li&gt;Fork가 발생, 해당 페이지를 COW로 mark&lt;/li&gt;&lt;li&gt;Thread 2 get_user_pages 호출, I/O issue. 그러므로 이 mapping은 physical page의 사본을 얻게 된다. &lt;/li&gt;&lt;li&gt;Thread 2가 issue한 I/O complete되고 새로운 데이터는 3에서 얻은 새로운 physical page에 복사&lt;/li&gt;&lt;li&gt;Thread 1이 issue한 I/O complete되고 데이터는 데이터는 old phsyical page에 복사&lt;/li&gt;&lt;/ol&gt;&lt;br /&gt;그래서 결국 페이지의 첫 512byte의 내용은 old data를 갖게 되어 data는 사라지게 된다. -_-;&lt;br /&gt;안전하게 user buffer 주소와 크기를 page boundary를 cross하게 만들지 않는 것이 좋을 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-974986437864690920?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/974986437864690920/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=974986437864690920&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/974986437864690920'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/974986437864690920'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/corruption-with-odirect-and-unaligned.html' title='Corruption with O_DIRECT and unaligned user buffers'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-298002006608134965</id><published>2008-12-03T21:58:00.005+09:00</published><updated>2008-12-03T22:11:57.111+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='눈'/><title type='text'>우리라는 것</title><content type='html'>언젠부터인지 기억이 잘 나지 않는다.&lt;br /&gt;제일 잘했던 것을 제일 못하게 되었다는 사실을 안 것은.&lt;br /&gt;&lt;br /&gt;지금 곱씹어 보면 아마도 그 때부터가 아니었나 싶다.&lt;br /&gt;하지만  더욱 안된 것은 향해가는 곳이 원하는 곳이 아니라는 점이다.&lt;br /&gt;&lt;br /&gt;발걸음 내려놓으면 그만인 것을 구태여 돌아가고 싶지 않은 것도 있지만,&lt;br /&gt;오래전 알게되었던 것들에 대한 두려움때문이기도 하다.&lt;br /&gt;&lt;br /&gt;어느 시간, 어느 곳이 되든 절벽산책의 기분으로...&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-298002006608134965?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/298002006608134965/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=298002006608134965&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/298002006608134965'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/298002006608134965'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/blog-post.html' title='우리라는 것'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5356856378236904057</id><published>2008-12-03T08:09:00.006+09:00</published><updated>2009-03-24T13:18:35.337+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>vmscan: bail out of page reclaim after swap_cluster_max pages</title><content type='html'>11/14일 Rik에 의한 패치이다.&lt;br /&gt;&lt;br /&gt;VM은 가끔 처음 몇번의 priority동안은 inactive page들을 pormotion시키기위해 rotating back하거나 dirty page들을 sync하기 위해 I/O를 submit한다. 이것은 do_try_to_free_pages 함수에서 볼 수 있다. 그러다 결국 더 낮은 priority가 되었을 경우 너무 많은 페이지들을 회수해버리게 되는 것이다.&lt;br /&gt;그래서 필요한 만큼의 페이지 회수를 완료했을 경우, 회수를 bail out하자는 것이다.&lt;br /&gt;이미 이와 같은 생각은 나뿐만이 아닌 많은 사람들이 생각하고 있었다. 문제는 second-chance 알고리즘의 balancing이다.  리눅스의 페이지 회수 정책은 LRU approximation을 사용하고 있기 때문에&lt;br /&gt;page referency의 정확도를 위해 효율적인 체크가 필요하다.&lt;br /&gt;&lt;br /&gt;하지만 이와 같은 패치는 각 zone 별 referency 체크의 불균형을 가져오게 된다.&lt;br /&gt;실제로 Andrew는 이와 같은 시도를 했었고, 문제를 겪었었다. 그래서 결국 그러한 패치는 revert되었었다. 또한 Mel Gorman또한 HugePage에 관한 comment를 주었다.  Mel이 우려하는 것은 그 패치가 lumpy reclaim에 영향을 주어 high-order block의 회수에 영향을 줄 수 있다고 생각하기 때문이다. Lumpy reclaim은 최소한 high-order block의 base 크기만큼의 페이지 회수를 기대하고 있으나 Rik의 패치로 인하여 그렇게 되지 못할 확률이 보다 커졌기 때문이다.  Mel의 테스트 결과에 의하면 테스트의 모든 machine에서 hugepage pool의 resizing을 위한 one-shot attempt은 훨씬 낮은 성공율을 보이고 있었다. 예상했던 결과이다. 하지만 multiple attempt는 결국 성공했고 aggressive한 hugepage pool의 resizing은 한 machine을 제외한 모든 machine에서 더 높은 성공률을 보였다.  Mel은 Rik의 패치에 대해서 몇가지 질문들을 하였다.&lt;br /&gt;&lt;ol&gt;&lt;li&gt;기존에 있는 baleout 루틴은 너무 늦나?? 그럼 삭제되야 하나? 이 루틴도 do_try_to_free_pages 함수안에 있다.&lt;/li&gt;&lt;li&gt;reclaim을 덜하게 되는 것은 결국 page aging을 old하게 만드는 것이다&lt;/li&gt;&lt;/ol&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5356856378236904057?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5356856378236904057/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5356856378236904057&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5356856378236904057'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5356856378236904057'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/vmscan-bail-out-of-page-reclaim-after.html' title='vmscan: bail out of page reclaim after swap_cluster_max pages'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4995527992204095143</id><published>2008-12-01T08:05:00.004+09:00</published><updated>2009-01-03T09:20:03.326+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Skip freeing memory from zones with lots free</title><content type='html'>Rik은 새로운 패치를 submit하였으나 Andrew는 별로 달가워 하지 않는다.&lt;br /&gt;패치의 골자는 어떤 memory zone에서 free memory를 찾기 어려울 경우, 다른 zone으로부터의 과도한 memory free를 피하자는 것이다. 왜냐하면 다른 memory zone으로부터의 pageout I/O는 문제의 zone에서 page를 free하는 것을 느리게 만들기 때문이다.&lt;br /&gt;&lt;br /&gt;이는 이미 kswapd의 balance_pgdat에서 하고 있는 것과 유사하다.&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;     note_zone_scanning_priority(zone, priority);&lt;br /&gt;     /* &lt;br /&gt;      * We put equal pressure on every zone, unless one&lt;br /&gt;      * zone has way too many pages free already.&lt;br /&gt;      */&lt;br /&gt;     if (!zone_watermark_ok(zone, order, 8*zone-&gt;pages_high,&lt;br /&gt;           end_zone, 0))&lt;br /&gt;       nr_reclaimed += shrink_zone(priority, zone, &amp;amp;sc);&lt;br /&gt;     reclaim_state-&gt;reclaimed_slab = 0;&lt;br /&gt;     nr_slab = shrink_slab(sc.nr_scanned, GFP_KERNEL,&lt;br /&gt;           lru_pages);&lt;br /&gt;     nr_reclaimed += reclaim_state-&gt;reclaimed_slab;&lt;br /&gt;&lt;/blockquote&gt;&lt;br /&gt;이 패치에 대해 Peter Zijlstra나 Johannes Weiner는 Ack를 한 상태지만,&lt;br /&gt;마지막 뒷다리를 잡은 것은 역시나 Andrew였다.&lt;br /&gt;&lt;br /&gt;Andrew는 이미 그와 유사한 시도를 2002년도에 이미 했었다.&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;commit 26e4931632352e3c95a61edac22d12ebb72038fe&lt;br /&gt;Author: akpm &lt;akpm&gt;&lt;br /&gt;Date:   Sun Sep 8 19:21:55 2002 +0000&lt;br /&gt;&lt;br /&gt;  [PATCH] refill the inactive list more quickly&lt;br /&gt;&lt;br /&gt;  Fix a problem noticed by Ed Tomlinson: under shifting workloads the&lt;br /&gt;  shrink_zone() logic will refill the inactive load too slowly.&lt;br /&gt;&lt;br /&gt;  Bale out of the zone scan when we've reclaimed enough pages.  Fixes a&lt;br /&gt;  rarely-occurring problem wherein refill_inactive_zone() ends up&lt;br /&gt;  shuffling 100,000 pages and generally goes silly.&lt;br /&gt;&lt;br /&gt;  This needs to be revisited - we should go on and rebalance the lower&lt;br /&gt;  zones even if we reclaimed enough pages from highmem.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Then it was reverted a year or two later:&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;commit 265b2b8cac1774f5f30c88e0ab8d0bcf794ef7b3&lt;br /&gt;Author: akpm &lt;akpm&gt;&lt;br /&gt;Date:   Fri Mar 12 16:23:50 2004 +0000&lt;br /&gt;&lt;br /&gt;  [PATCH] vmscan: zone balancing fix&lt;br /&gt;&lt;br /&gt;  We currently have a problem with the balancing of reclaim between zones: much&lt;br /&gt;  more reclaim happens against highmem than against lowmem.&lt;br /&gt;&lt;br /&gt;  This patch partially fixes this by changing the direct reclaim path so it&lt;br /&gt;  does not bale out of the zone walk after having reclaimed sufficient pages&lt;br /&gt;  from highmem: go on to reclaim from lowmem regardless of how many pages we&lt;br /&gt;  reclaimed from lowmem.&lt;/akpm&gt;&lt;/akpm&gt;&lt;/blockquote&gt;&lt;br /&gt;위의 글에서 보는 것과 같이 그러한 패치는 revert되었다. 왜냐하면 lowmem보다 highmem의 scanning 비율이 커지면서 page reclaiming 쪽의 zone의 scanning 불균형이 온 것이다.&lt;br /&gt;&lt;br /&gt;이에 대해 Rik은 다시 balance_pgdat도 이미 유사한 것을 하고 있고 지금까지 side effect 없이 잘 사용해왔다고 밝히고, Andrew의 패치와는 달리 이것은 baleout이 아니고 "이미 많은 free page를 가지고 있는 zone을 skip"하자는 것이라고 강조했다.&lt;br /&gt;&lt;br /&gt;Andrew는 이에 대해 하지만 Rik의 패치는 kswapd뿐만 아니라 direct reclaim에도 영향을 줄 수 있다고 말하며 bale out과 skip은 유사한 영향을 줄 것이라고 답변했다. 하지만 이번에는 Andrew가 틀렸다. kswapd는 shrink_zone을 direct로 호출하지 shrink_zones을 통하지 않는다. 그러므로 Rik의 패치는 kswapd에는 영향을 주지 않게 된다.&lt;br /&gt;&lt;br /&gt;어쨌든, Rik의 패치가 zone scanning ratio에 문제를 주는 것은 사실이다.&lt;br /&gt;이에 대해, Rik은 각 zone마다 같지 않은 allocation pressure로 인하여 때론 같지 않은 pressure가 바람질할 때도 있다고 반박하고 있다. 일리가 있는 말이다.&lt;br /&gt;lowmem에 대한 allocation요구가 많을 때, highmem에 page를 swapout하는 것은 바람직하지 않다. 또는 numactl로 pinned된 application이 다른 NUMA node에 page를 swapout하게 하는 것은 바람직하지 않다.&lt;br /&gt;&lt;br /&gt;또한 이미 balance_pgdat에서는 그와 같은 scannng imbalance를 만드는 코드가 들어가 있다.&lt;br /&gt;&lt;blockquote&gt;&lt;br /&gt;         if (!zone_watermark_ok(zone, order, zone-&gt;pages_high,&lt;br /&gt;                                             0, 0)) {&lt;br /&gt;                   end_zone = i;&lt;br /&gt;                   break;&lt;br /&gt;         }&lt;/blockquote&gt;&lt;br /&gt;&lt;br /&gt;하지만 양자간의 아직까지 의견일치가 되고 있지 않다.&lt;br /&gt;Rik이 Andrew를 설득시키지 못하는 한 이 패치는 반영되지 않을 것이다.&lt;br /&gt;&lt;br /&gt;Note :&lt;br /&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;Direct reclaim은 zonelkist에 모든 zone의 free page가 zone-&gt;pages_low이하로 떨어지지 않으면 들어가지 않는다. &lt;/li&gt;&lt;li&gt;old kernel git treee : git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/old-2.6-bkcvs.git&lt;/li&gt;&lt;/ol&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4995527992204095143?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4995527992204095143/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4995527992204095143&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4995527992204095143'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4995527992204095143'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/12/skip-freeing-memory-from-zones-with.html' title='Skip freeing memory from zones with lots free'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-912645480467193697</id><published>2008-06-22T12:54:00.003+09:00</published><updated>2009-01-03T09:20:35.707+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Lockess page cache</title><content type='html'>&lt;a target="_top" rel="nofollow" href="http://thread.gmane.org/gmane.linux.kernel/690220"&gt;speculative page references, lockless pagecache, lockless gup&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;리눅스 커널이 2.6으로 오면서 많은 변화가 있었지만 많은 사람들이 O(1) 스케줄러 이외에는 뚜렷이 이렇다할 만한 것을 얘기하고 있지는 않다. 사실 개인적으로 생각하였을 때 더욱 중요한 것들이 많이 있다.  그 중에 하나가 항상 RCU이다.&lt;br /&gt;&lt;br /&gt;RCU와 같은 새로운 Locking 메커니즘이 리눅스 커널에 도입되면서(사실, 2.4때부터 있어왔던 것들이다.) 커널에 많은 부분들이 RCU를 사용하여 scalability와 performance를 동시에 높여왔다. (RCU에 관한 것을 한번 다루고 싶은 데 사실 글로 언급하기가 좀 힘들다. 얼마전 아는 후배에게 RCU에 관하여 LWN에서 두른 기사를 가지고 아주 세심하게 설명하였음에도 불구하고 이해하기를 힘들어 하는 것이 글로써는 더욱 잘 설명할 자신이 없다. -_-).&lt;br /&gt;&lt;br /&gt;하지만 위의 패치를 이해하기 위해서는 RCU에 대한 근본적인 이해가 있어야 한다. (또 정확하게는 몰라도 된다. 위의 패치는 RCU를 사용하기도 했고 사용하지 않기도 했으니..말이 애매모호하지만 Nick Piggin의 논문을 읽어보면 왜 RCU를 사용하지 않았는가를 알 수 있고(물론 RCU 를 이해하지 못하면 아무리 논문을 읽어도 왜 사용하지 않았는가를 이해할 수 없을 것이다) 또 왜 RCU를 사용했는가도 알 수 있을 것이다.&lt;br /&gt;&lt;br /&gt;위의 패치의 내용은 page cache lookup의 read lock을 없애자는 것이다. 리눅스 커널에서 page cache lookup은 매우 빈번한 operation중의 하나이다. 그러므로 이 lock을 없앨 수 있다면 전체 성능에 큰 개선이 될 것이다. 더욱 중요한 것은 현재 사용하는 rwlock, spinlock은 CPU의 scalability에 큰 overhead가 된다는 것이다. 이 부분은 cache snooping과 bouncing으로 인한 문제이다. 그러므로 lock을 없애면 성능에 큰 개선이 될 수 있다.&lt;br /&gt;&lt;br /&gt;그럼 생각해보자. page cache의 lock을 없애기 위해서는 먼저 page cache가 사용하는 radix tree의  lock을 없애야 한다. 그걸 하기 위해서 Nick은 먼저 lockess radix-tree를 만들어 mainline에 반영하였다. 이것이 lockess pagecache 를 하기 위함이었기 때문에 mainline에 반영이 되고나서도 한동안 사용자가 없었다.  lockess radix-tree는 기존의 interface보다 다소 loose한 semantics를 갖게 되었다. 그러므로 이 loose함을 해결하기 위해서는 page cache의 새로운 알고리즘이 필요하게 되었으며 이것이 specualtive page reference이다.&lt;br /&gt;&lt;br /&gt;specualtve page reference는 nick이 처음 논문에 실었던 내용과 거의 유사하지만 다소 변형되었다. No new page reference를 막기 위해서 새로운 page flag를 사용하지 않고 page_freeze_refs 인터페이스를 사용하기로 했다. 이는 이미 알고리즘에서 free page와의 race문제를 해결하기 사용한 인터페이스(get_page_unless_zero)의 특성을 이용한 것이다. 그러므로 굳이 새로운 page flag를 정의할 필요가 없게 되었다.&lt;br /&gt;&lt;br /&gt;이 패치로 인해 앞으로 우리가 눈여겨 봐야 할 것은 새로운 페이지의 할당에 대해서 referece counter를 예측해서는 안된다는 것이다. 그 페이지는 이전에 page cache에 있었다 회수되어 재할당되었을 가능성이 있으며, 그런 페이지는 speculative page reference를 가지고 있을 수 있기 때문이다. 다른 하나는 radix tree의 update 전에 page를 freeze하여 lookup과의 race문제를 해결해야 한다는 것이다. lookup과 같은 reader는 더이상 rwlock에 의존하지 않기 때문에 reader와 writer의 race 문제가 발생할 수 있기 때문이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-912645480467193697?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/912645480467193697/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=912645480467193697&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/912645480467193697'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/912645480467193697'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/06/lockess-page-cache.html' title='Lockess page cache'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3173638986052417249</id><published>2008-05-30T08:48:00.003+09:00</published><updated>2009-01-03T09:20:50.863+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Ramdisk vs Ramfs</title><content type='html'>&lt;a href="http://www.linuxdevices.com/articles/AT4017834659.html"&gt;http://www.linuxdevices.com/articles/AT4017834659.html&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:Arial,Helvetica;font-size:100%;"&gt;A ramdisk (like initrd) is a ram based block device, which means it's a fixed size chunk of memory that can be formatted and mounted like a disk. This means the contents of the ramdisk have to be formatted and prepared with special tools (such as mke2fs and losetup), and like all block devices it requires a filesystem driver to interpret the data at runtime. This also imposes an artificial size limit that either wastes space (if the ramdisk isn't full, the extra memory it takes up still can't be used for anything else) or limits capacity (if the ramdisk fills up but other memory is still free, you can't expand it without reformatting it).&lt;br /&gt;&lt;br /&gt;But ramdisks actually waste even more memory due to caching. Linux is designed to cache all files and directory entries read from or written to block devices, so Linux copies data to and from the ramdisk into the "page cache" (for file data), and the "dentry cache" (for directory entries). The downside of the ramdisk pretending to be a block device is it gets treated like a block device.&lt;br /&gt;&lt;br /&gt;A few years ago, Linus Torvalds had a neat idea: what if Linux's cache could be mounted like a filesystem? Just keep the files in cache and never get rid of them until they're deleted or the system reboots? Linus wrote a tiny wrapper around the cache called "ramfs", and other kernel developers created an improved version called "tmpfs" (which can write the data to swap space, and limit the size of a given mount point so it fills up before consuming all available memory). Initramfs is an instance of tmpfs.&lt;br /&gt;&lt;br /&gt;These ram based filesystems automatically grow or shrink to fit the size of the data they contain. Adding files to a ramfs (or extending existing files) automatically allocates more memory, and deleting or truncating files frees that memory. There's no duplication between block device and cache, because there's no block device. The copy in the cache is the only copy of the data. Best of all, this isn't new code but a new application for the existing Linux caching code, which means it adds almost no size, is very simple, and is based on extremely well tested infrastructure.&lt;br /&gt;&lt;br /&gt;A system using initramfs as its root filesystem doesn't even need a single filesystem driver built into the kernel, because there are no block devices to interpret as filesystems. Just files living in memory.&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3173638986052417249?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3173638986052417249/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3173638986052417249&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3173638986052417249'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3173638986052417249'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/05/ramdisk-vs-ramfs.html' title='Ramdisk vs Ramfs'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7245201708867365245</id><published>2008-05-26T09:43:00.004+09:00</published><updated>2009-01-03T09:21:28.514+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>The big kernel lock strikes again</title><content type='html'>&lt;a href="http://lwn.net/Articles/281938/"&gt;http://lwn.net/Articles/281938/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Yanmin Zhang은 최근 2.6.26-rc1 커널부터 system performance가 약 40%가량 더 나뻐졌다고 보고했다. 그가 한 테스트는 AIM을 이용한 것이며 AIM은 많은 task들을 생성하여 각 task들이 커널의 여러 subsystem에 관련된 작업을 하는 benchmark 툴이다.&lt;br /&gt;&lt;br /&gt;그가 찾은 문제는 generic semaphore였다. 문제를 BKL로 촛점을 맞추는 데는 그리 오랜 시간이 걸리지 않았다. BKL은 몇년전 semaphore로 교체되었었다.&lt;br /&gt;&lt;br /&gt;Ingo Molnar은 새로운 semaphore코드로 구현을 교체하여 해결하는 방식을 제안하였다.&lt;br /&gt;문제는 기존의 semaphore 구현이 너무 공평하다는 것이다. 하지만 이 공평함은 상당히 비싸다.  semaphore를 얻은 쓰레드는 다른 프로세서의 run queue에 있을 수 있으며 게다가 그 쓰레드는 오랫동안 실행권을 얻지 못하여 상당히 cache cold할 것이다. 심지어 그 쓰레드는 굉장히 낮은 priority를 가지고 있어 오랫동안 실행되지 못할 수도 있다. 그 동안 그 semaphore를 기다리고 있는 큐에 저 뒤쪽에 있는 쓰레드들 (즉, 공평성의 관점에서 봤을 때 요청의 시간이 늦어 q-&gt;list의 저 뒤족에 매달려 있는 놈들) 또한 실행권을 얻지 못하는 문제가 발생한다.&lt;br /&gt;&lt;br /&gt;결과적으로 semaphore의 어떤 쓰레드도 실행하지 못하는 dead time이 상당히 늘어난 다는 것이다.&lt;br /&gt;&lt;br /&gt;해결은 기존의 semaphore구현을 빌려오는 것이다. 즉 공평하지 않게 처리하는 것이다.&lt;br /&gt;경쟁을 하여 누가 가져갈지 모른다는 것이다.&lt;br /&gt;&lt;br /&gt;흥미로운 것은 이 패치가 2.6.26-rc2 이전에 mainline에 merge되었다가 다시 revert되었다는 것인데 그 이유는 그 패치가 몇몇 사황에서 semaphore를 broken시켰다는 것이다. 즉 semaphore가 몇몇 상황에서 쓰레드를 깨우는 데 실패하는 경우가 있었던 것이다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Linus는 또 다른 패치를 넣어 이 문제를 해결하였다. BKL을 spinlock을 대체하는 패치였다. 대신에 느려터지지만 공평한 generic semaphore는 그대로 남겨두었다. 하지만 이 패치는 non-preemption구간을 증가시켜 rt guy들에게는 결코 환영받지 못하였다.&lt;br /&gt;&lt;br /&gt;하지만 Linus가 이렇게 패치를 한 이유는 BKL이나 semaphore는 제거되거나 minimization되어야 하는 상당히 낡은 메커니즘이라는 것이다.  그러한 관점에서 더 복잡했던 semaphore 코드를 다시 되돌리자고 하는 노력은 가치가 없다고 판단하였다.&lt;br /&gt;&lt;br /&gt;그래서 이러한 결론은 다시 BKL을 커널에서 제거하고자 하는 사람들에 또다시 격려가 될지도 모른다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7245201708867365245?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7245201708867365245/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7245201708867365245&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7245201708867365245'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7245201708867365245'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/05/big-kernel-lock-strikes-again.html' title='The big kernel lock strikes again'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-3003687850316059283</id><published>2008-05-26T09:33:00.006+09:00</published><updated>2009-01-15T13:18:34.629+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Generic Semaphore</title><content type='html'>&lt;a href="http://lwn.net/Articles/273731/"&gt;http://lwn.net/Articles/273731/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;현재 커널에서 semaphore는 굉장히 optimization이 되어 있고 각 arch에 specific하게 구현되어 있었다. 하지만 Mattew는 arch에 dependent한 semaphore들을 제거하고 하나의 semaphore로 교체하였다.&lt;br /&gt;&lt;br /&gt;구현은 상당히 직관적이고 간단하였다.&lt;br /&gt;&lt;br /&gt;&lt;pre&gt;&lt;blockquote&gt;    struct semaphore {&lt;br /&gt;spinlock_t  lock;&lt;br /&gt;int   count;&lt;br /&gt;struct list_head wait_list;&lt;br /&gt; };&lt;/blockquote&gt;&lt;br /&gt;&lt;/pre&gt;그럼 사람들은 궁금해 할지도 모른다. 왜 애초에 이렇게 하지 않았나?&lt;br /&gt;그에 대한 대답은 2.6.16 이전에는 semaphore가 커널의 주요 mutual exclusion중의 하나였기 때문이다. 그래서 semaphore들은 상당히 performance-critical primitive였던 것이다. 지금은 많은 부분은 mutex로 대체되었기 때문에 semaphore의 비중이 커널에서 기존보다는 많이 줄어들게 되었기 때문이다.&lt;br /&gt;&lt;br /&gt;다른 질문은 왜 아직도 이렇게 많은 semaphore들이 사용되고 있느냐이다.&lt;br /&gt;&lt;br /&gt;2.6.16이후로 많은 semaphore들이 mutex로 교체된 것이 사실이지만 그래도 아직 많은 semaphore들이 남아 있다.  하지만 이렇게 교체하기 위해서는 많은 audit이 필요하다. 이러한 audit이 충분해지면 semaphore의 counting feature가 필요하지 않은 것들은 mutex로 계속해서 교체될 것이며 정말 필요한 것들만으로 semaphore가 남게 될 것이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-3003687850316059283?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/3003687850316059283/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=3003687850316059283&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3003687850316059283'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/3003687850316059283'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/05/generic-semaphore.html' title='Generic Semaphore'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5962311659146310969</id><published>2008-04-23T13:48:00.002+09:00</published><updated>2009-01-03T09:23:32.989+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Toward better direct I/O scalability</title><content type='html'>&lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;a title="http://lwn.net/Articles/275808/" href="http://lwn.net/Articles/275808/"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;http://lwn.net/Articles/275808/&lt;/span&gt;&lt;/a&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;요즘 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;linux-mm&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;쪽에서  &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;nick &lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;아저씨하고 계속해서 얘기가 진행중인 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;topic&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;인데  &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;lwn&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에 보니 정리가 잘 되어 있네요&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;.  &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;요는 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;linux&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;가 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;CPU-intensive&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;한 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;work&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에서 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;scalability&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;가 계속해서 향상되고 있는데 반해  &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;database-heavy workload&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;의 경우에는 그렇지가 못하다는 데서 문제가  시작되었네요&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;. &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;DB&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;와 같은 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;app&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;들은 리눅스의 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;page cache policy&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;를 피하기 위해 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;direct I/O&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;를  사용하게 되고&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;, &lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;그렇게 되면 커널의 입장에서는 읽은 데이터를 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;user&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;의 메모리에 바로 써주어야 하는데 그렇게 하기 위해선 해당 프로세스의 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;page table&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에 먼제 페이지 프레임들을 고정시켜야 합니다&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;.  &lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;그것을 하기 위해서 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;get_user_pages API&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;를 사용해왔고&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;. &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;근데 이 함수를 사용하려면 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;mm&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에 세마포어를 하나 잡고 사용해야 하는데 두개 이상의 프로세스가 경쟁을 하기 시작하면 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;scalability&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;가 확 떨어져 버리는 단점이 생깁니다&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;.  &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;그래서 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;nick&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;이 곰곰히  생각해보니 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;lock&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;을 줄일 수 있는 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;point&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;도 몇몇 있고  페이지 테이블 엔트리의 하위 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;12bit&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;를 사용하여 필요한 정보를 저장하고 그것을 바탕으로 처리를 하니  전체적으로&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; 10%&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;의 성능 향상을 보였다네요&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;.  &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;Anyway, server &lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;단에서 일을 하니 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;DB&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;와 같은  것들에 문제점을 찾게 되고 어떻게 보면 사소할 수도 있지만&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;(lock&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;을 줄여 나가는 것&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;) &lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;또한 특정 상황에서는 도움이 안될 수도 있는 작은 패치일 수도 있지만 조금씩 성능을 개선해나가는 구루의  면모를 볼 수 있습니다&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;.&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;꼬랑지&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;)&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;패치 메일만 받고서는 뭔 내용인지 사실 잘 몰랐는데 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;lwn&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;을 보니 확 이해가 되네요&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;. &lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;역시 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;Jonathan Corbet&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;은 정리의 아버지&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;~~  &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;지난번 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;ticket spinlock(&lt;/span&gt;&lt;a title="http://lwn.net/Articles/267968/" href="http://lwn.net/Articles/267968/"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;http://lwn.net/Articles/267968/&lt;/span&gt;&lt;/a&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;)&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에  대해서도 원저자인 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;nick&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;보다 더 훌륭한 설명을 하여 &lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;nick&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;에게 칭잔을 받은 적도 있는데&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;..  &lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;" lang="EN-US"&gt;&lt;o:p&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt; &lt;/span&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"&gt;&lt;span style="font-family:굴림;"&gt;&lt;span style=" ;font-family:굴림;"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;정리는 이렇게 하는 것이다를 보여주네요&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;..&lt;/span&gt;&lt;/span&gt;&lt;span class="Apple-style-span" style="font-size: medium;"&gt;ㅎㅎ&lt;/span&gt;&lt;span lang="EN-US"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5962311659146310969?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5962311659146310969/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5962311659146310969&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5962311659146310969'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5962311659146310969'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/04/toward-better-direct-io-scalability.html' title='Toward better direct I/O scalability'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4417951711141386058</id><published>2008-03-18T19:19:00.002+09:00</published><updated>2008-03-18T19:29:07.202+09:00</updated><title type='text'>arm linux kernel에 system call 추가</title><content type='html'>기본적으로 뼈대는 x86과 동일하다. 약간의 매크로가 틀릴 뿐인데.. 중요한 것은 제일 나중에..&lt;br /&gt;&lt;br /&gt;먼저 커널의 다음 3 파일을 수정하여 새로운 system call을 추가하자.&lt;br /&gt;&lt;br /&gt;1. arch/arm/kernel/calls.S&lt;br /&gt;2. include/asm-arm/unistd.h&lt;br /&gt;3. 해당 system call을 구현 할 부분(따로 분리해서 구현해도 상관없고 기존의 아무 소스 파일에나 구현해도 상관없다. 단지 makefile만 잘 수정해준다면)&lt;br /&gt;&lt;br /&gt;마지막으로 해당 system call을 사용하는 application을 작성하여야 한다.&lt;br /&gt;&lt;br /&gt;#include "/home/barrios/work/xxx/linux/include/asm-arm/unistd.h"&lt;br /&gt;#include &lt;errno.h&gt;&lt;br /&gt;&lt;br /&gt;_syscall1(int,barrios_write,int,arg);&lt;br /&gt;_syscall1(int,barrios_t,int,arg);&lt;br /&gt;&lt;br /&gt;int main()&lt;br /&gt;{&lt;br /&gt;        int i;&lt;br /&gt;    &lt;br /&gt;        i = barrios_write(2);&lt;br /&gt;        i = barrios_t(2);&lt;br /&gt;    &lt;br /&gt;        return 0;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;자. 컴파일 하자.&lt;br /&gt;&lt;br /&gt;arm_unknown-linux-gnu-gcc -o barrios_syscall barrios_syscall.c &lt;br /&gt;&lt;br /&gt;에러 뜨나??&lt;br /&gt;barrios_syscall.c:5: error: expected declaration specifiers or ‘...’ before ‘barrios_write’&lt;br /&gt;barrios_syscall.c:5: error: expected declaration specifiers or ‘...’ before ‘arg’&lt;br /&gt;barrios_syscall.c:5: warning: data definition has no type or storage class&lt;br /&gt;barrios_syscall.c:6: error: expected declaration specifiers or ‘...’ before ‘barrios_t’&lt;br /&gt;barrios_syscall.c:6: error: expected declaration specifiers or ‘...’ before ‘arg’&lt;br /&gt;barrios_syscall.c:6: warning: data definition has no type or storage class&lt;br /&gt;&lt;br /&gt;그럼 다음과 같이...&lt;br /&gt;&lt;br /&gt;arm_unknown-linux-gnu-gcc -o barrios_syscall barrios_syscall.c &lt;span style="color: rgb(255, 0, 0);"&gt; -D__KERNEL__&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4417951711141386058?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4417951711141386058/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4417951711141386058&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4417951711141386058'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4417951711141386058'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/arm-linux-kernel-system-call.html' title='arm linux kernel에 system call 추가'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6302160450068044599</id><published>2008-03-10T09:24:00.004+09:00</published><updated>2009-01-16T19:42:27.455+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>cache line bouncing에 관하여</title><content type='html'>시스템에 관련된 서적이나 기사들을 보면 cache에 관해서 많은 용어들이 나온다.&lt;br /&gt;cache thrashing, cache line bouncing,  cache snooping, cache invalidation 등등.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;명확한 용어를 사용하지 않는다면 듣는 사람이나 말하는 사람 모두 피곤하기 마련이다.&lt;br /&gt;먼저, 가장 흔히 사용하는 용어는 cache line bouncing 이다.&lt;br /&gt;Cache는 일반적으로 공간 지역성을 최대한 활용하기 위하여 cache line size만큼 한번에 메모리의 데이터를 cache line에 올려 놓게 된다. 현재 Intel의 core2duo와 같은 경우는 이 크기가 64 Byte에 해당한다. &lt;br /&gt;&lt;br /&gt;예를 들어 메모리의 0xC0120800의 한 바이트를 read하였다고 할지라도, cache line size가 64바이트라면 0xc0120800부터 0xc0120840까지 의 데이터를 읽어들이는 셈이된다. SMP환경에서 여러 CPU들이 해당 주소를 읽게 되면 각 CPU이 local cache 안에  같은 메모리 주소의 데이터를 캐시안에 공유하고 있게 된다. &lt;br /&gt;이때, 여러 CPU중 한 CPU가  0xc0120800~0xc0120840의 범위 중 한 바이트라도 변경하게 되면 MESI 프로토콜에 의해 다른 CPU들의 cache line은 invalid되게 된다. 그러므로 다른 CPU들이 그 주소 범위 내의 한 바이트를 읽으려거든 cache miss가 발생하며 memory로부터 다시 읽어와야만 한다.  이러한 것들이 하드웨어적으로 보장이 되며 우리는 Cache Coherency라고 한다. &lt;br /&gt;Cache line bouncing이란 위의 설명과 같이 한 여러 CPU들의 local cache안에 공유되는 메모리 주소를 한 CPU가 변경하여 다른 CPU들의 Local cache도 update해야만 하는 상황을 일컫는다.  일부 사람들은  false sharing이 cache line bouncing이라고 얘기를 하곤 하는데, 그건 아니다.  False sharing은 cache line bouncing을 발생시키는 행동 중의 하나일 뿐이다.  false sharing을 설명하는 글들은 많이 있으니 굳이 설명하지 않는다. 단지 한가지 덧붙인다면 linux kernel의 hot path에서 사용되는 자료구조들은 false sharing을 막기 위해 최대한 자료 구조의 데이터와 그 데이터를 보호하는 Lock은 다른 cache line에 놓이도록 한다.  Cache line bouncing을 제일 많이 일으키는 부분이바로 contention이 심한 데이터에 대한 lock이다.  spin_lock의 test_and_set op는 해당 op를 발생시킨 CPU의 cache안에 해당 주소를 포함하는 cache line을 modify하고 그리고 다른 프로세서들은 자신의 cache안에 있는 데이터 중 방금 수정된 메모리 주소와 관련된 cache line을 소유하고 있는지 감시하게 되는 데.. 이것이 cache snooping이다.  cache snooping을 통해서 다른 CPU의 local cache들이 invalid 모드로 바뀌는 것이다. &lt;br /&gt;일반적으로, cache line bouncing이 굉장히 많이 발생하는 것을 cache thrashing이라고 한다. cache trashing은 SMP,CMP와 같은 멀티 프로세서 구조에서 심각하게 성능을 저하할 수 있으며 그 주범인 spin_lock들을 막기 위해 linux kernel은 RCU와 같은 lock free 알고리즘을 사용하여 점차 변화하고 있다. &lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6302160450068044599?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6302160450068044599/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6302160450068044599&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6302160450068044599'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6302160450068044599'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/cache.html' title='cache line bouncing에 관하여'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-4311218817162649497</id><published>2008-03-09T15:47:00.005+09:00</published><updated>2009-01-14T08:47:55.648+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>Kernel Synchronization에 관하여</title><content type='html'>커널의 동기화 관련함수들이 여럿 있다. &lt;br /&gt;이 함수들을 어느 시점에서 어떤 함수들을 사용하느냐는 사실 숙련된 개발자가 &lt;br /&gt;아니라면 여전히 많이 혼동스러운 부분이며, 굉장히 찾기 어려운 버그를 만들어 내곤한다.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.kernel.org/pub/linux/kernel/people/rusty/kernel-locking/c214.html#MINIMUM-LOCK-REQIREMENTS"&gt;http://www.kernel.org/pub/linux/kernel/people/rusty/kernel-locking/c214.html#MINIMUM-LOCK-REQIREMENTS&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;위의  URL은 Rusty russel이 작성한 문서이며 여러분들이 가지고 있는 커널의 /Documentation/에서도 &lt;br /&gt;구할 수 있는 문서이다. 커널의  locking에 관해서 예제와 함께 상당히 잘 정리된 문서이다.&lt;br /&gt;하지만 기본적으로 동기화 facility들에 대한 개념이 없다면 위의 표가 잘 이해되지 않을 것이다.&lt;br /&gt;&lt;br /&gt;커널에 관심이 많은 개발자라면 이미 softirq와 tasklet에 관해서는 이해하고 있을 것이다. &lt;br /&gt;이미 많은 linux kernel 관련 서적에서 다루고 있으니 굳이 따로 설명하진 않는다.&lt;br /&gt;&lt;br /&gt;위의 표를 이해하기 위해 우리가 알고 있어야 하는 중요한 것이 3 가지 있다.&lt;br /&gt;&lt;br /&gt;1. 인터럽트 핸들러가 실행중일 때 다른 인터럽트 핸들러들이 저절로  block되어 지는 것은 아니다.&lt;br /&gt;(많은 개발자들이 잘못 생각하고 있는 부분이다.  물론 IRQF_DISABLED 플래그를 통해 인터럽트 핸들러를 등록하면 커널은 사용자의 의해 등록된 ISR을 실행할 때 인터럽트 전체를 disable하여 시스템의 모든 인터럽트가 발생하지 않게 해줄 수 있긴하다. 이런 행동은 굉장히 지양해야 하는 행동이지만 제공하긴 한다. 커널의 default 행동은 그렇지 않다는 것이다.)&lt;br /&gt;&lt;br /&gt;2. 한 CPU의 인터럽트가 disable되었다고, 다른 CPU도 disable되지 않는다. 즉 인터럽트 핸들러 A를 실행하지 못하게 하려고 CPU A에서 disable해봐야, 인터럽트 핸들러 A는 CPU B에서 실행될 수도 있다는 것이다. 참고로 하나의 인터럽트 핸들러가 동시에 여러 CPU에서 실행되지 않는 다는 것은 커널이 보장해 준다.&lt;br /&gt;&lt;br /&gt;3. softirq는 다른 softirq를 선점하지 않는 다는 것이다. 이는 softirq를 이용하여 만들어진 tasklet에도 그대로 적용된다. &lt;br /&gt;&lt;br /&gt;4. 부록으로 하나만 더 알고 넘어가자. User context가 무얼까? 커널에 관련된 책이나 자료들을 보다 보면 Interrupt Context, User Context(Process Context)에 관해 가끔 말이 나온다. User context는 실행중인 User 영역의 프로세스를 의미하는 것이 절대 아니다. 여러분들은 구분을 current로 하면 된다. 현재 시점에서 current(current가 무엇인지 모른다면 아직 이 글을 보지 말길 권유한다)가 지금 커널이 행하고 있는 일의 주체인가를 판단하면 된다. 예를 들어 인터럽트가 발생했다고 가정하자. 커널은 인터럽트 처리를 바쁘게 하고 있다. 그 시점에서 current는 누가 될지 모른다. 왜냐하면 인터럽트는 비동기적인 이벤트이기 때문이다. 인터럽트를 유발 시킨 프로세스 B, 또는 커널의 특정 서브 시스템이라고 하더라도 실제 그 인터럽트 처리는 프로세스  C가 실행 중인 시점에서 발생하여 처리를 하게 될지도 모르기 때문이다. 이것은 Interrupt Context이다. &lt;br /&gt; 반면,  User Context는 현재 커널이 프로세스를 대신해서 수행하고 있는 경우이다. 일반적으로 system call(page fault와 같은 exception도 user context로 볼 수 있다. 왜냐하면 이때 커널은 current를 access하기 때문이다)이 이에 속한다.  이 때 프로세스란 user-mode process일 수도 있고  kernel thread일 수도 있다. Anyway, 현재 시점에서의 current는 그 일을 유발한 프로세스를 가리키고 있다는 것이다. 이해가 되었으면 좋겠다. &lt;br /&gt;&lt;br /&gt;이 부분 만큼은 기억하고 있어야만 위의 표를 논리적으로 풀어 나갈 수 있다. (우리가 수학을 배울때도 기본 공식은 외우고 있어야 만 하듯이 위는 기본적으로 우리가 알고 있어야 하는 기본이라고 생각하길 바란다.)&lt;br /&gt;&lt;br /&gt;위의 3가지를 암기하였다면  위의 표를 풀어 나가기 위해서는 두가지 질문을 던져 보면 된다.&lt;br /&gt;&lt;br /&gt;1. A가 B에 의해 선점될 수 있는가?&lt;br /&gt;=&gt; If yes, you should use "[irq/bh] disalbe"&lt;br /&gt;2. A의 critical section이 다른 CPU에 의해 접근될 수 있는가?&lt;br /&gt;=&gt; If yes, you should use "spin_lock".&lt;br /&gt;&lt;br /&gt;자, 위의 법칙을 적용해 보자. (문제를 풀 때는 항상 약한(?) 놈을 A로 하며 당신의 시스템은 무조건 SMP라고 하자.  SMP로 가정하는 것은 중요하다. 리눅스 커널은  general한 OS이다. 당신의 코드가 반드시 UP의 NON-PREMMPTIBLE에서만 실행된다는 보장은 없다. 그러므로 무조건 SMP를 고려해야 한다. )&lt;br /&gt;&lt;br /&gt;예제 1) User Context A, Takelet  B&lt;br /&gt;&lt;br /&gt;1법칙의 답변 )  yes&lt;br /&gt;2법칙의 답변)  yes&lt;br /&gt;&lt;br /&gt;당연하다. user context는 인터럽트에 의해 선점될 수 있다.&lt;br /&gt;인터럽트 종료시 softirq가 실행되고 결국 tasklet이 실행되게 된다. 그러므로 tasklet은 interrupt context에서&lt;br /&gt;동작하며 user context A에게는 일종의 인터럽트로 인한 선점으로 볼수 있다. 그러므로 A는 B에 의해 &lt;br /&gt;선점될 수 있으므로 1법칙의 답변은 yes이다. 그러므로 우리는 bh를 disable해야 한다. (이 경우, 굳이 irq까지 disable할 필요는 없다. 이유는 따로 설명하지 않는다.)&lt;br /&gt;&lt;br /&gt;2법칙의 답변 또한 당연하다.  &lt;br /&gt;A의 코드는 SMP 환경에서 언제나  다른 프로세서의 의해 접근 될 수 있기 때문이다. 그러므로 spin lock을 사용해야 한다.&lt;br /&gt;&lt;br /&gt;위를 종합해보면 결국 우리는 spin_lock_bh를 사용해야 한다는 것이다.&lt;br /&gt;&lt;br /&gt;예제 2) Taklet A, Tasklet B&lt;br /&gt;&lt;br /&gt;1법칙의 답변 )  No&lt;br /&gt;2법칙의 답변)  yes&lt;br /&gt;&lt;br /&gt;2번이 왜 yes인지는 조금만 생각하면  알 수 있다.  tasket은 softirq에 의해 실행된다. softirq는 인터럽트에 의해 실행된다. 인터럽트는 어느 CPU에 의해서나 처리 될 수 있다. 즉, tasklet A가 CPU A에 의해 실행중일 때 CPU B는 tasklet B를 실행시킬 수 있다는 것이다. 그러므로 A와 B 두 tasklet들이 서로 critical section을 가지고 있다면 보호되어야 마땅하다. 만일, 두 tasklet 가운데 공유되는 변수가 없다면 굳이 lock을 사용할 필요는 없어지므로 답이 NO일수도 있다. &lt;br /&gt;&lt;br /&gt;그럼 왜 1은 NO일까? 미리 얘기했듯이 softirq는 선점되지 않는다라고 이미 얘기하였다.&lt;br /&gt;결국 위를 종합해보면 spin_lock만으로 충분하다.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;예제 3) softirq A, Interrupt B&lt;br /&gt;&lt;br /&gt;1법칙의 답변 )  yes&lt;br /&gt;2법칙의 답변)  yes&lt;br /&gt;&lt;br /&gt;이뙈 왜 2법칙의 답변이 yes인지 궁굼할 수도 있을 것이다. 이건 여러분들의 몫.&lt;br /&gt;&lt;br /&gt;예제 4) Interrupt A, Interrupt B&lt;br /&gt;&lt;br /&gt;1법칙의 답변 )  yes&lt;br /&gt;2법칙의 답변)  yes&lt;br /&gt;&lt;br /&gt;하지만 이는 주의가 필요하다. 이때는 spin_lock_irqsave를 사용해야 한다는 것이다.&lt;br /&gt;그 이유는 앞의 예제 3가지는 모두 이미 커널의 디자인 단계에서 irq가 enable되어 있다는 것을 보장하고 있기 때문에 우리는 아무 생각 없이 spin_lock_irq를 사용할 수 있었다. 즉 softirq, tasklet, user context에서는 항상 irq가 enable되도록 커널이 설계되었기 때문에 우리는 아무 생각 없이 spin_lock_irq를 사용하면 됐다는 것이다.&lt;br /&gt;&lt;br /&gt;하지만, 커널의 인터럽트 핸들러가 호출되는 시점은 irq가 enable되어 있을 수도 있고 disable되어 있을 수도 있다.&lt;br /&gt;(이는 인터럽트 핸들러의 등록시 SA_INTERRUPT와 같은 파라미터를 통해 결정되기도 하며, kernel의 interrupt handler들은 nesting될 수 있기 때문이기도 하다. 즉, interrupt handler A가 수행되기 전, 어떤 interrupt handler들이 어떤 순서로 어떤 일을 했을지 모르기 때문이다.) 그러므로 우리는 함부로 spin_lock_irq를 사용할 수 없고 대신, spin_lock_irqsave를 사용하여 interrupt on/off 상태를 기억하고 있어야 한다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-4311218817162649497?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/4311218817162649497/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=4311218817162649497&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4311218817162649497'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/4311218817162649497'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/kernel-synchronization.html' title='Kernel Synchronization에 관하여'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-2286760999664586117</id><published>2008-03-05T10:12:00.002+09:00</published><updated>2008-03-05T10:15:21.408+09:00</updated><title type='text'>wordwrap에 관하여</title><content type='html'>가끔 커널에 패치를 보낼 때 wordwrap기능 때문에 다른 사람들이 나의 패치를 적용하다 fail이 나오는 경우가 종종 있다.&lt;br /&gt;&lt;br /&gt;wordwrap이 무엇인가에 대해서는 다음을 참조하라.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://mwultong.blogspot.com/2007/10/vim-vi-word-wrap.html"&gt;http://mwultong.blogspot.com/2007/10/vim-vi-word-wrap.html&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;이를 막기 위해서는 mail client 프로그램의 wordwrap기능을 disable해야 한다.&lt;br /&gt;또한 주의해야 할 것이 사용하는 편집기, 본인 같은 경우 vim을 사용하는데 편집기에서도 wordwrap기능을 disable해야 한다.하나 더 주의할 것이 복사를 할 때 vim의 윈도우상에서 그대로 copy and paste를 하게 되면 wrodwrap이 되곤한다.  즉, vim의 yy 명령을 사용하여 복사해야 한다. 그러기 싫으면  gedit등을 이용해서 복사하면 된다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-2286760999664586117?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/2286760999664586117/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=2286760999664586117&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2286760999664586117'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/2286760999664586117'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/wordwrap.html' title='wordwrap에 관하여'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8250678252019261780</id><published>2008-03-03T18:46:00.003+09:00</published><updated>2008-12-06T13:43:26.426+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>kerner stack size expansion</title><content type='html'>mainline은 점차 커널 스택 크기를 줄여가고 있는 추세이다. 반면 실무를 하는 회사에서는??&lt;br /&gt;아마도 스택 크기를 늘려달라고 아우성일 것이다.&lt;br /&gt;&lt;br /&gt;문제는 자신들의 드라이버에 있음에도 불구하고 커널의 스택 크기를 늘려 해결하려는 것이다.&lt;br /&gt;개발하다보면 가끔(?) 그런 일들에 부딪히곤 한다.&lt;br /&gt;&lt;br /&gt;하지만 사실, 그 어디에서도 커널 스택 크기를 늘리면 왜 안되는지에 대한 이유는 나와 있지 않다. 그냥 다들 그러지 말라고말 할 뿐이지..&lt;br /&gt;&lt;br /&gt;생각해보면 이것도 커널 메모리하고 밀접한 관련이 있음을 알 수 있다.&lt;br /&gt;일반적으로 user process들이 사용하는 메모리는 4K page이다.&lt;br /&gt;리눅스 커널에서 가장 많이 쓰이는 페이지도 바로 이 4K page이다.&lt;br /&gt;그래서 리눅스 커널은 나름 4K page들의 캐싱에 신경을 써놨고 할당 전략들은 4K page 할당에 많은 신경을 써 놓았다. 그런데 문제는 커널 스택이다.&lt;br /&gt;&lt;br /&gt;커널 스택은 x86을 제외하곤(4K) 내가 아는 architecture는 다 8K이다. 8K 할당은 메모리가 충분하면 문제 없지만 최대한 메모리를 모두 써버리는(?) 리눅스의 페이지 캐시 전략에서는 언젠가 메모리는 회수되기 시작할 것이다.&lt;br /&gt;&lt;br /&gt;문제는 이 때 발생한다. order가 큰 메모리 요청일 수록 회수 알고리즘은 잘 동작하지 못한다.&lt;br /&gt;그나마 최근 lumpy reclaim으로 인해 좀 나아지긴 했지만, 4K 만 못한 것이 사실이다.&lt;br /&gt;&lt;br /&gt;그래서 커널 스택을 4K로 줄이면 줄였지 8K 이상으로 확장하려는 생각은 별로 하지 않는 것이 좋다. OOM killer를 만나보고 싶지 않다면~~&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8250678252019261780?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8250678252019261780/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8250678252019261780&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8250678252019261780'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8250678252019261780'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/kerner-stack-size-expansion.html' title='kerner stack size expansion'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8876538137296123768</id><published>2008-03-03T09:54:00.004+09:00</published><updated>2009-01-03T09:28:43.690+09:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='linux kernel'/><title type='text'>KGDB가 merge될 것 같다</title><content type='html'>&lt;a href="http://lwn.net/Articles/270089/"&gt;http://lwn.net/Articles/270089/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Linus가 그렇게 싫어하던 KGDB가 Ingo Molnar의 각고의 노력으로 2.6.26 쯤에 merge될 것 같다.&lt;br /&gt;사실 Linus는 개발자들이 디버깅 툴을 쓰는 것을 좋아하지 않는다.  사람을 생각하지 않게 만들기 때문이다. 하지만 요즘은 생각이 약간 변한 듯 하다.&lt;br /&gt;어쨌든 많은 개발자들은 반기는 기색이다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8876538137296123768?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8876538137296123768/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8876538137296123768&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8876538137296123768'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8876538137296123768'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/03/kgdb-merge.html' title='KGDB가 merge될 것 같다'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-8065903805601253986</id><published>2008-02-27T08:21:00.002+09:00</published><updated>2008-02-27T08:38:46.657+09:00</updated><title type='text'>리눅스 커널 번역 프로젝트</title><content type='html'>&lt;a href="http://wiki.kldp.org/wiki.php/LinuxKernelDocEn2Kr"&gt;리눅스 커널 번역 프로젝트&lt;/a&gt;  페이지를 만들었습니다.&lt;br /&gt;&lt;br /&gt; 작년 7월 일본과 중국의 번역문서들이 mainline에서 토론되어지기 시작하는 것을 보고 바로 시작하였다.  하지만 일이나 부족한 번역실력으로 한 문서를 submit하기까지는 많은 시간이 걸리고 있는 실정이다. 뿐만 아니라 보다 중요한 것은 이미 일본이나 중국은 굉장히 활발하게 활동하는 리눅스 커널 로컬 커뮤니티를 가지고 있다는 것이다.&lt;br /&gt; 우리나라에도 많은 커널개발자가 있다고 생각한다. 하지만 mainline을 보면 정말 몇 안되는 분들만이 활동을 하고 있는 것이 오픈소스에 대한 우리나라의 리눅스 커널 개발에 대한 실정이다. 반면, 일본은 근래들어 점차 많은 사람들이 mainline에서 활동을 하고 있으며 중국은 이미 꽤 많이 눈에 띄었었다. 이렇게 할 수 있는 가장 큰 힘은 각국의 로컬 커뮤니티라고 생각한다. 우리나라에도 많은 커널 개발자들이 있고 지역적인 커뮤니티 또는 학생들의 스터디 그룹이 있는 것으로 알고 있지만 국내를 대표할만한 리눅스 커널 커뮤니티가 없는 실정이다.&lt;br /&gt; 나는 리눅스 커널 번역 프로젝트가 활성화되어 많은 국내 리눅스 커널 개발자들이 의견을 교환하고 새로운 지식을 공유하며 나아가서 오픈 소스 리눅스 커널 mainline에서의 많은 국내 리눅스 커널 개발자들의 활동을 통하여 한국의 위상을 높였으면 한다.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-8065903805601253986?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/8065903805601253986/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=8065903805601253986&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8065903805601253986'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/8065903805601253986'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/02/blog-post_27.html' title='리눅스 커널 번역 프로젝트'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-7273949319325532402</id><published>2008-02-22T19:20:00.001+09:00</published><updated>2008-02-22T19:21:46.920+09:00</updated><title type='text'>stack back trace for arm</title><content type='html'>예전에 작성한 arm backtrace에 관한 간단한 문서이다.&lt;br /&gt;&lt;br /&gt;         &lt;blockquote&gt;다음과 같은 테스트 프로그램을 만들어보자.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table class="zeroBorder" classname="zeroBorder" id="omts" border="0" cellpadding="3" cellspacing="0" width="100%"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;     #include &lt;execinfo.h&gt;&lt;br /&gt;     #include &lt;stdio.h&gt;&lt;br /&gt;     #include &lt;stdlib.h&gt;&lt;br /&gt;                                            &lt;br /&gt;     void trace (void)&lt;br /&gt;     {  &lt;br /&gt;       void *array[2]; int size;&lt;br /&gt;       size = backtrace (array, 2);&lt;br /&gt;     }  &lt;br /&gt;        &lt;br /&gt;     void  dummy_function (void)&lt;br /&gt;     {  &lt;br /&gt;        trace ();&lt;br /&gt;     }  &lt;br /&gt;        &lt;br /&gt;     int main (void)&lt;br /&gt;     {  &lt;br /&gt;       dummy_function ();&lt;br /&gt;       return 0;&lt;br /&gt;     }  &lt;br /&gt;&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;위의 프로그램을 컴파일 한후 역어셈 해보자. (동적 라이브러리 함수 호출과정의 설명을 생략하기 위하여 static으로 컴파일하였다.)&lt;br /&gt;&lt;br /&gt;arm_xxx-gcc -o trace main.c -static&lt;br /&gt;arm_xxx-objdump -D trace &gt; trace.dis&lt;br /&gt;&lt;br /&gt;trace.dis 파일을 보면 다음과 같이 trace 함수의 역어셈 결과를 볼 수 있다.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table class="zeroBorder" classname="zeroBorder" id="ipce" border="0" cellpadding="3" cellspacing="0" width="100%"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;   119 00008218 &lt;trace&gt;:&lt;br /&gt;   120     8218:   e1a0c00d    mov ip, sp&lt;br /&gt;   121     821c:   e92dd800    stmdb   sp!, {fp, ip, lr, pc}&lt;br /&gt;   122     8220:   e24cb004    sub fp, ip, #4  ; 0x4&lt;br /&gt;   123     8224:   e24dd00c    sub sp, sp, #12 ; 0xc&lt;br /&gt;   124     8228:   e24b3018    sub r3, fp, #24 ; 0x18&lt;br /&gt;   125     822c:   e1a00003    mov r0, r3&lt;br /&gt;   126     8230:   e3a01002    mov r1, #2  ; 0x2&lt;br /&gt;   127     8234:   eb001d28    bl  f6dc &lt;__backtrace&gt;&lt;br /&gt;   128     8238:   e1a03000    mov r3, r0&lt;br /&gt;   129     823c:   e50b3010    str r3, [fp, #-16]&lt;br /&gt;   130     8240:   e24bd00c    sub sp, fp, #12 ; 0xc&lt;br /&gt;   131     8244:   e89da800    ldmia   sp, {fp, sp, pc}&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;여느 함수와 마찬가지로 스택 프레임을 만드는 코드는 같다.  - 120 ~ 122&lt;br /&gt;지역 변수를 위해 12바이트 공간을 할당하였다. - 123&lt;br /&gt;r0에 array 배열을 위한 첫 주소를 지정한다 - 124 ~ 125&lt;br /&gt;r1에 2를 지정하여 __backtrace 함수를 호출하기 전 인수를 모두 지정한다. - 126&lt;br /&gt;브랜치&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;table class="zeroBorder" classname="zeroBorder" id="ru91" border="0" cellpadding="3" cellspacing="0" width="100%"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td width="100%"&gt;  7899 0000f6dc &lt;__backtrace&gt;:&lt;br /&gt;  7900     f6dc:   e1a0c00d    mov ip, sp&lt;br /&gt;  7901     f6e0:   e92dd810    stmdb   sp!, {r4, fp, ip, lr, pc}&lt;br /&gt;  7902     f6e4:   e24cb004    sub fp, ip, #4  ; 0x4&lt;br /&gt;  7903     f6e8:   e24dd004    sub sp, sp, #4  ; 0x4&lt;br /&gt;  7904     f6ec:   e1a0c000    mov ip, r0&lt;br /&gt;  7905     f6f0:   e3a00000    mov r0, #0  ; 0x0&lt;br /&gt;  7906     f6f4:   e24b4011    sub r4, fp, #17 ; 0x11&lt;br /&gt;  7907     f6f8:   e24b200c    sub r2, fp, #12 ; 0xc&lt;br /&gt;  7908     f6fc:   e1500001    cmp r0, r1&lt;br /&gt;  7909     f700:   a91ba810    ldmgedb fp, {r4, fp, sp, pc}&lt;br /&gt;  7910     f704:   e59fe030    ldr lr, [pc, #48]   ; f73c &lt;.text+0x766c&gt;&lt;br /&gt;  7911     f708:   e1520004    cmp r2, r4&lt;br /&gt;  7912     f70c:   391ba810    ldmccdb fp, {r4, fp, sp, pc}&lt;br /&gt;  7913     f710:   e59e3000    ldr r3, [lr]&lt;br /&gt;  7914     f714:   e1520003    cmp r2, r3&lt;br /&gt;  7915     f718:   291ba810    ldmcsdb fp, {r4, fp, sp, pc}&lt;br /&gt;  7916     f71c:   e5923008    ldr r3, [r2, #8]&lt;br /&gt;  7917     f720:   e78c3100    str r3, [ip, r0, lsl #2]&lt;br /&gt;  7918     f724:   e2800001    add r0, r0, #1  ; 0x1&lt;br /&gt;  7919     f728:   e5923000    ldr r3, [r2]&lt;br /&gt;  7920     f72c:   e243200c    sub r2, r3, #12 ; 0xc&lt;br /&gt;  7921     f730:   e1500001    cmp r0, r1&lt;br /&gt;  7922     f734:   a91ba810    ldmgedb fp, {r4, fp, sp, pc}&lt;br /&gt;  7923     f738:   eafffff2    b   f708 &lt;__backtrace+0x2c&gt;&lt;br /&gt;  7924     f73c:   00069828    andeq   r9, r6, r8, lsr #16&lt;br /&gt;&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;/div&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;backtrace 함수는 일반 함수와는 약간 달리 r4 레지스터를 stack에 추가로 보관한다. - 7901&lt;/li&gt;&lt;li&gt;지역변수를 위한 공간은 4byte 할당한다. - 7903&lt;/li&gt;&lt;li&gt;trace함수가 인수로 넘겨준 array의 주소를 ip 레지스터에 저장한다. - 7904&lt;/li&gt;&lt;li&gt;r0레지스터에는 0을 지정한다. 루프의 counter로 사용될 것이다. - 7905&lt;/li&gt;&lt;li&gt;r4레지스터에 fp - 17의 값을 저장한다. 이것은 현재 스택 프레임보다 1 바이트 더 내려간 값으로 비교를 위해 사용된다. - 7906&lt;/li&gt;&lt;li&gt;r2레지스터에 saved fp의 주소를 지정한다. - 7907&lt;/li&gt;&lt;li&gt;r0과 r1을 비교하여, 즉 counter 값이 trace에서 넘겨준 counter값보다 같거나 크다면 정리하고 함수를 빠져 pop한다. - 7908 ~ 7909&lt;/li&gt;&lt;li&gt;lr레지스터에 69828 값을 저장한다. 현재 pc는 0xf70c이다.여기에 48을 더하면 0xf73c이며 그곳에는 69828값이 들어 있다.  - 7910&lt;/li&gt;&lt;li&gt;r2와 r4를 비교한 후 r2가 r4보다 작다면 pop한다. - 7911~7912&lt;/li&gt;&lt;li&gt;lr 을 저장되어 있는 주소에 있는 값을 가져와 r3에 저장한다. 이 주소는 69828이다. 69828의 주소는 __libc_stack_end의 라벨이 되어 있으며 image에는 0x0 값이 들어가 있지만 실행시에는 어떤 값으로 채워질 것이며(누가 채워줄까??) 이 값이 __libc_stack_end 값이 될 것이다. - 7913&lt;/li&gt;&lt;li&gt;r2의 saved fp의 주소가 __libc_stack_end의 값보다 같거나 더 크다면 pop한다. - 7914 ~ 7915&lt;/li&gt;&lt;li&gt;saved lr의 값을 r3레지스터에 저장한다. - 7916&lt;/li&gt;&lt;li&gt;인수로 넘어온 arrary의 주소 * count * 4의 주소에 r3 값을 저장한다. 즉 return address를 인수의 array에 저장하는 것이다. - 7917&lt;/li&gt;&lt;li&gt;counter를 1 증가시킨다. - 7918&lt;/li&gt;&lt;li&gt;saved fp에 있는 값을 r3에 저장한다. 즉 이전 스택 프레임의 주소를 r3에 저장하는 것이다. - 7919&lt;/li&gt;&lt;li&gt;마찬가지로 r3에서 12를 빼서 이전 스택 프레임의 saved fp의 주소의 값을 r2에 저장한다. - 7920&lt;/li&gt;&lt;li&gt;counter의 값이 인수로 넘어온 counter값보다 크지 않다면 9번으로 돌아간다. 그렇지 않으면 pop한다.&lt;br /&gt;&lt;/li&gt;&lt;/ol&gt; &lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-7273949319325532402?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/7273949319325532402/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=7273949319325532402&amp;isPopup=true' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7273949319325532402'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/7273949319325532402'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/02/stack-back-trace-for-arm.html' title='stack back trace for arm'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-5586759421239414505</id><published>2008-02-22T11:13:00.003+09:00</published><updated>2008-02-22T11:17:57.818+09:00</updated><title type='text'>nopfn</title><content type='html'>&lt;a href="http://lwn.net/Articles/242625/"&gt;http://lwn.net/Articles/242625/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;populate, nopage, nopfn이 fault 메소드로 통합된지 오래다.&lt;br /&gt;사실 예전부터 nopfn을 언제 써야하는지 궁금했었다. 좋은 기사에 정확한 설명이 있어 덧붙인다.&lt;br /&gt;&lt;a href="http://lwn.net/Articles/200213/"&gt;&lt;br /&gt;http://lwn.net/Articles/200213/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;  Meanwhile, one of the longstanding limitations of &lt;tt&gt;nopage()&lt;/tt&gt; is that it can only handle situations where the relevant physical memory has a corresponding &lt;tt&gt;struct page&lt;/tt&gt;.  Those structures exist for main memory, but they do not exist when the memory is, for example, on a peripheral device and mapped into a PCI I/O memory region.  Some architectures also do very strange things with special memory and multiple views of the same memory.  In such cases, drivers must explicitly map the memory into user space with &lt;tt&gt;remap_pfn_range()&lt;/tt&gt; instead of using &lt;tt&gt;nopage()&lt;/tt&gt;.&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-5586759421239414505?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/5586759421239414505/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=5586759421239414505&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5586759421239414505'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/5586759421239414505'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/02/httplwn.html' title='nopfn'/><author><name>barrios</name><uri>http://www.blogger.com/profile/17430525060458411817</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='23' height='32' src='http://2.bp.blogspot.com/_x1T3vyNglZo/SWWP4MCyNDI/AAAAAAAAAG0/5rE5tfzVu3o/S220/zaemong.JPG'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-1518098013643077976.post-6283987279220434053</id><published>2008-02-18T12:23:00.003+09:00</published><updated>2008-02-19T15:37:15.411+09:00</updated><title type='text'>Memory Controller background reclaim</title><content type='html'>&lt;a href="https://lists.linux-foundation.org/pipermail/containers/2007-October/008122.html"&gt;https://lists.linux-foundation.org/pipermail/containers/2007-October/008122.html&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;valinux의 YAMAMOTO Takashi의 패치이다.&lt;br /&gt;&lt;br /&gt;background reclaim 정책을 두어 굉장한 성능 향상을 한 것을 알 수 있다. 물론 위의 테스트는 SMP였을 것이라 생각된다. 하지만 UP에서도 어느 정도의 향상이 있을 것으로 보인다.&lt;br /&gt;&lt;br /&gt;Memory Controller에 대한 얘기는 다음을 참조하라.&lt;br /&gt;&lt;a href="http://lwn.net/Articles/243795/"&gt;http://lwn.net/Articles/243795/&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/1518098013643077976-6283987279220434053?l=barriosstory.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://barriosstory.blogspot.com/feeds/6283987279220434053/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=1518098013643077976&amp;postID=6283987279220434053&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6283987279220434053'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/1518098013643077976/posts/default/6283987279220434053'/><link rel='alternate' type='text/html' href='http://barriosstory.blogspot.com/2008/02/memory-controll
