Collapsing Huge Pages & Swap In/Out

Last week, I focused on collapsing huge pages and swap in/out. Rik  have asked me some questions and I countinue to reply them. When we study, he puts some hints to questions and sometimes, I back to old questions and try to understand them better. I've started to follow linux-mm list and understand what they mention about at least :). Before I've tried to follow some staging lists but see emails a lot* everyday.

My project includes very small coding according to other kernel internship projects but the topic is too complex and its about core functionality of Linux Kernel. That's really good :). Before the internship, I was thinking "I should pick a small staging driver and study for todo issues". Because with small driver, learning and to be part of Linux Kernel can be easier and I was going to do just self study, also work at another company so have not enough time. Todays, I study on almost hardest topic with a Linux Kernel developer!

I can start coding for my project but need to discuss which policy we will follow to get swapped out pages to memory. We should discuss about trade off to collapsing pages in a 2 mb page when getting them from swap to memory. Keeping in mind the functions is a bit hard for me, I re-look a lot of time to which function what does. My memory is not good :(.

I've replied following questions which are asked me by my mentor. When I reply the questions, don't need to search just from books, look to codes and understand a bit of them :).

Following call chains for Linux Kernel - 3.18

1) How is a page swapped out?


                if (split_huge_page_to_list(page, list))

Swapped out is implemented by add_swap_page(). The function allocates swap space for a page. Swap areas includes slots, and their size are equals to page frames.

It checks whether page up to date and locked then gets swap page, get_swap_page() firstly checks is there a swap page with atomic_long_read(&nr_swap_pages) if so, decrements nr_swap_pages by one. In there used highhest_bit to decrease searching time of free slot. get_swap_page() returns type swap_entry_t. add_swap_page(), cheks whether the page is huge, if so; it splits the huge page to list with

split_huge_page_to_list(page, list).  The function calls __split_huge_page() -> __split_huge_page_map().

If split_huge_page_to_list() returns 0, that means splitted pages succesfully. After that it adds the page entry to swap cache. If huge page can not splitted then called swapcache_free(entry), to release retrieved swap page.

Note: I did not understand why we set page as dirty? at line:202. The page is not changed. Rik's answer: After the page is added to the swap, it is removed from the process page tables.

Then we have a page that is only in the page cache, and not mapped in any process. The dirty bit indicates the data has to be saved to swap before the page can be freed.

scan_swap_map() is used to find free swap slot.

2) Where is the information of where a page is in swap, stored in the data structures used to track the memory of a process?  In other words, how does swap in find where in swap memory is?

Using swap_info_struct swap_info[] array, it includes indexes of ptes and also offsets are stored in swap_map.

3) How is a page swapped in?

        if (!page)

        else if (PageHWPoison(page)) {...}

It calls pte_to_swp_entry(), pte is converted to swap entry. the function converts pte to architecture independent entry format. Then checks validation of entry with non_swap_entry(). Sets DELAYACCT_PF_SWAPIN flag to spcefiy that does in swap operation. It checks whether the page in swap cache. If so, checks HWPoison flag which is for recovering memory errors; if not runs swapin_readahead() to get probably needs to swap in pages. If HWPoison is setted, it goes to label out_release and release the page and swap cache page from page cache. I've a question here: if the page was huge, but right now it is not because splitted to locate on swap. The page have no compound flag anymore? Is that correct?

Rik's answer: Swap only ever stores single pages, indeed. That means swapped
in pages will not have the compound flag set page_cache_release() calls put_page(), and the function checks using PageCompound().

Note: do_swap_page() gets two pte argument. orig_pte is created by handle_mm_fault() using ACCESS_ONCE(). The macro is for volatile issues maybe but I didn't understand why second pte is created.

Answer: do_swap_page gets both the location of the pte (a pointer) and the value of the pte at handle_mm_fault time. This way it can verify whether the pte changed from its original value, while it is doing things (like retrieving data from swap)

4) How can you discover whether a page is present in the swap cache?

_PAGE_FILE detects whether the page in swap cache, it is into page table entry.

5) Under what conditions are 4kB pages collapsed into a 2MB THP?

In handle_pte_fault(), at line: 3219 do_swap_page() is called because system want to swapped in pages, so it wants to collapse the pages but it can't. This happens, if the cases occur: pte shouldn't be on memory and swap cache. Also pte should be belong to anonymous page, not to file.

Rik's question: Can you write down the call traces that contain the collapse functions in mm/huge_memory.c?
My answer, there are two cases for it:
do_huge_pmd_anonymous_page() -> alloc_hugepage_vma() -> .. __alloc_pages_nodemask()

khugepaged_scan_pmd() -> collapse_huge_page() -> khugepaged_alloc_page() -> alloc_pages_exact_node() -> .. -> __alloc_pages_nodemask()

Rik's answer: Firt call chain, you can leave alone during your project, and is important to understand what the data structures look like.

Second call chain: This is the one you will want to work with.

6) how many pages would be good to bring into swap when trying to collapse a huge page? how many is too much?

x86 systems use 4kB page size. It can be enlarged maximum 4mb. With 2mb page, it is enlarged 512 times, thats good. 4mb page means 1024 times enlarged, it is not so good, if size is more than 4mb huge page, it will be useless.

Rik's answer: Sure, but if all of them are swapped out, it is obviously a bad
idea to bring them all into memory just to collapse them into a 2MB THP.

