Was ist zu tun, wenn der Befehl "ls" nicht funktioniert?

15

Ich habe versucht, den lsBefehl zu verwenden und habe einen Fehler erhalten:

bash: /bin/ls: cannot execute binary file

Was kann ich anstelle dieses Befehls verwenden?

jimmij
quelle
Vielleicht haben Sie Ihren libc*sooder Ihrenld-linux*so
Basile Starynkevitch
31
Persönlich würde ich mich darauf konzentrieren, mein System zu reparieren, es sei denn, dies ist ein verrücktes Gedankenexperiment.
Faheem Mitha
2
@BasileStarynkevitch noch nie davon gehört, aber Busybox ist allgemein verfügbar und kann
einspringen
8
... eine Systemrettungs-CD?
Federico Poloni
1
Eine Frage zur Behebung des eigentlichen Problems in solchen Fällen lautet superuser.com/questions/435988 . Und weit davon entfernt, ungewöhnlich zu sein, sashist es unter Ubuntu Linux als Shells / Sash im FreeBSD-Ports-Tree, als Gentoo-Paket und an anderen Orten, einschließlich direkt vom Autor , verfügbar .
JdeBP,

Antworten:

32

Sie können die Befehle echooder findanstelle von ls:

echo *

oder:

find -printf "%M\t%u\t%g\t%p\n"
Aufrufer
quelle
7
Ich würde verwendenecho -- *
Edward Torvalds
9
@Invoker: Wenn -nim aktuellen Verzeichnis eine Datei aufgerufen wird, wird diese als Flag interpretiert und nicht als Echo.
MvG,
2
Es wäretouch ./-n
Basile Starynkevitch
1
@Invoker Auf die alphabetische Reihenfolge kommt es an. Führen Sie diesen Oneliner für einen Fall aus, in dem dies einen Unterschied macht:rm -rf /tmp/foo && mkdir /tmp/foo && cd /tmp/foo && touch ./-n oops && set -x && ls && echo *
jlliagre
3
echoscheint nicht zu Ehre --, per se . Wie ist es echo -- *besser als echo "" *oder noch besser echo "The file(s) are:" *?
G-Man sagt, dass Monica am
24

Sie können auch den printfBefehl anstelle von echo verwenden:

printf '%s\n' *

printfüberlegen ist echoin dieser Situation, dass echosie nicht den „doppelten Bindestrichs“ (Achtung --) bedeutet das Ende der Argumentliste (auf einigen Systemen, darunter Ubuntu 14.04 , die getestet es auf dem , was ich):

llama@llama:~$ mkdir -p Misc/unix210948
llama@llama:~$ cd !$
cd Misc/unix210948
llama@llama:~/Misc/unix210948$ touch -- -n
llama@llama:~/Misc/unix210948$ ls
-n
llama@llama:~/Misc/unix210948$ echo *
llama@llama:~/Misc/unix210948$ echo -- *
-- -n
llama@llama:~/Misc/unix210948$ printf '%s\n' *
-n

In diesem Fall können Sie mit nicht das gewünschte Ergebnis erzielen echo(da eine aufgerufene Datei -nals Option interpretiert wird und der doppelte Bindestrich nicht funktioniert, müssen Sie verwenden printf).

Beachten Sie, dass Sie im Umgang mit unbekannten Daten immer einen Formatstring wie oben verwenden sollten printf, da Sie sonst unerwartete Ergebnisse erhalten könnten (danke an @ G-Man für den Hinweis in den Kommentaren!):

llama@llama:~/Misc/unix210948$ rm ./-n
llama@llama:~/Misc/unix210948$ touch '\n'
llama@llama:~/Misc/unix210948$ ls
\n
llama@llama:~/Misc/unix210948$ printf -- *

llama@llama:~/Misc/unix210948$ printf '%s\n' *
\n

Eine aufgerufene Datei \nwird von als Newline interpretiert printf. Um dies zu vermeiden, verwenden wir einen Formatierungsstring für printf( %s) und übergeben ihm die Namen der Dateien (wie zuvor durch Globbing erweitert).

Diese printf+ Formatierung String - Lösung kann eine Vielzahl von Dateinamen umgehen (und auch behandelt „versteckt“ Dateien, das heißt, diejenigen mit einem Start ., den gleichen wie ls):

