Hlavní navigace

Triky pro začátečníky (6)

28. 8. 2000
Doba čtení: 4 minuty

Sdílet

Posledně jsem trochu nakousnul přesměrování standardního vstupu a výstupu. Dnes si tuto výbornou vlastnost probereme trochu důkladněji. Předem ale upozorňuji, že se uvedené příklady budou týkat především bashe a v jiných shellech (Korn shell, C shell) vám nemusí fungovat (většinou budou).

Představte si situaci, kdy potřebujete zachytit výsledek příkazu do souboru, abyste si jej mohli později prohlédnout či nějak zpracovat. Například instalujete program ze zdrojových textů a chcete vědět, co při tom dělá. Nejjistějším způsobem je prohlédnout si Makefile, ale některé rozsáhlé produkty mají neméně dlouhé Makefily a navíc, pokud neznáte syntaxi tohoto užitečného souboru, stejně nic nepochopíte. Pokud instalace probíhá neinteraktivně (instalátor se vás na nic neptá), stačí napsat make install > vystup. V souboru vystup pak najdete vše, co se při instalaci zapisovalo na standardní výstup. Pak již není problém hledat spouštění příkazů install, cp, mv, rm, chmod apod.

Teď už víte, že jeden znak většítka () přesměruje standardní výstup z programu do souboru. Většina unixových filtrů spoléhá na toto chování. Takže pokud chcete vytvořit animovaný gif, použijete něco jako gifsicle -lforever -d110 -O2 out*gif > banner.gif. Velký pozor si ale musíte dávat, pokud manipulujete s jediným souborem. Pokud chcete provést transformaci na souboru, NESMÍTE výstup z filtru přesměrovat do stejného souboru, který se zároveň používá pro vstup dat. Shell totiž ještě před spuštěním příkazu vytvoří výstupní soubor a pokud existuje, zkrátí jeho velikost na nulu. Takže například použití příkazu cstocs 1250 il2 soubor.txt > soubor.txt se rovná ztrátě všech dat v daném souboru. Správný tvar výše zmíněného příkazu je cstocs 1250 il2 soubor.txt > soubor.tmp; mv soubor.tmp soubor.txt a převede soubor v kódování Windows do kódování ISO-8859–2, které používá Linux. Ještě teď si vzpomínám na okamžik, kdy jsem poprvé objevil toto chování shellu. Tehdy jsem několik dnů ručně upravoval naskenovaný obrázek a pak jsem v něm chtěl změnit jednu barvu na průhlednou příkazem giftrans …

Většítko se dá použít i na vytváření prázdných souborů či mazání obsahu existujících souborů. Příkaz > soubor.txt vytvoří soubor soubor.txt o velikosti 0 bytů. Pokud tento soubor existoval, bude jeho délka zkrácena na 0 bytů. Toho se dá úspěšně využít na mazání logovacích souborů, pokud nepoužíváte sofistifikovanější řešení logrotate. Například je už soubor .xsession-errors příliš dlouhý? Zkraťme jej příkazem > .xsession-errors. Mohli bychom sice použít rm, ale některé prográmky špatně nesou neexistenci svých souborů.

Nebyl by to Unix, kdyby neexistovala i jiná cesta, jak vytvořit prázdný soubor a tou je příkaz touch. Touch dělá přesně to, co napovídá jeho název, tedy dotkne se souboru, změní čas posledního přístupu a poslední změny na současnost, ale jinak soubor nemění, ani nemaže. Pouze pokud soubor neexistuje, tak jej vytvoří (prázdný, ovšem). Malý příklad syntaxe vám ukáže, jak se můžete dotknout nebe :-) : touch nebe.

Někdy se vám ale nemusí hodit chování většítka, které vždy přepisuje soubor. Třeba byste byli spokojenější, kdyby se nový obsah připsal na konec souboru. Žádný problém, místo jednoho většítka použijte většítka dvě. Například cat hesla.txt >> jak_se_stat_c­rackerem.txt připojí obsah souboru hesla.txt na konec souboru jak_se_stat_c­rackerem.txt.

Možná trochu programujete a tak vás napadlo, že pokud je možné přesměrovat standardní výstup, musí jít přesměrovat i standardní chybový výstup. Trefa. Jde to. Jedinou změnou oproti normálnímu přesměrování je přidání čísla 2 před většítko. Například příkaz make 2> chyby.txt uloží do souboru chyby.txt hlášení všech chyb při kompilaci. Pro zajímavost vám ukážu skript, který používám při kompilování jádra:

#!/bin/bash
cd /usr/src/linux
make clean
make dep
echo "make bzImage" > chyba_kompilace
make bzImage 2>> chyba_kompilace || exit 1
beep
echo "make modules" >> chyba_kompilace
make modules 2>> chyba_kompilace || exit 1
beep
echo "make modules_install" >> chyba_kompilace
make modules_install 2>> chyba_kompilace || exit 1
echo "Done." >> chyba_kompilace
beep

Po skončení si stačí prohlédnout soubor chyba_kompilace a hned vidím všechna varování i chyby. Beep je malá utilitka, která vyloudí skřeky ze systémového reproduktoru. Pokud má o ni někdo zájem, pak má smůlu, o zdrojáky jsem přišel a už si nepamatuji, jak jsem ji vytvořil. Pokud nepotřebujete vidět standardní chybový výstup, tak jej přesměrujte do /dev/null, kde se zaručeně ztratí.

Někdy se hodí přesměrovat do souboru jak standardní výstup, tak i standardní chybový výstup. V bashi stačí dát před většítko ampersand: &, například ls -l neexistující_soubor /tmp &>vystup.txt.

Když je možné si takhle hrát s přesměrováním výstupu z příkazů, musí to jít i se vstupem. Jednoduše napíšete za příkaz menšítko a název souboru, který má nahradit standardní vstup. Program pak nebude číst pokyny či data z terminálu, ale ze zvoleného souboru. Kdysi jsem například takto ovládal ftp. Vytvořil jsem si soubor prikazy.txt s obdobným obsahem:

open sunsite.mff.cuni.cz
user anonymous
password literakl@server.cz
cd /pub/OS/Linux/ker­nel/v1.2
bin
get linux-1.2.13.tar.gz
 quit

CS24_early

Pak jsem spustil příkaz at midnight a napsal na standardní vstup ftp < prikazy.txt. O půlnoci pak démon atd spustil ftp klienta a ten si přečetl má přání z určeného souboru (za jeho obsah neručím, už jsem to dlouho nezkoušel a na lokále ftp server nemám).

To je pro dnešek vše, příště se podíváme na některé další příkazy, například at a tee. Ještě si na závěr neodpustím skrytou reklamu: informace, jak nastavovat a zprovozňovat hardware hledejte na serveru Linux Hardware.

Byl pro vás článek přínosný?

Autor článku