Out of the 512 pages, what would be a reasonable number to not be in memory already, and bring in from swap? 1? 5? 10? 20? What would the number depend on?

My answer: do_swap_page() ->  swapin_readahead() -> swapin_nr_pages()

In swapin_nr_pages(), using page_cluster it detects how many pages getting swap in.

page_cluster defined in swap.c. swap_setup() function assigns its default value.

7) what about pages that are already in the swap cache? how should we count those?

For this question, I'm a bit confused, thought swap cache is a swap slot .. and replied different thing :). Firstly, I've tried to count how many pages in swap, afterwards go ahead to correct intent.

If a page in the swap cache, that means the page up to date on memory. Also the page is on the one swap slot. Swap cache size is equal to a swap slot. struct swap_info_struct, it has array swap_map.

I've read from book, swap_duplicate() increases slot usagecounter, probably it mentions about the line:

count = p->swap_map[offset];

I've seen on comment line of the function "increment its swap map count." So I guess, swap_map count can be slot usage counter. But I know swap_info struct per swap area not per swap slot. A swap area can include set of slots, so I think, swap_map count doesn't mean swap cache usage counter. Did I misunderstand? Can you inform me about swap_map?

Rik's answer: The swap_map counter means the number of users of that swap slot, which may be different from the number of users of the swap cache page.

However, this line of research is tangential to your project, and your interpretation of question 2 differs from my intent.

My answer: I've thought, when a page will be added to swap cache, it increases count of swap cache page.

add_to_swap_cache() -> __add_to_swap_cache()

In __add_to_swap_cache(), after adding radix tree, it increases the counter at line 104:

nrpages specify total number of pages in address_space which stores swap cache address that means how many pages are in swap cache.

8) what about the !pte_write test in __collapse_huge_page_isolate? how can that break collapsing of a THP? is there a simple way to improve that?

pte_present() checks whether the entry have write access. It needs to create a page using page table entry with vm_normal_page(). If write access is disallowed, can't create page.

