“Memfd” leri “dosyanın sahibi olan sürece” açıklanmış olarak düşünmek yanlış mıdır?


15

https://dvdhrm.wordpress.com/2014/06/10/memfd_create2/

Teorik olarak, memfd_create()yeni sistem çağrıları yapmadan [ ] davranışını şu şekilde başarabilirsiniz :

int fd = open("/tmp", O_RDWR | O_TMPFILE | O_EXCL, S_IRWXU);

(Bir tmpfs'yi daha portatif olarak garanti etmek için " /dev/shm" yerine " /tmp" kullanabiliriz).

Bu nedenle, en önemli soru neden üçüncü bir cehenneme ihtiyacımız var?

[...]

  • Yedekleme belleği, dosyanın sahibi olan ve mount-kotalara tabi olmayan işleme göre hesaplanır.

^ Bu cümlenin ilk kısmına güvenilemeyeceğini düşünmekte haklı mıyım?

Memfd_create () kodu anlamıyla bir "olarak uygulanmaktadır çekirdek iç olmalıdır [a] tmpfs içinde bağlantısız dosya yaşayan ". Kod izleme, ben LSM kontrolleri uygulamak farklı olduğunu anlıyorum, ayrıca blog yazısı açıklamaya devam gibi memfds "mühürler" desteklemek için oluşturulur. Ancak, ben memfds olduğunu son derece şüpheci hesaba prensipte bir tmpfile farklı şekilde.

Özellikle, OOM katili vurma geldiğinde, memfds tarafından tutulan hafızayı açıklayacağını sanmıyorum. Bu, RAM'in% 50'sine kadar çıkabilir - tmpfs için size = seçeneğinin değeri . Çekirdek, dahili tmpfs için farklı bir değer ayarlamaz, bu nedenle varsayılan% 50 boyutunu kullanır.

Bu yüzden genel olarak büyük bir memfd içeren süreçler bekleyebiliriz, ancak başka önemli bellek ayırma işlemleri OOM tarafından öldürülmeyecektir. Bu doğru mu?


2
OOM skorlarına gelince , çekirdek oom_badness fonksiyonuna iniyor gibi görünüyor . Memfd_create bir / proc / {pid} / haritada görünmüyorsa, o zaman onun sayılmaz. Yani genel cevap, öldürülebilecekleri, ancak memfd_create kullanımı nedeniyle büyük bir puanları olmayacak. Fd için bellek, aynı fd olmak üzere birden çok işlem miras alabileceği / gönderilebileceği için süreçler arasında paylaşılabilir.
danblack

Yanıtlar:


1

@ Danblack'ın cevabı üzerine inşa:

Karar aşağıdakilere dayanmaktadır oom_kill_process()(biraz temizlenmiştir):

for_each_thread(p, t) {
        list_for_each_entry(child, &t->children, sibling) {
                unsigned int child_points;

                child_points = oom_badness(child,
                        oc->memcg, oc->nodemask, oc->totalpages);
                if (child_points > victim_points) {
                        put_task_struct(victim);
                        victim = child;
                        victim_points = child_points;
                        get_task_struct(victim);
                }
        }
}

( https://github.com/torvalds/linux/blob/master/mm/oom_kill.c#L974 )

Hangi oom_badness()en iyi adayı bulmaya bağlıdır :

child_points = oom_badness(child,
        oc->memcg, oc->nodemask, oc->totalpages);

oom_badness() yapar:

points = get_mm_rss(p->mm) + get_mm_counter(p->mm, MM_SWAPENTS) +
        mm_pgtables_bytes(p->mm) / PAGE_SIZE;

( https://github.com/torvalds/linux/blob/master/mm/oom_kill.c#L233 )

Nerede:

static inline unsigned long get_mm_rss(struct mm_struct *mm)
{
        return get_mm_counter(mm, MM_FILEPAGES) +
                get_mm_counter(mm, MM_ANONPAGES) +
                get_mm_counter(mm, MM_SHMEMPAGES);
}

( https://github.com/torvalds/linux/blob/master/mm/oom_kill.c#L966 )

Görünüşe göre anonim sayfaları sayıyor, bu da memfd_create()kullanıyor.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.