GNU/Linux >> Znalost Linux >  >> Linux

Ukončovací kódy příkazového řádku Bash byly demystifikovány

Když spustíte příkaz nebo skript, obdržíte kód ukončení . Ukončovací kód je systémová odpověď, která hlásí úspěch, chybu nebo jiný stav, který poskytuje vodítko o tom, co způsobilo neočekávaný výsledek vašeho příkazu nebo skriptu. O kódu se však možná nikdy nedozvíte, protože výstupní kód se neprozradí, dokud ho o to někdo nepožádá. Programátoři používají výstupní kódy k ladění svého kódu.

Poznámka: Často uvidíte kód ukončení označované jako stav ukončení nebo dokonce jako kódy stavu ukončení . Termíny se používají zaměnitelně s výjimkou dokumentace. Doufám, že vám mé použití těchto dvou výrazů bude jasné.

Nejsem programátor. Je pro mě těžké to přiznat, ale je to tak. Studoval jsem BASIC, FORTRAN a pár dalších jazyků formálně i neformálně a musím říct, že rozhodně nejsem programátor. Jistě, umím trochu skriptovat a programovat v PHP, Perlu, Bash a dokonce PowerShellu (ano, jsem také správce Windows), ale nikdy bych se programováním nemohl živit, protože jsem příliš pomalý v psaní kódu a pokus-omyl není účinná strategie ladění. Je to smutné, opravdu, ale jsem dostatečně kompetentní v kopírování a přizpůsobování nalezeného kódu, abych mohl splnit své požadované úkoly. A přesto také používám výstupní kódy, abych zjistil, kde jsou mé problémy a proč se věci nedaří.

[ Také by se vám mohlo líbit: Malé kouzlo kopírování souborů SSH na příkazovém řádku. ]

Výstupní kódy jsou do určité míry užitečné, ale mohou být také vágní. Například výstupní kód 1 je obecný segment pro různé chyby a není vůbec užitečný. V tomto článku vysvětluji několik rezervovaných chybových kódů , jak k nim může dojít a jak je použít, abyste zjistili, jaký je váš problém. Vyhrazený chybový kód je kód, který používá Bash a neměli byste vytvářet vlastní chybové kódy, které jsou s nimi v konfliktu.

Dost vyprávění. Je čas podívat se na příklady toho, co generuje chybové kódy/stavy.

Extrahování nepolapitelného výstupního kódu

Chcete-li zobrazit kód ukončení posledního příkazu, který jste spustili na příkazovém řádku, použijte následující příkaz:

$ echo $?

Zobrazená odpověď neobsahuje žádnou okázalost ani okolnost. Je to jen číslo. Můžete také obdržet chybovou zprávu shellu od Bash, která dále popisuje chybu, ale kód ukončení a chyba shellu by vám měly pomoci zjistit, co se pokazilo.

Stav ukončení 0

Výstupní stav 0 je obecně nejlepší možný scénář. Říká vám, že váš poslední příkaz nebo skript byl úspěšně proveden. Úspěch je relativní, protože výstupní kód vás pouze informuje, že skript nebo příkaz byly provedeny správně, ale výstupní kód vám neřekne, zda informace z něj mají nějakou hodnotu. Příklady lépe ilustrují to, co popisuji.

Například seznam souborů ve vašem domovském adresáři. Ve svém domovském adresáři nemám nic jiného než skryté soubory a adresáře, takže zde není nic k vidění, ale ukončovací kód se nestará o nic jiného než o úspěch provedení příkazu:

$ ls
$ echo $?
0

Výstupní kód 0 znamená, že ls příkaz běžel bez problémů. I když, opět, informace z výstupního kódu pro mě nemají žádnou skutečnou hodnotu.

Nyní spusťte ls příkaz v /etc adresář a poté zobrazte ukončovací kód:

$ ls /etc
**Many files**
$ echo $?
0

Můžete vidět, že každé úspěšné provedení má za následek návratový kód 0, včetně něčeho, co je zcela nesprávné, jako je například vydání cat příkaz na binárním spustitelném souboru, jako je ls příkaz: 

$ cat /usr/bin/ls
**A lot of screen gibberish and beeping**
$ echo $?
0

Stav ukončení 1