My mentor said __collapse_huge_page_isolate() is important point your project, and I've reviewed it:

        for (_pte = pte; _pte < pte+HPAGE_PMD_NR; _pte++, address += PAGE_SIZE) {
                !pte_present() || !pte_write()

For loop:
Firstly, it checks pte_none(), this function returns true if pte is not in Ram. There is a counter none, checks with none for allowed khugepaged_max_ptes_none. If exceeds the limit then goes to label out. pte_none() returns true if none of the bits in the pte are set, that is the pte is all zeroes. pte_present() also is used for page swapped out. pte_write() checks whether the kernel write to page. Then checks is the page compound, if so does system halt. If page is not anon nor swap backed then does system halt. The page should have only one reference, this property checked by _count variable. Then it locks the page.

I'm looking isolate_lru_page(), Lru list includes inactive file/page, active file/page. But I didn't understand why there is PG_lru flag and we check it with PageLRU(page) at line 1344, vmscan.c

Rik's answer: If the page is not currently on an LRU, a different task may have that page on a pagevec, and do something with it later. That could race with trying to collapse the hugepage, and cause all sorts of problems.

In isolate_lru_page(), it checks again VM_BUG_ONE(!page_count(page), page), but already it checked for page_count() before calling isolate_lru_page() line at: 2171. Why it does this again?

Rik's answer: The page_count check is debugging code, in case somebody changes the kernel and calls isolate_lru_page on a page that got freed. It checks PageLRU once outside the lock (it can be changed by another CPU), and once inside the lock (taking a lock is expensive, and only done conditionally).

And also it checks PageLRU two times, in isolate_lru_page(). It gets lruvec then runs page_lru(), which checks page unevictable, if so sets lru as unevictable; if not, calls page_lru_base_type(), this decides base type for page - file or anon after adds active property and returns lru. Then isolate function runs get_page(), if page head or normal, increments _count. Then clear page lru and calls del_page_from_lru_list(), this function deletes lru from page using list_del()

It checks for page young conditions, then set referenced as 1. If it goes to label out, it runs release_pte_pages().

Note: That function gets a pointer to the start of a page table page, and iterates over all the ptes inside that page table page. A 2MB THP contains 512 4kB pages, which is 1<<HPAGE_PMD_ORDER pages.

31 Aralık 2014

Posted In: collapse huge page, Gezegen, kernel, linux, opw, swap in, swap out

Socks Vekil Sunucu (Proxy) ile Git Kullanımı

Öncelikle yazımdaki araya sıkışıp kalan İngilizce kısımlar için anlayış göstereceğinizi umarak başlamak istiyorum.  Bu yazımda, socks vekil sunucu kullanarak uzaktaki bir git sunucusuna (ssh protokolünü kullanarak) bağlanmak için izlediğim birkaç küçük adımı paylaşmak istiyorum.

Gelelim asıl konumuza. Vekil sunucu olarak “ssh-tunneling” [2] yardımıyla kendi yerel makinamı kullanmaktayım ve hedef git sunucu olarak’u ele almak istiyorum. İnternette `git clone` şeklinde gördüğümüz ifadeler sadece ssh protokolünün kısa yazımıdır ve `ssh://` ifadesi ile aynı anlama gelmektedir [1].

Örnek olarak aldığımız adresi için ~/.ssh/config dosyasına birkaç ekleme yapmamız gerekiyor. Kendi kullanıcı dizininizde bu dosya mevcut değilse oluşturup düzenlemeye devam edebilirsiniz. ~/.ssh/config dosyasına aşağıdakine benzer şekilde eklemelerinizi yapabilirsiniz.

    User                    git
    ProxyCommand            nc -x localhost:1080 %h %p

İlk olarak burada kullandığımız `nc` (netcat) aracı sisteminizde yoksa bunu kurmanız gerekmekte. Kendi sistemim Debian olduğundan dolayı aşağıdaki komutla bu paketi kuruyorum.

apt-get install netcat-openbsd

Daha sonra, Host ile belirttiğimiz alana git sunucumuzun adresini giriyoruz ( yerine kendi sunucumuz olabilir). User alanı ise git sunucusu üzerinde size açılan kullanıcı adı olacaktır. ProxyCommand bağlantı sırasında vekil sunucumuzu kullanmamızı yarayacak temel alanımızdır. `-x` parametresi ile vekil sunucu adresimizi ve port numarasını belirttikten sonra `%h` ile hedef adresimizi (git sunucumuzu) ve `%p` hedef portumuzu belirtmiş oluyoruz.


Port 444

alanı ile öntanımlı 22 yerine başka bir port kullanmamız (444 gibi) mümkün. Parola yerine ortak anahtar kullanarak giriş yapmak istiyorsak aşağıdaki eklemeyi (github.key yerine tabi ki kendi ortak anahtar dosyamızı belirterek) yaparak bu sorunu da halletmemiz mümkün.

IdentityFile ~/.ssh/github.key

Tüm bu adımlardan sonra uzaktaki git sunucumuza vekil sunucumuz üzerinden bağlanmaya hazırız. Yazının başında belirttiğim gibi bu adımlar ssh ile yapılan bağantıları kapsamaktadır. HTTP(S) için [3] adresindeki bilgilere göz atmanızı öneririm. Yazımın işinize yaraması dileğiyle.




Tagged: lkd

31 Aralık 2014

Posted In: lkd

AB 15 Java 101 Kursu

Her yıl farklı bir üniversitede gerçekleşen Akademik Bilişim etkinliğine bu yıl Eskişehir Anadolu Üniversitesi ev sahipliği yapıyor. Etkinlik 31 Ocak – 6 Şubat tarihleri arasında düzenlenecek. Konferans öncesi kurslar ise 31 Ocak – 3 Şubat arasında…

Bu yıl Akademik Bilişim’de Java 101 başlıklı Java’ya başlangıç yapmak isteyenler için kurs vereceğim. Katılım tamamen ücretsizdir. Katılımcılar isterlerse KYK’da konaklayabilirler.

Hedef Kitle

  • Temel algoritma, veri yapıları ve temel düzeyde nesne yönelimli programlama bilgisi olan,

  • Başka bir programlama dilini bilen ve Java’ya başlangıç yapmak isteyen,

  • Uzun zaman önce Java ile tanışmış fakat ilerleyememiş, temiz ve hızlı bir başlangıç yapmak isteyenler kişiler için hedeflenmiştir.

  • Kurs sonunda katılımcılar nesne yönelimli programlama (Object oriented programming) öğrenip, Java ile ilgili teknolojilerde kendilerini geliştirebilmek için temel oluşturacak bilgi birikimine sahip olacaktır.

Katılımcılardan İstenenler

  • Herhangi bir linux dağıtımı yüklü dizüstü bilgisayarını getirmesi (Sanal makine tercih edilmemelidir. Mümkünse OpenSuse, Ubuntu veya Fedora dağıtımlardan biri tercih edilmelidir )

  • Sistemlerine OpenJDK 7(veya üzeri) yüklemeleri

  • Eclipse Luna (veya bir önceki sürümü Kepler) yüklemeleri gerekmektedir.

Not: Kurs sırasında herhangi bir yükleme işlemi yapılmayacaktır. O yüzden mutlaka yazılımların yüklü olması gerekmektedir. Yazılım yüklemeleri için gereken döküman katılımcılara özel olarak eposta gönderilecektir.

Kontenjan ve Kursiyer Seçimi

Katılımcı sayısı 30 ile sınırlandırılmıştır. Başvuru sayısı fazla olması halinde adaylara 3 gün içerisinde doldurması gereken anket gönderilecektir. Cevaplanan anketler sonucunda kursa uygun olan katılımcılar seçilecektir.


1. Gün

  • Java

  • JDK, JRE, JVM, Java Versiyonları

  • Java ile İlk Program

  • Veri Tipleri, Operatörler, String

  • Döngü ve Koşul

  • Sınıflar, Nesneler

  • Construction

  • Nesne Yönelimli Programlamaya Giriş

  • Kapsülleme (Encapsulation)

  • Kalıtım (Inheritance)

2. Gün

  • Polimorfizm

  • Soyutlama (Abstraction)

  • Casting

  • Interface & Abstract Sınıflar

  • Statik ve Final

3. Gün

  • Exception Handling (Checked & Unchecked)

  • Diziler (Array)

  • Generic

4. Gün

  • Collections (List, Set, Map, Iteration)

  • Enumeration

  • Mutable & Immutable

  • Inner Class

  • String & StringBuilder


Kursa kayıt olmak için 1 Ocak 2015 tarihinden itibaren adresinden yapabilirsiniz. Kurs ile ilgili sorularınızı eposta ile sorabilirsiniz.

Diğer Kurslar

Akademik Bilişim’de 40’a yakın kurs düzenlenecektir. Kurslarla ilgili detaylı bilgiyi adresinden edinebilirsiniz.

Eskişehir’de görüşmek üzere…

30 Aralık 2014

Pebble ile Libreoffice Impress Uzaktan Kontrolü

    Libreoffice üzerinde sunumlarınızı yaparken slaytı değiştirmek için yeniden bilgisayarın başına mı gitmeniz gerekiyor? Ya da bu işi uzaktan yapmak için elinizde kocaman bir telefon mu taşımak zorunda kalıyorsunuz? Durun! Artık slaytlarınızı Pebble ile değiştirebilirsiniz... Nasıl mı? :D

    1) Pebble'ınızın telefonunuzla olan bağlantısını kesin.

    2) Pebble'ı bilgisayarınızın bluetoothu ile eşleştirin. Pebble sürekli dışarıya görünür halde olmadığından bu eşleşmeyi yapmak için biraz hızlı olmanız gerekecek. Pebble'ın dışarıya görünür hale gelmesi için  Settings-->Bluetooth ayarına girdiğinizde yukarıda "Now Discoverable" yazısı çıkacaktır. O anda bu eşleşmeyi yapmak gerekiyor. Bir defada olmayabilir. Bu kısım bi miktar sıkıntılı ancak bunu sadece bir kez yapmanız yeterli. Siz elle bu eşleşmeyi bitirmediğiniz sürece bir daha böyle bir işlemeye ihtiyaç olmayacaktır.

    3) pebble-remote uygulamasın indirin. Sıkıştırılmış bir şekilde indirebilirsiniz ya da şu komutu kullanarak uygulamayı klonlayabilirsiniz.

        $ git clone

    4) Bağımlılıkları kuruyoruz.

        $ sudo apt-get install python-dev libopenobex1-dev python-tk python-lightblue python-pexpect xdotool python-bluez

     5) lightblue-0.4 uygulamasını indirip kuruyoruz:

        $ git clone
          $ cd lightblue-0.4
          $ sudo python install

    6) Bir terminal aracılığıyla pebble-remote dizini içine geçin:
        $cd /path/to/pebble-remote

    7) Burada çalıştırmak için gerekli komutu yazarken bazı parametrelere ihtiyacınız olacak.

