Maximale Anzahl von Threads pro Prozess unter Linux?


245

Was ist die maximale Anzahl von Threads, die von einem Prozess unter Linux erstellt werden können?

Wie kann dieser Wert (wenn möglich) geändert werden?

Antworten:


246

Linux hat kein separates Thread-Limit pro Prozess, sondern nur ein Limit für die Gesamtzahl der Prozesse auf dem System (Threads sind im Wesentlichen nur Prozesse mit einem gemeinsam genutzten Adressraum unter Linux), die Sie folgendermaßen anzeigen können:

cat /proc/sys/kernel/threads-max

Der Standardwert ist die Anzahl der Speicherseiten / 4. Sie können dies wie folgt erhöhen:

echo 100000 > /proc/sys/kernel/threads-max

Es gibt auch eine Begrenzung für die Anzahl der Prozesse (und damit für Threads), die ein einzelner Benutzer erstellen kann. Weitere ulimit/getrlimitInformationen zu diesen Begrenzungen finden Sie hier.


3
Das Limit in / proc / sys / vm / max_map_count kann auch die Anzahl der Threads begrenzen. Es sollte sicher sein, dieses Limit stark zu erhöhen, wenn Sie es treffen.
Mikko Rantalainen

1
Robert: Linux implementiert indirekt pro Prozesslimit. Überprüfen Sie meine Antwort für Details;)
codersofthedark

Ich versuche dies auf meinem Ubuntu 12.04 zu ändern und es ändert sich nicht mit Ihrem Befehl. Ich habe auch versucht, vi zu ändern, aber ich bekomme, E667: Fsync failedwenn ich versuche, auf vi zu sparen.
Siddharth

4
@dragosrsupercool Der maximale Thread wird unter Verwendung des gesamten RAM berechnet, nicht des virtuellen Speichers
c4f4t0r

1
Die Menge der Stapelgröße pro Thread (die Standardeinstellung auf Ihrem System) ist eher die Grenze als alles andere. Das Reduzieren der Stapelgröße pro Thread ist eine Möglichkeit, die Gesamtzahl der Threads zu erhöhen (obwohl dies selten eine gute Idee ist).
Randy Howard

67

Dies ist FALSCH zu sagen, dass LINUX keine separaten Threads pro Prozesslimit hat.

Linux implementiert indirekt die maximale Anzahl von Threads pro Prozess !!

number of threads = total virtual memory / (stack size*1024*1024)

Somit kann die Anzahl der Threads pro Prozess durch Erhöhen des gesamten virtuellen Speichers oder durch Verringern der Stapelgröße erhöht werden. Eine zu starke Verringerung der Stapelgröße kann jedoch zu einem Codefehler aufgrund eines Stapelüberlaufs führen, während der maximale virtuelle Speicher dem Auslagerungsspeicher entspricht.

Überprüfen Sie Ihre Maschine:

Gesamter virtueller Speicher: ulimit -v(Standard ist unbegrenzt, daher müssen Sie den Auslagerungsspeicher erhöhen, um dies zu erhöhen.)

Gesamtstapelgröße: ulimit -s(Standard ist 8 MB)

Befehl zum Erhöhen dieser Werte:

ulimit -s newvalue

ulimit -v newvalue

* Ersetzen Sie den neuen Wert durch den Wert, den Sie als Grenzwert festlegen möchten.

Verweise:

http://dustycodes.wordpress.com/2012/02/09/increasing-number-of-threads-per-process/


11
Mit Ausnahme von drei kleinen Details: 1. Linux tut dies nicht. Das Vorhandensein von Stapeln und die Tatsache, dass Speicher und Adressraum eine begrenzte Größe haben, haben nichts damit zu tun. 2. Sie müssen den Stapel eines Threads angeben, wenn Sie ihn erstellen. Dies ist unabhängig davon ulimit -s. Es ist sehr gut möglich (nicht sinnvoll, aber möglich), so viele Threads zu erstellen, wie es mögliche Thread-IDs gibt. Unter 64-Bit-Linux ist es sogar leicht "möglich", mehr Threads zu erstellen, als Thread-IDs vorhanden sind (natürlich ist dies nicht möglich, aber was den Stack betrifft, ist dies der Fall). 3. Stack Reserve, Commit und VM sind verschiedene Dinge, besonders bei OC.
Damon

