Ukuran tumpukan default untuk pthreads

24

Seperti yang saya mengerti, ukuran stack default untuk pthread di Linux adalah 16 ribu. Saya mendapatkan hasil yang aneh pada pemasangan Ubuntu 64-bit saya.

$ ulimit -s
8192

Juga:

pthread_attr_init(&attr);
pthread_attr_getstacksize(&attr, &stacksize);
printf("Thread stack size = %d bytes \n", stacksize);

Prints
    Thread stack size = 8388608 bytes

Saya cukup yakin ukuran tumpukan tidak "8388608". Apa yang salah?

Kamath
sumber
7
Saya pikir 8388608 / 1024 = 8192.
cuonglm
6
Anda berpikir tentang 16k per tumpukan kernel thread . Masalah yang benar-benar terpisah dari memori ruang pengguna. tumpukan kernel sangat kecil karena tidak dapat di-paging, atau dialokasikan dengan malas, dan harus berupa halaman-halaman yang berdekatan dalam memori fisik. elinux.org/Kernel_Small_Stacks . Memiliki jumlah total utas yang sangat tinggi dapat menjadi masalah bagi i386, di mana ruang alamat terbatas, terutama dengan tumpukan 8k secara default untuk 32-bit.
Peter Cordes

Jawaban:

21
int pthread_attr_setstacksize(pthread_attr_t *attr, size_t stacksize);

The stacksizeatribut harus menentukan ukuran minimum stack (dalam byte) yang dialokasikan untuk benang tumpukan dibuat.

Dalam contoh Anda, ukuran tumpukan diatur ke 8388608 byte yang sesuai dengan 8MB, seperti yang dikembalikan oleh perintah ulimit -s Jadi yang cocok.

Dari pthread_create()uraian:

Di Linux / x86-32 , ukuran tumpukan default untuk utas baru adalah 2 megabita . Di bawah implementasi threading NPTL, jika RLIMIT_STACK batas sumber daya lunak pada saat program dimulai memiliki nilai selain "tidak terbatas", maka ia menentukan ukuran tumpukan default utas baru. Menggunakan pthread_attr_setstacksize (3), atribut ukuran stack dapat secara eksplisit diatur dalam argumen attr yang digunakan untuk membuat utas, untuk mendapatkan ukuran stack selain dari default.

Jadi ukuran tumpukan ulir dapat diatur baik melalui fungsi yang ditetapkan di atas, atau ulimitproperti sistem. Untuk 16k yang Anda maksudkan, tidak jelas pada platform yang Anda lihat itu dan / atau jika ada batas sistem yang ditetapkan untuk ini.

Lihat halaman pthread_create dan di sini untuk beberapa contoh menarik tentang ini.

fduff
sumber
47

Sebenarnya, ukuran tumpukan virtual Anda adalah 8388608 byte (8 MB). Tentu saja, wajar untuk menyimpulkan bahwa ini tidak mungkin benar, karena itu adalah jumlah memori yang sangat besar untuk dikonsumsi oleh setiap utas untuk tumpukannya ketika 99% dari waktu mungkin diperlukan beberapa KB.

Berita baiknya adalah utas Anda hanya menggunakan jumlah memori fisik yang sebenarnya dibutuhkan. Ini adalah salah satu kekuatan ajaib yang diperoleh OS Anda dari menggunakan perangkat keras Memory Management Unit (MMU) di prosesor Anda. Inilah yang terjadi:

  1. OS mengalokasikan 8 MB memori virtual untuk tumpukan Anda dengan mengatur tabel halaman MMU untuk utas Anda. Ini membutuhkan sangat sedikit RAM untuk menyimpan entri tabel halaman saja.

  2. Ketika utas Anda berjalan dan mencoba mengakses alamat virtual pada tumpukan yang belum memiliki halaman fisik yang ditetapkan untuknya, pengecualian perangkat keras yang disebut "kesalahan halaman" dipicu oleh MMU.

  3. Inti CPU merespons pengecualian kesalahan halaman dengan beralih ke mode eksekusi istimewa (yang memiliki tumpukan sendiri) dan memanggil fungsi penanganan pengecualian kesalahan halaman di dalam kernel.

  4. Kernel mengalokasikan halaman RAM fisik ke halaman memori virtual dan kembali ke utas ruang pengguna.

Utas ruang pengguna tidak melihat satupun dari pekerjaan itu. Dari sudut pandangnya, ia hanya menggunakan tumpukan seolah-olah memori ada di sana selama ini. Sementara itu, tumpukan secara otomatis tumbuh (atau tidak) untuk memenuhi kebutuhan utas.

MMU adalah bagian penting dari perangkat keras sistem komputer saat ini. Secara khusus, ini bertanggung jawab untuk banyak "keajaiban" dalam sistem, jadi saya sangat merekomendasikan belajar lebih banyak tentang apa yang dilakukan MMU, dan tentang memori virtual secara umum. Selain itu, jika aplikasi Anda peka terhadap kinerja dan berurusan dengan sejumlah besar data, Anda harus memahami cara kerja TLB (cache tabel halaman MMU) dan bagaimana Anda dapat menyusun kembali data atau algoritme Anda untuk memaksimalkan tingkat hit TLB Anda.

jtchitty
sumber