Wenn die Argumentliste zu lang ist (denken Sie daran, dass * zu einer Liste aller Dateien erweitert wird, die dem Glob entsprechen), können Sie sie umgehen, indem Sie z . B. IFS="\n" for file in /src/*; do mv "$file" /dst/; doneoder verwenden rsync -a /src/ /dst/.
DopeGhoti
Antworten:
18
Dies hängt stark vom System und der Version, von der Anzahl und Größe der Argumente sowie von der Anzahl und Größe der Umgebungsvariablennamen ab.
Traditionell lag das Limit (wie von Unix angegeben getconf ARG_MAX) mehr oder weniger bei der kumulierten Größe von:
Die Länge der Argumentzeichenfolgen (einschließlich der Beendigung '\0')
Die Länge des Array von Zeigern auf diese Zeichenfolgen, also normalerweise 8 Bytes pro Argument in einem 64-Bit-System
Die Länge der Umgebungszeichenfolgen (einschließlich der Beendigung '\0'), wobei eine Umgebungszeichenfolge gemäß Konvention so etwas wie ist var=value.
Die Länge des Array von Zeigern auf diese Zeichenfolgen, also normalerweise 8 Bytes pro Argument in einem 64-Bit-System
Denken Sie daran, dass dies cpauch als Argument gilt (ist das erste Argument).
Unter Linux hängt es von der Version ab. Das Verhalten dort hat sich kürzlich geändert, wo es kein fester Raum mehr ist.
Bei der Überprüfung unter Linux 3.11 wird getconf ARG_MAXjetzt ein Viertel des für die Stapelgröße festgelegten Grenzwerts angegeben (128 KB, wenn dies weniger als 512 KB sind).
Diese Grenze liegt in der kumulativen Größe der Argument- und Umgebungszeichenfolgen und in einem gewissen Overhead (ich vermute aufgrund der Berücksichtigung der Ausrichtung an den Seitengrenzen). Die Größe der Zeiger wird nicht berücksichtigt.
Auf der Suche nach dem Limit bekomme ich:
$ /bin/true {1..164686}
$ /bin/true {1..164687}
zsh: argument list too long: /bin/true
$ x= /bin/true {1..164686}
$ x=1 /bin/true {1..164686}
zsh: argument list too long: /bin/true
Die maximale kumulative Größe vor dem Brechen in diesem Fall ist:
Das bedeutet nicht, dass Sie 1 Million leere Argumente übergeben können. Auf einem 64-Bit-System ergeben 1 Million leere Argumente eine Zeigerliste von 8 MB, was über meiner Stapelgröße von 4 MB liegen würde.
(Sie werden feststellen, dass es sich nicht um einen E2BIG-Fehler handelt. Ich bin mir nicht sicher, an welchem Punkt der Prozess dort abgebrochen wird, wenn er sich innerhalb des execveSystemaufrufs oder später befindet.)
Beachten Sie auch (immer noch unter Linux 3.11), dass die maximale Größe eines einzelnen Arguments oder einer Umgebungszeichenfolge 128 KB beträgt, unabhängig von der Größe des Stapels.
$ /bin/true ${(l.131071..a.)${:-}} # 131072 OK
$ /bin/true ${(l.131072..a.)${:-}} # 131073 not
zsh: argument list too long: /bin/true
$ /bin/true ${(l.131071..a.)${:-}} ${(l.131071..a.)${:-}} # 2x 131072 OK
Kannst du bitte teilen, wie bist du auf die 164686Nummer gekommen? dh wie haben Sie berechnet, dass die Sequenz unter der 2097152Größe ARG_MAX liegen würde ?
Sergiy Kolodyazhnyy
14
Dies hängt vom Wert von ARG_MAX ab, der sich zwischen den Systemen ändern kann. So ermitteln Sie den Wert für Ihren Systemlauf (zeigen Sie das Ergebnis auf meinem als Beispiel):
$ getconf ARG_MAX
2097152
Dies hat nichts mit cpIhrer Shell zu tun. Es ist eine vom Kernel auferlegte Grenze. Es werden keine ( exec()) Befehle ausgeführt, wenn ihre Argumente länger als sind ARG_MAX. Wenn also die Länge der Argumentliste, die Sie angegeben haben, cpgrößer als ARG_MAX ist, wird der cpBefehl überhaupt nicht ausgeführt.
Um Ihre Hauptfrage zu beantworten, cpwerden keine Dateien verarbeitet, da sie niemals mit so vielen Argumenten ausgeführt werden. Ich sollte auch erwähnen, dass dies nicht von der Anzahl der Argumente abhängt, sondern von ihrer Länge. Möglicherweise haben Sie das gleiche Problem mit sehr wenigen, aber sehr langen Dateinamen.
Um diese Fehler zu umgehen, führen Sie Ihren Befehl in einer Schleife aus:
IFS="\n" for file in /src/*; do mv "$file" /dst/; done
oder verwendenrsync -a /src/ /dst/
.Antworten:
Dies hängt stark vom System und der Version, von der Anzahl und Größe der Argumente sowie von der Anzahl und Größe der Umgebungsvariablennamen ab.
Traditionell lag das Limit (wie von Unix angegeben
getconf ARG_MAX
) mehr oder weniger bei der kumulierten Größe von:'\0'
)'\0'
), wobei eine Umgebungszeichenfolge gemäß Konvention so etwas wie istvar=value
.Denken Sie daran, dass dies
cp
auch als Argument gilt (ist das erste Argument).Unter Linux hängt es von der Version ab. Das Verhalten dort hat sich kürzlich geändert, wo es kein fester Raum mehr ist.
Bei der Überprüfung unter Linux 3.11 wird
getconf ARG_MAX
jetzt ein Viertel des für die Stapelgröße festgelegten Grenzwerts angegeben (128 KB, wenn dies weniger als 512 KB sind).(
zsh
Syntax unten):Diese Grenze liegt in der kumulativen Größe der Argument- und Umgebungszeichenfolgen und in einem gewissen Overhead (ich vermute aufgrund der Berücksichtigung der Ausrichtung an den Seitengrenzen). Die Größe der Zeiger wird nicht berücksichtigt.
Auf der Suche nach dem Limit bekomme ich:
Die maximale kumulative Größe vor dem Brechen in diesem Fall ist:
Das bedeutet nicht, dass Sie 1 Million leere Argumente übergeben können. Auf einem 64-Bit-System ergeben 1 Million leere Argumente eine Zeigerliste von 8 MB, was über meiner Stapelgröße von 4 MB liegen würde.
(Sie werden feststellen, dass es sich nicht um einen E2BIG-Fehler handelt. Ich bin mir nicht sicher, an welchem Punkt der Prozess dort abgebrochen wird, wenn er sich innerhalb des
execve
Systemaufrufs oder später befindet.)Beachten Sie auch (immer noch unter Linux 3.11), dass die maximale Größe eines einzelnen Arguments oder einer Umgebungszeichenfolge 128 KB beträgt, unabhängig von der Größe des Stapels.
quelle
164686
Nummer gekommen? dh wie haben Sie berechnet, dass die Sequenz unter der2097152
Größe ARG_MAX liegen würde ?Dies hängt vom Wert von ARG_MAX ab, der sich zwischen den Systemen ändern kann. So ermitteln Sie den Wert für Ihren Systemlauf (zeigen Sie das Ergebnis auf meinem als Beispiel):
Dies hat nichts mit
cp
Ihrer Shell zu tun. Es ist eine vom Kernel auferlegte Grenze. Es werden keine (exec()
) Befehle ausgeführt, wenn ihre Argumente länger als sindARG_MAX
. Wenn also die Länge der Argumentliste, die Sie angegeben haben,cp
größer als ARG_MAX ist, wird dercp
Befehl überhaupt nicht ausgeführt.Um Ihre Hauptfrage zu beantworten,
cp
werden keine Dateien verarbeitet, da sie niemals mit so vielen Argumenten ausgeführt werden. Ich sollte auch erwähnen, dass dies nicht von der Anzahl der Argumente abhängt, sondern von ihrer Länge. Möglicherweise haben Sie das gleiche Problem mit sehr wenigen, aber sehr langen Dateinamen.Um diese Fehler zu umgehen, führen Sie Ihren Befehl in einer Schleife aus:
quelle
C
Probleme mit ARG_MAX und wirklich langen Dateinamen haben können?