Birinci parametre pebble id Bu bilgiyi iki şekilde öğrenebilirsiniz. Birincisi Pebble üzerinde Settings-->About-->BT Address

İkincisi bilgisayarınızda bluetooth ayarlarında eşleşmiş cihazlara girip Pebble cihazına tıkladığınızda sağ tarafta adres bilgisi olacaktır.

Adres 6 oktetten oluşan 11:22:33:AA:BB:CC gibi bir bilgidir. Bu bilgiyi bir kenara not edelim.

İhtiyacımız olan ikinci parametre, yapmak istediğiniz sunumun bilgisayardaki tam yolu.
Örneğin: /home/gulsah/sunum1.odp

Artık  şu komutu çalışırabiliriz(Kendi pebble id niz ve sunumunuzun tam yolu ile):

./ --pebble_id 11:22:33:AA:BB:CC --lightblue remote libreoffice /home/gulsah /sunum1.odp

    Bu komutu çalıştırdıktan sonra pebble ile bağlantıda bir sorun yaşarsanız bir defa bu komutu çalıştırırken yine pebble'ın ikinci adımda tarif ettiğim gibi görünür olması gerekebilir.

    Sunum önünüze tam ekran açılacaktır. Pebble içindeki müzik uygulamasını açıp üst ve alt düğmelerini kullanarak slaytlarınızı Pebble ile değiştirebilirsiniz. :)


24 Aralık 2014

Posted In: Gezegen, linux, pebble, python, remote, smartwatch

Begining to Read Memory Management Codes

My Linux Kernel internship started two weeks ago and will take 3 months. My mentor is Rik Van Riel. My project aim to fix transparent huge page swapping issues, if system needs to swap huge pages, it has to split the pages to small sized ones but then the system can not reconstitute the huge pages.

Rik asked me some questions about huge page and swapping and I've replied them. Before the reply the questions I've looked for following data structures and definitions.

Firstly I've started to examine struct page and mm_struct in mm_types.h. The kernel holds all information in mm_struct, it includes vm_area_struct *mmap which involves list of memory areas.  vm_areas_struct is an object to show memory areas. Also, the kernel threads don't use mm_struct so if you see if (!mm) {...} it means this is  kernel thread.

Likely & Unlikely Functions: Theese are for branch prediction so used for compiler optimization. They supply to guess which instruction will run and do read ahead.

Numa & Uma Systems: I've understood the two keywords looking the picture :).

Hot &  Cold Page: If a page in cpu cache, it is hot page however cold page is vice versa.

struct scan_control: It is used for page scaning, holds following variables:
unsigned long nr_scanned: How many inactive pages were scanned.
int may_writepage: It determines whether the kernel can write backing store.
swap_cluster_max: It is restriction for a lru list.

struct zone: The kernel divides memory to nodes, and the nodes include zone lists. Every zone area include pages. You can look for struct zone.

struct list_head: Doubly linked list, to build & manage lists.

Page Flags:

High Memory: Linux Kernel seperate high rate of memory for user space so high memory means user space.

Page Vector: Provides operations on page list instead of individual pages.

Slot: Swap area is divided to slots. Size of each slot equals to page frame.

up_read/write, down_read/write functions: They are for spinlock issues and includes assembly instructions.