Ja, um die Anzahl der Threads zu erhöhen, müssen Sie den virtuellen Speicher erhöhen oder die Stapelgröße verringern. In Raspberry Pi habe ich keine Möglichkeit gefunden, den virtuellen Speicher zu vergrößern, wenn die Stapelgröße von standardmäßig 8 MB auf 1 MB verringert wird. Es werden möglicherweise mehr als 1000 Threads pro Prozess angezeigt, aber die Stapelgröße wird mit dem Befehl "ulimit -s" verringert Machen Sie dies für alle Threads. Meine Lösung bestand also darin, die Instanz "pthread_t" der "Thread-Klasse" zu verwenden, da ich mit "pthread_t" die Stapelgröße für jeden Thread festlegen konnte. Schließlich bin ich verfügbar, um mehr als 1000 Threads pro Prozess in Raspberry Pi mit jeweils 1
MB

43

In der Praxis wird die Grenze normalerweise durch den Stapelraum bestimmt. Wenn jeder Thread einen 1-MB-Stapel erhält (ich kann mich nicht erinnern, ob dies unter Linux die Standardeinstellung ist), wird einem 32-Bit-System nach 3000 Threads der Adressraum ausgehen (vorausgesetzt, die letzte GB ist für den Kernel reserviert). .

Wenn Sie jedoch mehr als ein paar Dutzend Threads verwenden, werden Sie höchstwahrscheinlich eine schreckliche Leistung erleben. Früher oder später erhalten Sie zu viel Overhead beim Kontextwechsel, zu viel Overhead im Scheduler und so weiter. (Das Erstellen einer großen Anzahl von Threads verbraucht kaum mehr als viel Speicher. Aber viele Threads, die tatsächlich arbeiten müssen, werden Sie verlangsamen, da sie um die verfügbare CPU-Zeit kämpfen.)

Was machen Sie, wenn diese Grenze überhaupt relevant ist?


3
1 MB pro Thread für Stack ist ziemlich hoch, viele Programme benötigen nicht annähernd so viel Stack-Speicherplatz. Die Leistung basiert auf der Anzahl der ausführbaren Prozesse und nicht auf der Anzahl der vorhandenen Threads. Ich habe gerade eine Maschine mit mehr als 1200 Threads und einer Last von 0,40.
Robert Gamble

13
Die Leistung hängt davon ab, was die Threads tun. Sie können viel höher als ein paar Dutzend gehen, wenn sie nicht viel und damit weniger Kontextwechsel tun.
Corey Goldberg

Der Stapel wächst dynamisch, nur die erste Seite wird sofort zugewiesen
Michael Pankov

28

richtige 100k Threads unter Linux:

ulimit -s  256
ulimit -i  120000
echo 120000 > /proc/sys/kernel/threads-max
echo 600000 > /proc/sys/vm/max_map_count
echo 200000 > /proc/sys/kernel/pid_max 

 ./100k-pthread-create-app

Update 2018 von @Thomas auf systemd-Systemen:

/etc/systemd/logind.conf: UserTasksMax=100000

4
Vielen Dank, es hat mir endlich erlaubt, die 32k Java Thread Anzahl zu durchbrechen.
berezovskyi

1
Funktioniert bei mir nicht: $ ulimit -s 100000 $ ulimit -i 63645 $ cat / proc / sys / kernel / threads-max 127626 $ cat / proc / sys / vm / max_map_count 600000 $ cat / proc / sys / kernel / pid_max 200000 $ java -Xmx4G -Xss256k -cp. ThreadCreation ... 11542 11543 java.lang.OutOfMemoryError: Es kann kein neuer nativer Thread unter java.lang.Thread.start0 (native Methode) unter java.lang.Thread.start (Thread.java:717) unter ThreadCreation.main ( ThreadCreation.java:15)
Martin Vysny

