Membuat utas gagal dengan “Sumberdaya sementara tidak tersedia” dengan kernel 4.3


39

Saya menjalankan server buruh pelabuhan di Arch Linux (kernel 4.3.3-2) dengan beberapa kontainer. Sejak reboot terakhir saya, baik server docker dan program acak di dalam wadah macet dengan pesan tentang tidak dapat membuat utas, atau (lebih jarang) melakukan fork. Pesan kesalahan spesifik berbeda tergantung pada program, tetapi sebagian besar dari mereka tampaknya menyebutkan kesalahan spesifik Resource temporarily unavailable. Lihat di akhir posting ini untuk beberapa contoh pesan kesalahan.

Sekarang ada banyak orang yang memiliki pesan kesalahan ini, dan banyak tanggapan terhadap mereka. Apa yang benar-benar membuat frustasi adalah bahwa semua orang tampaknya berspekulasi bagaimana masalah ini dapat diselesaikan, tetapi tidak ada yang menunjukkan bagaimana mengidentifikasi penyebab dari berbagai kemungkinan masalah yang ada.

Saya telah mengumpulkan 5 kemungkinan penyebab kesalahan ini dan cara memverifikasi bahwa mereka tidak ada di sistem saya:

  1. Ada batasan seluruh sistem pada jumlah utas yang dikonfigurasikan dalam /proc/sys/kernel/threads-max( sumber ). Dalam kasus saya ini diatur ke 60613.
  2. Setiap utas membutuhkan ruang di tumpukan. Batas ukuran tumpukan dikonfigurasikan menggunakan ulimit -s( sumber ). Batas untuk shell saya dulu 8192, tapi saya telah meningkat dengan meletakkan * soft stack 32768ke dalam /etc/security/limits.conf, sehingga ulimit -ssekarang kembali 32768. Saya juga telah meningkat untuk proses buruh pelabuhan dengan menempatkan LimitSTACK=33554432ke dalam /etc/systemd/system/docker.service( sumber , dan saya memverifikasi bahwa batas berlaku dengan melihat ke dalam /proc/<pid of docker>/limitsdan dengan menjalankan ulimit -sdalam sebuah wadah buruh pelabuhan.
  3. Setiap utas membutuhkan memori. Batas memori virtual dikonfigurasi menggunakan ulimit -v. Di sistem saya diatur ke unlimited, dan 80% dari 3 GB memori saya bebas.
  4. Ada batasan jumlah proses yang digunakan ulimit -u. Thread dihitung sebagai proses dalam hal ini ( sumber ). Pada sistem saya, batasnya diatur ke 30306, dan untuk daemon buruh pelabuhan dan di dalam wadah buruh pelabuhan, batasnya adalah 1048576. Jumlah utas yang saat ini berjalan dapat ditemukan dengan menjalankan ls -1d /proc/*/task/* | wc -latau dengan menjalankan ps -elfT | wc -l( sumber ). Di sistem saya mereka berada di antara 700dan 800.
  5. Ada batasan jumlah file terbuka, yang menurut beberapa sumber juga relevan saat membuat utas. Batas tersebut dikonfigurasi menggunakan ulimit -n. Di sistem saya dan di dalam buruh pelabuhan, batasnya diatur ke 1048576. Jumlah file terbuka dapat ditemukan menggunakan lsof | wc -l( sumber ), di sistem saya ini tentang 30000.

Sepertinya sebelum reboot terakhir saya menjalankan kernel 4.2.5-1, sekarang saya menjalankan 4.3.3-2. Downgrade ke 4.2.5-1 memperbaiki semua masalah. Posting lain yang menyebutkan masalahnya adalah ini dan ini . Saya telah membuka laporan bug untuk Arch Linux .

Apa yang telah berubah di kernel yang dapat menyebabkan ini?


Berikut ini beberapa contoh pesan kesalahan:

Crash dump was written to: erl_crash.dump
Failed to create aux thread

 

Jan 07 14:37:25 edeltraud docker[30625]: runtime/cgo: pthread_create failed: Resource temporarily unavailable

 

dpkg: unrecoverable fatal error, aborting:
 fork failed: Resource temporarily unavailable
E: Sub-process /usr/bin/dpkg returned an error code (2)

 

test -z "/usr/include" || /usr/sbin/mkdir -p "/tmp/lib32-popt/pkg/lib32-popt/usr/include"
/bin/sh: fork: retry: Resource temporarily unavailable
 /usr/bin/install -c -m 644 popt.h '/tmp/lib32-popt/pkg/lib32-popt/usr/include'
test -z "/usr/share/man/man3" || /usr/sbin/mkdir -p "/tmp/lib32-popt/pkg/lib32-popt/usr/share/man/man3"
/bin/sh: fork: retry: Resource temporarily unavailable
/bin/sh: fork: retry: No child processes
/bin/sh: fork: retry: Resource temporarily unavailable
/bin/sh: fork: retry: No child processes
/bin/sh: fork: retry: No child processes
/bin/sh: fork: retry: Resource temporarily unavailable
/bin/sh: fork: retry: Resource temporarily unavailable
/bin/sh: fork: retry: No child processes
/bin/sh: fork: Resource temporarily unavailable
/bin/sh: fork: Resource temporarily unavailable
make[3]: *** [install-man3] Error 254

 

Jan 07 11:04:39 edeltraud docker[780]: time="2016-01-07T11:04:39.986684617+01:00" level=error msg="Error running container: [8] System error: fork/exec /proc/self/exe: resource temporarily unavailable"

 

[Wed Jan 06 23:20:33.701287 2016] [mpm_event:alert] [pid 217:tid 140325422335744] (11)Resource temporarily unavailable: apr_thread_create: unable to create worker thread

1
Apakah Anda baru saja meningkatkan ke kernel 4.3?
Roni Choudhury

Itu sangat mungkin. Mengapa?
cdauth

1
Luar biasa, saya diturunkan ke kernel 4.2.5-1 dan semuanya berfungsi lagi! Apakah Anda memiliki petunjuk apa yang menyebabkan ini dan bagaimana cara memperbaikinya dengan 4.3?
cdauth

Tidak tahu apa yang menyebabkannya. Metode saya memperbaikinya menunggu thread forum Linux Arch pada topik yang akan ditandai "ASK" :-P.
Roni Choudhury

1
+1 Karena menjadi pertanyaan yang diajukan dengan sangat baik dan diteliti, bahkan jika saya tidak memiliki masalah yang sama
Roy Truelove

Jawaban:


47

Masalahnya disebabkan oleh TasksMaxatribut systemd. Itu diperkenalkan di systemd 228 dan memanfaatkan subsistem pid cgroups, yang diperkenalkan di kernel linux 4.3. Batasan tugas 512dengan demikian diaktifkan di systemd jika kernel 4.3 atau yang lebih baru berjalan. Fitur diumumkan di sini dan diperkenalkan dalam permintaan tarikan ini dan nilai-nilai default ditetapkan oleh permintaan tarikan ini . Setelah memutakhirkan kernel saya ke 4.3, systemctl status dockermenampilkan Tasksbaris:

# systemctl status docker
● docker.service - Docker Application Container Engine
   Loaded: loaded (/etc/systemd/system/docker.service; disabled; vendor preset: disabled)
   Active: active (running) since Fri 2016-01-15 19:58:00 CET; 1min 52s ago
     Docs: https://docs.docker.com
 Main PID: 2770 (docker)
    Tasks: 502 (limit: 512)
   CGroup: /system.slice/docker.service

Pengaturan TasksMax=infinitydi [Service]bagian docker.serviceperbaikan masalah. docker.servicebiasanya masuk /usr/share/systemd/system, tetapi juga bisa dimasukkan / disalin /etc/systemd/systemagar tidak ditimpa oleh manajer paket.

Sebuah permintaan tarik meningkat TasksMaxuntuk buruh pelabuhan misalnya systemd file, dan laporan bug Arch Linux berusaha untuk mencapai hal yang sama untuk paket. Ada beberapa diskusi tambahan yang terjadi di Arch Linux Forum dan dalam laporan bug Arch Linux tentang lxc .

DefaultTasksMaxdapat digunakan di [Manager]bagian dalam /etc/systemd/system.conf(atau /etc/systemd/user.confuntuk layanan yang dijalankan pengguna) untuk mengontrol nilai default untuk TasksMax.

Systemd juga menerapkan batas untuk program yang dijalankan dari shell-login. Default ini untuk 4096per pengguna (akan ditingkatkan menjadi12288 ) dan dikonfigurasikan seperti UserTasksMaxpada [Login]bagian /etc/systemd/logind.conf.


1
FWIW, file layanan ada di /lib/systemd/system/docker.servicedalam pengujian Debian saya.
The Compiler

2
FWIW, mengatakan systemctl set-property docker.service TasksMax=4096akan mengatur properti untuk layanan yang sedang berjalan dan bertahan pengaturan untuk reboot berikutnya di tempat yang benar untuk instalasi buruh pelabuhan yang dimaksud.
Nakedible

Ini adalah pendekatan umum . Tetapi perhatikan bahwa perubahan Docker yang Anda usulkan dikembalikan setelah Anda memposting jawaban ini, pada 2016-02-09, pengembalian ini kemudian dirilis ke dunia dalam Docker versi 1.10.1.
JdeBP

Pria, terima kasih, terima kasih, terima kasih! Saya telah mencari terlalu lama untuk ini
achabahe

Jika Anda membuat perubahan pada file konfigurasi (milik saya ada di /etc/systemd/system/docker.service.d/50-TasksMax.confUbuntu 16), Anda harus menjalankannya systemctl daemon-reload. Melakukan sudo service docker restartTIDAK akan berhasil.
osman

4

Jawaban cdauth benar, tetapi ada detail lain untuk ditambahkan.

Pada sistem Ubuntu 16.04 saya dengan systemd 229 dan kernel 4.3, batas 512 pid diberlakukan pada cakupan sesi secara default bahkan ketika UserTasksMax diatur ke yang baru, peningkatan default 12288. Jadi, setiap sesi sesi pengguna dibatasi hingga 512 utas.

Satu-satunya cara saya menemukan untuk menghapus batas itu untuk set DefaultTasksMax=unlimiteddi /etc/systemd/system.confdan systemctl daemon-reexec(atau reboot).

Anda dapat memeriksa apakah ini terjadi dengan mengeluarkan systemctl status, memilih cakupan sesi, dan cat /sys/fs/cgroup/pids/user.slice/user-${UID}.slice/session-FOO.scope/pids.max.


Saya membuat perubahan ke /etc/systemd/system.conf dan reboot. Docker masih mencantumkan batas tugas sebagai 512. Menggunakan komentar @ Nakedible dari atas memang memperbarui tugas yang tersedia.
Ben Mathews

1
Ryan terima kasih! @BenMathews mungkin ini adalah karena keduanya adalah masalah berlaku pada Ubuntu 16.04, Anda harus memperbaiki mereka berdua hal yang dapat bekerja dengan baik. Masalah ini tampaknya berlaku untuk wadah yang dimulai oleh daemon, bukan oleh pengguna di shell. Jadi semuanya tampak baik-baik saja, Anda menambahkan @reboot lxc-autostartke crontab Anda untuk melakukan autostart pada saat boot, dan Anda tiba-tiba mendapatkan wadah yang lumpuh setelah reboot.
qris

1

Setelah membaca utas ini .

Solusi ini bekerja untuk saya: docker -d --exec-opt native.cgroupdriver=cgroupfs. Saya sebenarnya menambahkannya ke OPTIONSdalam /etc/sysconfig/docker...

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.