Použijeme výše uvedený příklad, ale přidáme dlouhý výpis a rekurzivní možnosti (-lR ), obdržíte nový výstupní kód 1:

$ ls -lR /etc
**A lengthy list of files**
$ echo $?
1

Přestože výstup příkazu vypadá, jako by vše proběhlo v pořádku, pokud rolujete nahoru, uvidíte ve výpisu několik chyb „Povolení odepřeno“. Tyto chyby mají za následek stav ukončení 1, který je popsán jako „nepřípustné operace“. Ačkoli byste mohli očekávat, že chyba „Oprávnění odepřeno“ povede ke stavu ukončení 1, mýlili byste se, jak uvidíte v další části.

Dělení nulou vám však dá výstupní stav 1. Také obdržíte chybu od shellu, abyste věděli, že operace, kterou provádíte, je „nepřípustná:“

$ let a=1
$ let b=0
$ let c=a/b
-bash: let: c=a/b: division by 0 (error token is "b")
$ echo $?
1

Bez chyby shellu není stav ukončení 1 příliš užitečný, jak můžete vidět z prvního příkladu. Ve druhém příkladu víte, proč jste obdrželi chybu, protože Bash vám to sdělí chybovou zprávou shellu. Obecně platí, že když obdržíte výstupní stav 1, vyhledejte nepovolené operace (Povolení odepřeno zprávy) smíšené s vašimi úspěchy (jako je vypsání všech souborů pod /etc , jako v prvním příkladu v této sekci).

Stav ukončení 2

Jak je uvedeno výše, upozornění shellu „Oprávnění odepřeno“ má za následek stav ukončení 2 místo 1. Chcete-li to sami prokázat, zkuste uvést soubory v /root :

$ ls /root
ls: cannot open directory '/root': Permission denied
$ echo $?
2

Stav opuštění 2 se zobrazí, když se vyskytne problém s oprávněními nebo chybí klíčové slovo v příkazu nebo skriptu. Příklad chybějícího klíčového slova je zapomenutí přidat donedo skriptu smyčka. Nejlepší metodou pro ladění skriptů s tímto stavem ukončení je zadat příkaz v interaktivním prostředí, abyste viděli chyby, které obdržíte. Tato metoda obecně odhalí, kde je problém.

Problémy s oprávněními je o něco méně obtížné dešifrovat a ladit než jiné typy problémů. Jediná věc, "Oprávnění odepřeno" znamená, že se váš příkaz nebo skript pokouší porušit omezení oprávnění.

Stav ukončení 126

Exit status 126 je zajímavý kód chyby oprávnění. Nejjednodušší způsob, jak demonstrovat, když se tento kód objeví, je vytvořit soubor skriptu a zapomenout dát tomuto souboru oprávnění ke spuštění. Zde je výsledek:

$ ./blah.sh
-bash: ./blah.sh: Permission denied
$ echo $?
126

Tento problém s oprávněním není problém přístupu, ale problém nastavení, jako v režimu. Chcete-li se této chyby zbavit a místo toho získat stav ukončení 0, zadejte chmod +x blah.sh .

Poznámka: Obdržíte stav ukončení 0, i když spustitelný soubor nemá žádný obsah. Jak již bylo řečeno dříve, „úspěch“ je otevřen interpretaci.

Zobrazuje se mi stav ukončení 126. Tento kód mi ve skutečnosti říká, co je špatně, na rozdíl od vágnějších kódů.

Stav ukončení 127

Návratový stav 127 vám říká, že se stala jedna ze dvou věcí: Buď příkaz neexistuje, nebo příkaz není ve vaší cestě ($PATH ). Tento kód se také zobrazí, pokud se pokusíte provést příkaz, který je ve vašem aktuálním pracovním adresáři. Například výše uvedený skript, kterému jste udělili oprávnění ke spuštění, je ve vašem aktuálním adresáři, ale pokusíte se skript spustit, aniž byste uvedli, kde se nachází:

$ blah.sh
-bash: blah.sh: command not found
$ echo $?
127

Pokud k tomuto výsledku dojde ve skriptu, zkuste přidat explicitní cestu k problémovému spustitelnému souboru nebo skriptu. Pravopis se také počítá při specifikování spustitelného souboru nebo skriptu.