@MartinVysny ulimit -s = Threadgröße in kb. Sie versuchen also, Threads mit einer Thread-Stapelgröße von 100 MB zu erstellen.
Vladimir Kunschikov

fügte Ihren Vorschlag hinzu, ohne zu überprüfen, @Thomas, danke für das Feedback trotzdem.
Vladimir Kunschikov

2
@VladimirKunschikov Danke Kumpel, deine Lösung hat wirklich funktioniert, und danke Thomas, dass er diese zusätzliche Zeile hinzugefügt hat. Ich kann bestätigen, dass sie ohne diese Zeile nicht funktioniert.
BillHoo

14

@dragosrsupercool

Linux verwendet nicht den virtuellen Speicher, um das Maximum des Threads zu berechnen, sondern den auf dem System installierten physischen RAM

 max_threads = totalram_pages / (8 * 8192 / 4096);

http://kavassalis.com/2011/03/linux-and-the-maximum-number-of-processes-threads/

kernel / fork.c

/* The default maximum number of threads is set to a safe
 * value: the thread structures can take up at most half
 * of memory.
 */
max_threads = mempages / (8 * THREAD_SIZE / PAGE_SIZE);

Thread max unterscheidet sich also zwischen den einzelnen Systemen, da der installierte RAM unterschiedliche Größen haben kann. Ich weiß, dass Linux den virtuellen Speicher nicht vergrößern muss, da wir auf 32 Bit 3 GB für den Benutzerplatz und 1 GB für den Kernel haben. Auf 64-Bit haben wir 128 TB virtuellen Speicher, was unter Solaris der Fall ist. Wenn Sie den virtuellen Speicher erhöhen möchten, müssen Sie Swap-Speicher hinzufügen.


11

So rufen Sie es ab:

cat /proc/sys/kernel/threads-max

So stellen Sie es ein:

echo 123456789 > /proc/sys/kernel/threads-max

123456789 = Anzahl der Threads


Ich bekomme die Erlaubnis verweigert, wenn ich versuche zu schreiben, auch mit root.
Kim

Nun, es ist fast ein Jahrzehnt her, seit dies veröffentlicht wurde. Ich bin nicht auf dem neuesten Stand der Dinge, aber vieles könnte sich geändert haben (und hat sich wahrscheinlich geändert) ...
Vincent Van Den Berghe

Problem mit Perm-Deny kann sein append ( >) Teil verliert die sudo: tryecho 12345678 | sudo tee -a /proc/sys/kernel/threads-max
dwanderson

10

Fadenzahlbegrenzung:

$ cat /proc/sys/kernel/threads-max 

Wie es berechnet wird:

max_threads = mempages / (8 * THREAD_SIZE / PAGE_SIZE);

und: x86_64 Seitengröße (PAGE_SIZE) ist 4K; Wie alle anderen Architekturen verfügt x86_64 über einen Kernel-Stack für jeden aktiven Thread. Diese Thread-Stapel sind THREAD_SIZE (2 * PAGE_SIZE) groß.

für mempages:

cat /proc/zoneinfo | grep spanned | awk '{totalpages=totalpages+$2} END {print totalpages}';

Die Anzahl hängt also nicht mit der Beschränkung der Größe des Thread-Speicherstapels zusammen (ulimit -s ).

PS: Die Beschränkung des Thread-Speicherstapels in meiner Rhel-VM beträgt 10 MB. Für 1,5 GB Speicher kann sich diese VM nur 150 Threads leisten.


5

Für alle, die dies jetzt betrachten, gibt es auf systemd-Systemen (in meinem Fall speziell Ubuntu 16.04) eine weitere Begrenzung, die durch den Parameter cgroup pids.max erzwungen wird.

Dies ist standardmäßig auf 12.288 festgelegt und kann in /etc/systemd/logind.conf überschrieben werden