BUG_ON* functions: Checks given condition and returns system halt or nothing.

Swap Cache: Some pages after swapped out, if the page is not changed, it has an entry on swap cache and system can read data on memory withouth get the page to back memory.

Transparent Huge Page vs. Huge Page: Transparent huge page supplies a layer for huge page.

Note-1: Swap space used by user space tools (mkswap)

Note-2: x86 systems don't use pte level for THP (transparent huge page), it can direct access data on pmd.

Following questions which are asked to me by my mentor. I've explained just important points for my project and their function traces because there are a lot of functions, sometimes they can be very complex :).

Below call chains for Linux Kernel - 3.18

1) from do_page_fault(), sometimes the VM uses transparent huge pages
   (2MB size on x86) for anonymous memory. What functions does the
   code go through between do_page_fault() and the function that
   installs 2MB pages in the process page tables?
When I examined functions, I saw a lot of spinlock functions and Rik said, they for ensure that multiple concurrent instances of the page fault code do not manipulate the page table simultaneously.

  __do_page_fault() /* checks the fault is belong to bad area or good area */
pgtable_trans_huge_withdraw takes a page table page from the process's
reserve of page table pages, so the 2MB page (mapped at pmd level) can
be mapped as 4kB page entries (at the pte level).

2) When are 2MB pages used?

If PAE is enabled, then use 2mb pages. I've looked for it following links:

3) What does the VM do when a 2MB page cannot be allocated?
   (still in memory.c and huge_memory.c)
In  do_huge_pmd_anonymous_page(), if it can not allocate 2MB page;
it returns, out of memory or fall back. It also calls count_vm_event()
with THP_FAULT_FALLBACK argument. At line: 824, it tries to set
huge zero page, if it can't do that, calls put_huge_zero_page(),
which calls atomic_dec_and_test(). 

At line: 839: If it couldn't install huge page, it calls
put_page(). I've thought;in put_page, it checks whether
the page compound or not, but the page will be compound
always, because the page comes from alloc_hugepage_vma().

4) When the system runs low on memory and wants to swap something
   out, it will split up a huge page before assigning it space in
   a swap area. Find the code in vmscan.c, swapfile.c and huge_memory.c
   that does that. What does the function trace look like from
   try_to_free_pages to the function that splits the huge pages?
  throttle_direct_reclaim(gfp_mask, zonelist, nodemask)
    do_try_to_free_pages(zonelist, &sc)
      do while { vmpressure_prio()
      shrink_zones() /* if a zone reclaimable it returns true */}

I've seperated shrink_zones() to below:

  populated_zone() {return (!!zone->present_pages);}
  zone_reclaimable_pages(zone) -> get_nr_swap_pages()

try_to_free_pages(): If memory is not sufficent, it checks pages and removes least used one.
shrink_zones(): It is runned by kswapd with specified time interval and used for remove rarely used
pages. It also balances inactive and active lists using shrink_active_list().
shrink_active_list(): Provides to transfer pages between active_list and inactive_list and detect least used active lists and also implements page selection.
shrink_inactive_list(): Removes lists from inactive_list and send the lists to shrink_page_list().

In general, shrink_* functions run per zone.

5) in huge_memory.c look at collapse_huge_page and the functions
   that call it - under what conditions does the kernel gather up
   512 4kB pages and collapse them into one 2MB page?
                khugepaged_alloc_page() /* allocate new page */
                __collapse_huge_page_isolate(vma, address, pte); /* this one is new function for me */
                if (isolate_lru_page(page)) { ... }
                if (pte_young(pteval) || PageReferenced(page) ||
                        mmu_notifier_test_young(vma->vm_mm, address)) { ... }

collapse_huge_page_isolate() removes pages from lru with isolate_lru_page().
I've thought: when collapsing pages, their lru's will change. So it isolates

Note-1: __collapse_huge_page_copy(): 
The 4kB pages could be anywhere in memory.
The 2MB page needs to be one contiguous page.
That means the contents of the 4kB pages need
to be copied over into the one 2MB page.
khugepaged_scan_pmd(), if page is young, it will call collapse_huge_page().
If the collapse function can correct vma, pmd and isolate pages, it collapses

6) under what conditions does the kernel decide not to collapse
   the 4kB pages in a 2MB area into a 2MB page?
There some conditions for it:
1) If can't alloc khuge page, it won't collapse.
2) I've looked to this condition in collapse_huge_page():
        if (unlikely(khugepaged_test_exit(mm))) {goto out;}
   if mm has no user, it goes to label out and doesn't collapse pages.
3) If it can't find vma and pmd
4) If it can't isolate pages

7)  look at what happens when shrink_page_list()
passes a 2MB transparent huge page to add_to_swap()
When it sent 2 MB page to add_to_swap function, it firstly checks whether page locked and up to date then calls get_swap_page(). If there is no swap page returns 0, If not it checks transHugePAge() then implements split_huge_page_to_list(). In split_huge_page_to_list it gets anonymous vma and does write-lock for it and checks PageCompound. With PageCompound it controls the is huge or not.  Then it checks PageSwapBacked. Then calls __split_huge_page() and the function wants the page shouldn't be tail and splits the page in __split_huge_page_splitting(). The function backs to add_to_swap and does swapcache_free() issues.

8) Can you explains what the page looks like after it has been split?
What happened to the 2MB page?  What do we have instead?
What happened with the PageCompound flag?
__split_huge_page(), it calls __split_huge_page_splitting() in the iteration. It counts number of mapped pmds before splitted it and increase mapcount.