llama@llama:~/Misc/unix210948$ rm ./*
zsh: sure you want to delete all the files in /home/llama/Misc/unix210948/. [yn]? y
llama@llama:~/Misc/unix210948$ touch -- '-n' '\n' 'name with spaces' '.hidden'
llama@llama:~/Misc/unix210948$ ls
-n  \n  name with spaces
llama@llama:~/Misc/unix210948$ printf '%s\n' *
-n
\n
name with spaces

Wenn Sie dies printfunterstützen %q, können Sie auch that ( printf '%q\n' *) verwenden. Dadurch werden Leerzeichen, Zeilenumbrüche usw. ausgeblendet, wenn Ihre Dateinamen seltsame Zeichen enthalten. (Danke an @muru im Chat für den Hinweis !)

Türknauf
quelle
2
Wenn sie mit unbekannten Daten zu tun, sollten Sie immer verwenden '%s'(mit \nund / oder jede andere Konstante gewünschten Text). Probieren Sie zum Beispiel die Befehle aus touch '%.0s' foo bar; ls; printf -- *. Umgekehrt verstehe ich nicht, warum Sie brauchen, --wenn Sie eine '%s\n'Formatzeichenfolge haben.
G-Man sagt, dass Monica am
@ G-Man Guter Punkt! Danke, ich habe das Unnötige --mit der Formatzeichenfolge übersehen und meinen Beitrag bearbeitet, um das andere zu adressieren.
Türknauf
Der -nDateiname ehrlich soll nicht ein Problem für ein POSIX-2001 sein + echo- auf SUSv3 Systemen der echoDienstprogramm erforderlich keine Optionen überhaupt zu akzeptieren. bashs echound einige andere behandeln die Option zwar, bashkönnen jedoch mit der Build-Option kompiliert werden --enable-xpg-echo-default, damit sie sich die ganze Zeit über richtig verhält. Richtiges Verhalten echobedeutet jedoch, dass die Argumente immer mit einem Flankenspiel versehen werden. Daher würde jeder Dateiname mit einem C-Escape nicht mit Wiedergabetreue ausgegeben - er echowürde übersetzt.
mikeserv
2
bitte, bitte, jeder sollte aufhören zu empfehlen '-', wenn die Unix-FAQ seit mehr als 10 Jahren erklärt, dass die Verwendung von "./" besser und portabler ist (funktioniert mit allen Programmen, auch mit den (vielen), die nicht funktionieren '- ')
Olivier Dulac
1
@OliverDulac - nicht einmal das würde helfen [w / ein Konformist echo.
mikeserv
8

Sie sollten wahrscheinlich die Hilfsprogramme fileund verwenden uname, um eine bessere Vorstellung davon zu bekommen, was zum Teufel mit Ihrer Maschine los ist. Ihr Fehler weist auf eine ausführbare Binärdatei hin, die für eine Systemarchitektur kompiliert wurde, die mit der nicht kompatibel ist, für die sie aufgerufen wurde.

Auf meiner Maschine:

uname -m; file /bin/ls

... druckt ...

x86_64
/bin/ls: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, for GNU/Linux 2.6.32, BuildID[sha1]=..., stripped

... weil dort alles in Ordnung mit der Welt ist. Hier ist jedoch eine kleine Auswahl von Befehlen, die von meinem Android-Tablet auf einer sshVerbindung zu meinem Desktop ausgeführt werden ...

#first copy android ls to desktop
scp /system/bin/ls "$ssh:arm_ls"

ls               100%  151KB 151.4KB/s   00:00

#next login to desktop and run the following
ssh "$ssh" '
   HOME=./arm_ls
   chmod +x ~
   file ~
   bash -c ~ ||
   rm ~
'

./arm_ls: ELF 32-bit LSB shared object, ARM, EABI5 version 1 (SYSV), dynamically linked, interpreter /system/bin/linker, stripped
bash: ./arm_ls: cannot execute binary file: Exec format error
mikeserv
quelle
Dies ist eine großartige Antwort, die ein Szenario abdeckt und die mögliche zugrunde liegende Ursache anspricht.
Pranab,
falsch verstanden ^^ sorry. Warum nicht einfach die Datei kopieren und verwenden? Warum das ganze Homedir-Ding? scp zu desktop, datei drauf und bash ./it?
Olivier Dulac
@OlivierDulac -hmm .. Ich bin nicht sicher, ob ich eine Ahnung habe, was du genau fragst. Die HOME=Sache ist, dass ich einfach ~ein paar Mal machen kann, anstatt ./arm_ls - aus Bequemlichkeitsgründen. Der springende Punkt der Übung ist, dass ich die Arm-Binärdatei auf meinem x86-Desktop nicht verwenden kann, und ich wollte, dass die Ausgabe von filezeigt, dass es eine sehr andere Art von Binärdatei ist als die systemeigene - die oben gezeigt wird. Und so entschied ich mich, anstatt eine ganze Cross-Kompilierung zu erstellen, eine inkompatible Binärdatei, die mir auf meinem Arm Dev zur Verfügung stand, auf mein x86-Gerät zu kopieren und die Ergebnisse und die bashFehlerbehebung zu zeigen.
mikeserv
1
oh, es war nur um ein paar tippen zu sparen? OK, aber ich denke, es macht es verwirrender als es sein sollte (es ist kein Codegolf ^^)
Olivier Dulac
1
@OliverDulac - natürlich ist es kein Code-Gold, aber es ist praktisch, es ist überhaupt nicht mehrdeutig und ich hasse es, mit dem Daumen zu tippen.
mikeserv
5

Mit bash (oder vielen anderen Shells) können Sie die Tabulatorvervollständigung verwenden, um Dateien aufzulisten:

$ thisisnotacommand ./public_html/<TAB>
acc/              papers/           android/          l/
sdr/              blast             formalcss.html    switch/
busy/             formalcss.tar.gz  others/           together.jpg
user1998586
quelle
3

Wenn Sie etwas Ähnliches wünschen ls -l(Dateigröße, Berechtigungen, Eigentümer, Zeitstempel usw.), stat -- *kann dies hilfreich sein:

$ ls -l
total 8
-rw-rw-r-- 1 ubuntu ubuntu   4 Jun 20 21:50 a.txt
-rw-rw-r-- 1 ubuntu ubuntu 279 Jun 20 21:50 b.txt
$ stat -- *
  File: ‘a.txt’
  Size: 4           Blocks: 8          IO Block: 4096   regular file
Device: 801h/2049d  Inode: 787691      Links: 1
Access: (0664/-rw-rw-r--)  Uid: ( 1000/  ubuntu)   Gid: ( 1000/  ubuntu)
Access: 2015-06-20 21:50:23.395223851 -0700
Modify: 2015-06-20 21:50:23.395223851 -0700
Change: 2015-06-20 21:50:23.395223851 -0700
 Birth: -
  File: ‘b.txt’
  Size: 279         Blocks: 8          IO Block: 4096   regular file
Device: 801h/2049d  Inode: 844130      Links: 1
Access: (0664/-rw-rw-r--)  Uid: ( 1000/  ubuntu)   Gid: ( 1000/  ubuntu)
Access: 2015-06-20 21:50:31.763084155 -0700
Modify: 2015-06-20 21:50:51.066758216 -0700
Change: 2015-06-20 21:50:51.066758216 -0700
 Birth: -
$ 

Alternativ, wenn alles, was Sie tun wollten, eine falsche Schreibweise lsist versuchen Sie es slstattdessen . ;-) (weitermachen - probieren Sie es aus ... möglicherweise müssen Sie es installieren)

Digitales Trauma
quelle
3

Auf vielen Systemen ist ein sehr ähnliches Dienstprogramm verfügbar:

dir

Laut den Infoseiten ist es äquivalent zu ls -C -b, aber es ist eine eigenständige Binärdatei.

Der Vorteil der Verwendung dir (anstelle von beispielsweise einem Shell-Vervollständigungssystem) besteht in der Verfügbarkeit verschiedener Optionen wie Sortieren, Anzeigen versteckter Dateien, Färben usw., genau wie im Standardprogramm ls.

Übrigens, ich denke, der Name kommt von Windows (oder besser gesagt DOS).

jimmij
quelle
1

verwenden

 echo -- *
    find . -printf "%M\t%u\t%g\t%p\n"
    ls -C -b

quelle