Es gelten weiterhin andere Hinweise, einschließlich pids_max, threads-max, max_maps_count, ulimits usw.


5

Überprüfen Sie die Stapelgröße pro Thread mit ulimit, in meinem Fall Redhat Linux 2.6:

    ulimit -a
...
    stack size              (kbytes, -s) 10240

Jedem Ihrer Threads wird diese Speichermenge (10 MB) für seinen Stapel zugewiesen. Bei einem 32-Bit-Programm und einem maximalen Adressraum von 4 GB sind das maximal nur 4096 MB / 10 MB = 409 Threads !!! Minus Programmcode minus Heap-Space führt wahrscheinlich zu einem beobachteten max. von 300 Fäden.

Sie sollten in der Lage sein, dies zu erhöhen, indem Sie 64-Bit kompilieren und ausführen oder ulimit -s 8192 oder sogar ulimit -s 4096 einstellen. Aber wenn dies ratsam ist, ist eine andere Diskussion ...


4

Es sollte wahrscheinlich keine Rolle spielen. Sie werden eine viel bessere Leistung erzielen, wenn Sie Ihren Algorithmus so entwerfen, dass eine feste Anzahl von Threads verwendet wird (z. B. 4 oder 8, wenn Sie 4 oder 8 Prozessoren haben). Sie können dies mit Arbeitswarteschlangen, asynchronen E / A oder so etwas wie libevent tun.


3
Der Zweck von Multithreading ist nicht nur die Leistung. Zum Beispiel lauschen Sie 10 Ports mit einem Blockiersystem auf einem 4-Kern-Prozessor. In diesem Beispiel gibt es keine Bedeutung von 4.
Obayhan

3

Verwenden Sie eine nbio nicht blockierende E / A-Bibliothek oder was auch immer, wenn Sie mehr Threads für E / A-Aufrufe dieses Blocks benötigen


2

Abhängig von Ihrem System schreiben Sie einfach ein Beispielprogramm [indem Sie Prozesse in einer Schleife erstellen] und überprüfen Sie es mit ps axo pid, ppid, rss, vsz, nlwp, cmd. Wenn es keine Threads mehr erstellen kann, überprüfe nlwp count [nlwp ist die Anzahl der Threads] voila du hast deine narrensichere Antwort erhalten, anstatt Bücher durchzugehen


1

Um dauerhaft einzustellen,

vim /etc/sysctl.conf

und hinzufügen

kernel.threads-max = "value"

0

Wir können die maximale Anzahl von Threads sehen, die in der folgenden Datei unter Linux definiert sind

cat / proc / sys / kernel / threads-max

(ODER)

sysctl -a | grep threads-max


0

Sie können den aktuellen Wert mit dem folgenden Befehl anzeigen: cat / proc / sys / kernel / threads-max

Sie können den Wert auch wie folgt einstellen

echo 100500> / proc / sys / kernel / threads-max

Der von Ihnen festgelegte Wert wird mit den verfügbaren RAM-Seiten verglichen. Wenn die Thread-Strukturen mehr als 1/8 der verfügbaren RAM-Seiten belegen, wird Thread-Max entsprechend reduziert.


0

Ja, um die Anzahl der Threads zu erhöhen, müssen Sie den virtuellen Speicher erhöhen oder die Stapelgröße verringern. In Raspberry Pi habe ich keine Möglichkeit gefunden, den virtuellen Speicher zu vergrößern, wenn die Stapelgröße von standardmäßig 8 MB auf 1 MB verringert wird. Es werden möglicherweise mehr als 1000 Threads pro Prozess angezeigt, aber die Stapelgröße wird mit dem Befehl "ulimit -s" verringert Machen Sie dies für alle Threads. Meine Lösung war also die Verwendung der Instanz "pthread_t" der "Thread-Klasse", da ich mit "pthread_t" die Stapelgröße für jeden Thread festlegen konnte. Schließlich kann ich in Raspberry Pi mehr als 1000 Threads pro Prozess mit jeweils 1 MB Stapel archivieren.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.