In split_huge_page_map(), it takes page offset with address argument. Firstly, it checks pmd address validity. It
creates small entries in for loop with mk_pte(), set_pte_at(), pte_unmap (this one is just nop instruction for x86 systems). The for loop does one entry for page one, then page two, then page three etc. It changes address of entry adding pagesize (haddr += PAGE_SIZE) up to number of pmd.

I've asked, why pmd_populate()  is performed two times at lines: 1790, 1843?
Rik's answer: The first pmd_populate puts in place a special transparent huge page
PMD that says "this transparent hugepage is being split, do not mess
with it".

The second pmd_populate puts in place the page table page containing
the 4kB pages that map the 2MB area.

Note-1: In __split_huge_page() iterates vma from root of red black tree at line: 1864 but the function gets only one page and a page can match just one vma. So why it needs to iterate vma?

Rik replied my question: "The same page may be shared by multiple processes, if the
process that created the 2MB page originally called fork() afterwards."

Note-2: In  __split_huge_page_splitting(), it calls  pmdp_splitting_flush() what does it do also pmd_update and flush_tlb_range function? I think it should save pmd's content before splitting, it shouldn't lose it. Why it flushes pmd?
Rik's answer: if a small page is touched or dirtied afterwards, we want the MMU to set the accessed and/or dirty bit on the 4kB page entry.

Note-3: We can ignore PVOP_VCALL stuff - that is for Xen, which uses an alternate function for filling in page table info. 

9) Under what conditions can a region with 4kB pages be
turned into a 2MB transparent huge page?
I've traced following call chain:
                        __handle_mm_fault() /* check conditions */
                                do_huge_pmd_anonymous_page() /* check conditions */
                                __do_huge_pmd_anonymous_page() /* check conditions */

In __handle_mm_fault(), "if (pmd_none(*pmd) && transparent_hugepage_enabled(vma)) { ... }" if the expression is correct, it can realize do_huge_pmd_anonymous_page(). I've seen this quote for pmd_none() "if page is not in RAM, returns true." But I think, if page is not used for any process, it includes zeros and should be in RAM.

In do_huge_pmd_anonymous_page(), "if (!(flags & FAULT_FLAG_WRITE) && transparent_hugepage_use_zero_page()) { ... }"
if it can correct the condition, it can start to create transparet huge page. I've looked for condition values.
flags = FAULT_FLAG_ALLOW_RETRY | FAULT_FLAG_KILLABLE; allow retry and killable flag values are defined with special values (0x08, 0x02)?
I think their values only for to check something. And transparent_hugepage_flags is 0UL, is it always have this value? I've looked for its value,
probably always have same value. The last condition creates huge zero page using  set_huge_zero_page() which calls pmd_mkhuge().

One more condition: __do_huge_pmd_anonymous_page(mm, vma, haddr, pmd, page), if it returns false, that means created transparent huge page at line: huge_memory.c#L808
If pmd_none() returns true, creates thp.

10) What code turns 4kB pages into a 2MB page?
pmd_mkhuge() installs 2 MB page. Actually, it does pmd_set_flags(pmd, _PAGE_PSE).
_PAGE_PSE uses _PAGE_BIT_PSE which means huge page.

11) Under what conditions can a region with 4kB pages not
be turned into a 2MB transparent huge page?
There are a lot conditions for this.
1) If the entire 2MB page inside vma, return fall back.
2) If it can't create anonymous vma, return out of memory.
3) If it can't create huge page vma, return fall back.
4) If it get true from __do_huge_pmd_anonymous_page(), return fall back.
5) in __do_huge_pmd_anonymous_page(), if page is not support huge page, the code create kernel panic, and halt.
   VM_BUG_ON_PAGE(!PageCompound(page), page);

6)  If it cannot allocate a huge page

24 Aralık 2014

Posted In: Gezegen, huge page, internship, kernel, linux, memory management, opw, swap, thp

İnternetle Özgür Yazılım Sembiotik Bir İlişki İçinde

BTHABER 1000. sayı söyleşisi 15 aralık 2014
Sedef Özkan

BThaber-AkgulÜlkemizin bilişim otoritelerinden Mustafa Akgül ile bilişim tarihimizde; sözcüklerle kısa sürse de, bir o kadar uzun ve devam edecek yolculuğa çıktık.

Bilişim dünyasına girişinin internetle olduğunu söyleyen Mustafa Akgül, “İnterneti çok önemsiyorum; ‘İnternet Yaşamdır!’ diyorum, onun en az sanayi devrimi kadar önemli, insanlığı ‘Bilgi Toplumu’na taşıyan bir gelişme olduğunu düşünüyorum” şeklinde konuşmasına başladı. Çabasını; interneti Türkiye’ye tanıtmak, ülkenin gündemine taşımak, ülkenin ekonomik, sosyal ve demokratik anlamda gelişmesine yönelik önündeki engelleri kaldırmak olarak aktaran Akgül, “Bu amaçla, İnternet Konferansı’nı 19 kere, Akademik Bilişim Konferansı’nı 16 kere, İnternet Haftası’nı 17 kere arkadaşlarımla düzenledik, düzenlemeye devam ediyoruz. KamuNet Konferansı’nı sadece 1 kere yapabildik. Bunların yanında Linux ve özgür yazılımı Türkiye’ye tanıtmak, gelişmesine katkı vermek için uğraştım. İnternetle özgür yazılım sembiyotik bir ilişki içindeler. İnternet sayesinde birbirini tanımayan insanlar birlikte, tüm insanların ortak malı ürünleri geliştiriyor. Bunların yanında pek çok bilişim etkinliği içinde oldum” açıklamasını yaptı.