[ Čtenáři si také užili: 10 základních příkazů Linuxu, které potřebujete znát. ]

Stav ukončení 128

Výstupní stav 128 je odpověď přijatá, když je při programování použit výstupní kód mimo rozsah. Podle mých zkušeností nelze stav opuštění 128 vytvořit. Vyzkoušel jsem například několik akcí a nedaří se mi to. Mohu však vytvořit kód přilehlého ke stavu ukončení 128. Pokud váš výstupní kód překročí 256, vrácený výstupní stav je váš výstupní kód odečtený o 256. Tento výsledek zní zvláštně a ve skutečnosti může vytvořit nesprávný výstupní stav. Podívejte se na příklady a přesvědčte se sami.

Pomocí výstupního kódu 261 vytvořte výstupní stav 5:

$ bash
$ exit 261
exit
$ echo $?
5

Pro vytvoření chybného výstupního stavu 0:

$ bash
$ exit 256
exit
$ echo $?
0

Pokud jako kód opuštění použijete 257, váš stav opuštění je 1 a tak dále. Pokud je výstupní kód záporné číslo, výsledný výstupní stav je toto číslo odečtené od 256. Pokud je tedy váš výstupní kód 20, je výstupní stav 236.

Znepokojující, že? Řešením pro mě je vyhnout se používání výstupních kódů, které jsou rezervované a mimo rozsah. Správný rozsah je 0-255.

Stav ukončení 130

Pokud spouštíte program nebo skript a stisknutím kláves Ctrl-C jej zastavíte, váš stav ukončení je 130. Tento stav lze snadno demonstrovat. Vydání ls -lR / a poté okamžitě stiskněte Ctrl-C:

$ ls -lR /
**Lots of files scrolling by**
^C
$ echo $?
130

K tomuhle se toho moc říct nedá. Není to příliš užitečný stav ukončení, ale zde je pro vaši informaci.

Stav ukončení 255

Tento konečný stav rezervovaného ukončení lze snadno vytvořit, ale je obtížné jej interpretovat. V dokumentaci, kterou jsem našel, se uvádí, že obdržíte výstupní stav 255, pokud použijete výstupní kód, který je mimo rozsah 0-255.

Zjistil jsem, že tento status lze vyrobit i jinak. Zde je jeden příklad:

$ ip
**Usage info for the ip command**
  
$ echo $?
255

Některé nezávislé autority říkají, že 255 je obecný chybový kód. Toto tvrzení nemohu potvrdit ani vyvrátit. Vím pouze, že mohu vytvořit návratový stav 255 spuštěním konkrétních příkazů bez voleb.

[ Související článek: 10 dalších základních příkazů Linuxu, které potřebujete znát. ]

Koneckonců

Tady to máte:Přehled čísel rezervovaných výstupních stavů, jejich významů a způsobu jejich generování. Moje osobní rada je vždy zkontrolovat oprávnění a cesty pro cokoli, co spustíte, zejména ve skriptu, místo toho, abyste se spoléhali na kódy stavu ukončení. Moje metoda ladění spočívá v tom, že když příkaz ve skriptu nefunguje správně, spustím jej individuálně v interaktivním prostředí. Tato metoda funguje mnohem lépe než zkoušet luxusní taktiky s přestávkami a výjezdy. Vydávám se touto cestou, protože (většinou) moje chyby souvisí s oprávněními, takže jsem byl vycvičen, abych začal tam.

Bavte se kontrolou svých stavů a ​​teď je čas, abych skončil.

[ Chcete si vyzkoušet Red Hat Enterprise Linux? Stáhněte si ji nyní zdarma. ]


Linux
  1. Bash tipy pro každý den na příkazovém řádku

  2. Jak vymazat historii příkazového řádku BASH v Linuxu

  3. Rozdíl mezi ‚A‘ na příkazovém řádku (bash)??

  1. 5 Standardní dokončení K dispozici v příkazovém řádku Linux Bash

  2. Výstupní kód přiřazení proměnné k substituci příkazu v Bash

  3. Bash:Smyčka, dokud se stav ukončení příkazu nerovná 0

  1. Rozdíl mezi operátory Bash [[ Vs [ Vs ( Vs ((?

  2. Jak vyhledat výstupní kódy pro aplikace?

  3. Co dělá -e v bash shebang?