Bilim, Ar-Ge ve inovasyonu temel alan kapsamlı bir strateji ve planla ülkemiz kalkınabilir

“Bilişim ve internet bir yandan toplumun bütünleşmesi, bir hedef etrafında birleşmesi, katılımcı ve saydam, demokratik olmaya yardımcı olacak araçları, öte yandan tüm sektörleri değiştiren, geliştiren, tüm yaşamı etkileyen, kolaylaştıran, sinerjiler oluşturma potensiyeline sahiptir” diyen Akgül, bilim, Ar-Ge ve inovasyonu temel alan kapsamlı bir strateji ve planla ülkemizin kalkınabileceğinin altını çizdi ve şu detayları verdi: “AB seviyesine ulaşabiliriz. ‘İnternet ve Bilişim’ tüm toplum kesimleri, tüm sektörler için önemli. Herkesin kendi işini yaparken, internet ve bilişimi kullanması, iyi planlanır ve düzgün araçlar geliştirilirse, işini daha iyi yapmasına, yüksek katma değere neden olacaktır. Şu anda Türkiye’de iyi niyetle çabalayan, para harcayan ama düzgün ve kapsamlı bir stratejisi olmayan, katılımcı, saydam mekanizmaları olmayan, resmin tamamını göremeyen çelişkiler içinde bir görüntü var. Bir yandan Bill Gates, Steve Jobs, Mark Zuckerberg’ler yetiştirmeyi hedefleyen, öte yandan twitter, facebook ve youtube’un kökünü kazımak isteyen bir ülkeyiz. Microsoft’un bile Açık Kaynak dünyasına katılma çabasında olduğu bir zamanda, olayın farkında olmayan bir bilişim sektörü, basın ve üniversiteleri olan bir ülkeyiz. Herkesin bilişimin önemini söylediği ama bir curcunanın sürdüğü, bütünsel bir yapının olmadığı acı bir gerçek olarak karşımızda.”

Dünya, anaokulunda programlama kavramlarını öğretmeye çalışıyor

“Bilişimi ve bilişimle ülkeyi ne geliştirir?” sorusuna şöyle yanıt veren Akgül, açık kaynak ve özgür yazılıma da vurgu yaptı: “Bilişim için siyasal liderlik, sorumluluk alacak siyasal geleceği bilişime bağlı bir siyasal kadro, tüm paydaşları içeren, katılımcı, tüm çalışmaları koordine edecek bir yapılanma, kapsamlı bir strateji, açık ortamlarda periyodik gözden geçirilen Eylem Planı; bilişimi ve bilişimle ülkeyi geliştirir. Demokrasi, saydamlık, katılımcılık, ifade özgürlüğü, merak, girişim, bilişim sektörünün gelişmesi için önemlidir. Açık Kaynak ve özgür yazılımlar stratejinin bir parçası olmak zorunda. İnsan gücü, eğitimi de önemli bir parçası olmalı. Ülke olarak bilişim eğitimi ve bilişim kültürüne önem vermemiz gerekir. Kaliteli uzmanlar, doktoralı elamanlar yetiştirmeliyiz. Bizim, dağdaki çobandan, denizdeki balıkçıya, tarihçiden ziraatçiye, temel bilişim kavramlarını, bilişim ve internet tehdit ve olanaklarını, sınırlarını ve potensiyeli anlatacak mekanizmalar kurmamız gerekir.” Mustafa Akgül, “Dünya anaokulunda programalama kavramlarını öğretmeye çalışıyor” diyerek erken yaşta bilişim eğitimine dikkat çekerek şunları paylaştı: “Okullarda temel bilişim kültürünü, başta programalama, bilgi sistemi, veri tabanı, ağ, güvenlik, mahremiyet, etik ve estetik kavramlarını öğretmeniz lazım. Bilişimin önemini, karmaşıklığını, zorluğunu ve kırılganlığını okullarda anlatmamız gerekir. Her meslekten okullu, bir yelpazede bilişim kültürü almalı. Öğretmenler, hukukçular, kamu/siyaset bilimciler, idareciler, işletmeciler biraz daha öncelikli olmalı.” Yazılım stratejisine de değinen Akgül, “Doğru dürüst bir yazılım stratejimiz olmalı. Bunda Açık Kaynak ve özgür yazılımlar, gömülü sistemler önemli rol almalı. Stratejik sektörler belirlemeli, onlara daha fazla odaklanmalıyız. Bütün bunlar bir miktar öğrenme ister. Öğrenen, geri besleme yapacak, katılımcı yapılar kurmalıyız.”

Eşit bir dünya vatandaşı olduğunun farkında yaşamak…

Akgül, tecrübelerini paylaşırken yolu bilişimden geçenlere yani herkese şunları önerdi: “Başta merak, işin özünü anlamaya, öğrenmeye, deney yapmaya, eleştirisel bakmaya önem vermeli, özen göstermeliler. Yapıcı ve girişimci olmalılar. Sorumluluk almaktan, hata yapmaktan korkmasınlar. İnsanları kırmaktan kaçınsınlar, yumuşak bir dille uzlaşmacı olsunlar. İlkelerden taviz vermeden, diyalogla orta yol bulmanın yollarını arasınlar. Sanat ve kültürden, müzikten zevk almaya çalışsınlar. Doğa ve çevreye saygılı, yaşama saygılı bir tavır sergilesinler. Eşit bir dünya vatandaşı olduğunun farkında olarak yaşasınlar.”

İnterneti savunmaya, tanıtmaya, yaymaya devam edecegiz

Hedefleri hiç tükenmeyen Akgül, “Benim çalışmalarım birbirine bağlı olarak ‘İnternet ve Özgür Yazılım’ etrafında olmuştur. İnternet konusunda, yurt dışındaki internet özgürlüğünü savunan gruplarla birlikte çalışan isoc-tr yani İnternet Derneği’ni geniş bir kadroyla birlikte kuruyoruz. İnterneti savunmaya, tanıtmaya, yaymaya devam edecegiz. Yıllık kapssamlı internet raporları çıkartmak, interneti toplumun gündemine koymak, demokrasiyi geliştirici uygulamalara destek olmak gibi hayallerimiz var. 1998’de bir kere yapabildigimiz KamuNet Konferansı’nı günün koşullarında; kamunun saydamlaşmasına, etkin çalışmasına, yurttaşa hızlı hizmet ve demokrasiye katkı vermesine yönelik yılık konferanslar olarak yapmak istiyoruz. Özgür yazılım boyutunda; üniversitelerde özgür yazılım derslerinin ve kullanımının artması, yıllık raporların hazırlanması gibi çaba/proje/hayallerim var. Son yirmi yılı özetlemeye çalışan 2 sloganımız bulunuyor: ‘İnternet yaşamdır’ ve ‘Türkiye Bilişimle, Bilişim Özgür Yazılımla gelişir!’”

23 Aralık 2014

Posted In: bilgi toplumu, bilişim, bthaber 1000. sayısı, demokrasi, e-devlet, Genel, ifade özgürlüğü, internet, linux, lkd, Özgür yazılım, sosyal ağlar, temel bilişim eğitimi, yönetişim

3. Türkiye PostgreSQL Konferansı’nın ardından

Biraz gecikmeli de olsa 3. Türkiye PostgreSQL Konferansı'nı değerlendirmek istedim.

Bu seneki konferans, İstanbul'daki 2 büyük etkinlikle aynı gün, ama Ankara'da idi. Biz tarihi daha önceden belirlemiş olmamıza rağmen geç duyurduğumuz için çakışıyor gibi gösterildik. Bir dahaki sefere zamanında duyuracağız, bundan ders aldık.
Continue reading "3. Türkiye PostgreSQL Konferansı'nın ardından"

19 Aralık 2014

Posted In: fedora, Özgür yazılım, postgresql

İmzalamadığınız Commit Sizin Değildir

Git kullananlar bilirler, .gitconfig isimli dosyaya isim soyisim ve e-posta adresi yazılarak commit loglarına commit sahibinin bilgileri otomatik eklenir.

Ancak bu durumun bir olumsuz(?) yanı vardır. Başkaları sizin adınıza commit yapabilir.
Kendi .gitconfig dosyanıza Ali yazsanız Ali’nin adına Veli yazsanız Veli’nin adına commit yapabilirsiniz.

Ancak bir commit’in gerçekten o kişinin yaptığına emin olmak için commit’i imzalamakta fayda vardır.

Peki imzalamayı nasıl yapacağız?

Öncelikle sisteminizde imza var mı bakınız:

gpg --list-keys

(Eğer daha önce GPG ile ilgili işlem yapmamışsanız, bu komut gerekli dosyaları da oluşturacaktır.)

Şuna benzer bir sonuç döndürmeli:

pub   2048R/B489436C 2014-12-14
uid                  Adil Ilhan <>

Eğer GPG anahtarınız yoksa boş sonuç dönecektir.

gpg --gen-key

komutu ile GPG anahtarınızı oluşturabilirsiniz. Bu komut size yol gösterecektir.

Ekstra olarak açıklama gereği duyduğum kısım passphrase kısmı. Buraya parola girerseniz oluşturacağınız anahtar bu parola olmadan çalışmayacaktır. Yani anahtarınız çalınsa bile ekstra olarak bir de buraya yazdığınız parolaya ihtiyaç duyulacaktr.

GPG anahtarı artık oluşmuş olmalı. Kontrol için:

gpg --list-keys

Git ortamınıza bu anahtarı tanımlamak gerek:

git config --global user.signingkey B489436C

B489436C bilgisini gpg –list-keys komutunun sonucundan aldım.

Artık commitleri -S parametresi ile imzalayabiliriz:

git commit -m "test" -S

İmzalanmış commitleri görme ve doğruluğunu teyit etme:

git log --show-signature

Bu komut, yerel (local) makinenizdeki GPG bilgisi ile commit log’unda yer alan GPG bilgisini eşleştirir.
Uyuşan loglara gpg: Good signature… yazılır. Uyuşmayan loglara Can’t check signature yazılır.

Örneğin sizin bilgisayarınızdan imzalanarak commitlenen bir commit başka bir bilgisayarda bakıldığında ve o bilgisayarda sizin GPG anahtarınız yoksa log sonuçlarına Can’t check signature bilgisi yazılır.

15 Aralık 2014

Posted In: Genel, Gezegen, git, GPG

Twitter Auto Publish Powered By :