Narzędzia użytkownika

Narzędzia witryny


Pasek boczny

so:variables_substitutions

Podstawy zmiennych środowiskowych

Czym są

Zmienne środowiskowe (Environment variables) to powiązany z procesem zbiór par nazwa – wartość. Nazwy zmiennych nie mogą zawierać znaku = i powinny zawierać tylko litery (z zakresu ASCII), cyfry i podkreślnik, oraz powinny zaczynać się od litery.
Częstym stylem jest używanie tylko znaków A-Z, _ i 0-9 w nazwach zmiennych.

Każdy proces ma osobny zbiór zmiennych środowiskowych.
Tworząc nowy proces można wybrać czy kopiuje wszystkie zmienne środowiskowe rodzica, czy kopiuje inny podany zbiór zmiennych.
Powłoka dzieli swoje zmienne środowiskowe na te które zostaną przekazane procesom potomnym (eksportowane) i te, które nie będą przekazane procesom potomnym.

Zmienne środowiskowe nie są pomysłem powłoki, tylko systemu operacyjnego.

Ustawianie

Ustawienie wartości zmiennej (i stworzenie jej, jeśli wcześniej nie istniała):
NAZWA=wartość
Uwaga: NAZWA =wartość spróbuje uruchomić program NAZWA z argumentem =wartość.
Uwaga: NAZWA = wartość spróbuje uruchomić program NAZWA z argumentami = oraz wartość.
Uwaga: NAZWA= wartość spróbuje uruchomić program wartość przekazując mu wśród zmiennych środowiskowych zmienną NAZWA z pustą wartością.

Do usunięcia zmiennej należy wykorzystać polecenie unset NAZWA.
Uwaga: zwykle w powłoce pusta zmienna i nieustawiona zmienna zachowują się identycznie

Domyślnie nowo tworzone zmienne nie są przekazywane do procesów potomnych.

Aby ustawić przekazywanie zmiennej środowiskowej o nazwie NAZWA do procesów potomnych, należy wykonać:
export NAZWA
lub, aby jednocześnie ustawić przekazywanie do procesów potomnych i wartość:
export NAZWA=wartość
Uwaga: można wyeksportować jeszcze nieistniejącą zmienną i później ją stworzyć.

POSIX nie przewiduje cofnięcia eksportu zmiennej; można ją co najwyżej usunąć komendą unset NAZWA i ustawić na nowo jako zwykłą nieeksportowaną zmienną. Bash pozwala na cofnięcie eksportowania zmiennej przez export -n NAZWA.

Aby zobaczyć listę wszystkich zmiennych środowiskowych, należy wykonać komendę set1).
Aby zobaczyć listę eksportowanych zmiennych środowiskowych, należy wykonać komendę env2).

(Najprostsze) odczytywanie wartości

Aby powłoka wstawiła w podane miejsce wartość zmiennej o nazwie NAZWA, należy wpisać $NAZWA.
Np: jeśli wartość zmiennej $UID to 1000, to cd /run/user/$UID/ wejdzie do katalogu /run/user/1000/ a polecenie echo $NAZWA wyświetli wartość zmiennej NAZWA.

Przykłady

Wybrane standardowe zmienne

PATHLista oddzielonych dwukropkami ścieżek w których będą szukane programy
Np. żeby wykonać komendę ls, powłoka szuka pliku o nazwie ls w ścieżkach z PATH
HOMEKatalog domowy bieżącego użytkownika
PS1
PS2
Podstawowy znak zachęty (prompt)
Znak zachęty dla kolejnych linii komendy
PWDBieżący katalog roboczy
EDITORDomyślny edytor tekstowy
Np. less przy otwarciu pliku do edycji skrótem v uruchamia $EDITOR ścieżka_do_pliku
LOGNAME / USER
UID
Nazwa bieżącego użytkownika
Numeryczny identyfikator bieżącego użytkownika
LANGJęzyk, region i kodowanie znaków; dla Polski zwykle pl_PL.UTF-8
np. de_CH.UTF-8 oznacza niemiecki, Szwajcarię i kodowanie UTF-8
TERMNazwa terminala określająca jego techniczne możliwości, takie jak ilość wspieranych kolorów, możliwość przesuwania kursora wstecz etc. Więcej w man 7 term (wersja online).
COLUMNS
LINES
Liczba znaków mieszczący się na ekranie w wierszu (=kolumn)
Liczba wierszy (linii tekstu) mieszczących się na ekranie
RANDOMLosowa liczba (generowana na nowo przy każdym odwołaniu się do zmiennej)

Więcej w dokumentacji Basha i standardzie POSIX .

Ćwiczenia

Zadanie 1 Ustaw zmienną o nazwie VAR a następnie wyświetl jej wartość.

Zadanie 2 Ustaw zmienną o nazwie OTHER na wartość zmiennej VAR. Wypisz wartość OTHER

Zadanie 3 Ustaw wartość zmiennej PROG na ls, oraz wartość zmiennej ARG na /tmp. Następnie wpisz w powłokę $PROG $ARG.

Zadanie 4 Wyświetl wartości zmiennych z tabeli powyżej.

Zadanie 5 Zmień wartość zmiennej LANG na ja_JP.UTF-8 i uruchom program date oraz vim.
Zmień wartość zmiennej LANG na de_DE.UTF-8 i spróbuj wykonać rm -rf /root/.ssh/nope oraz lscpu.

Zadanie 6 Zmień wartość zmiennej PS1.

Zadanie 7 Spróbuj wykonać komendę lspci. Zmień wartość zmiennej PATH tak, żeby zawierała ścieżki /sbin i /usr/sbin. Ponownie spróbuj wykonać komendę lspci.

Grupowanie poleceń i podstawienia

Działanie powłoki (wg. POSIX, wg. podręcznika Basha):

1. czyta linię echo ${Y} "$Z 2+3=$((2+3))" > file; ls baz
2. rozbija ją na tokeny i rozwiązuje aliasy echo, ${Y}, "$Z 2+3=$((2+3))", >, file, ;, ls, --color=auto, baz
3. dzieli na komendyecho, ${Y}, "$Z 2+3=$((2+3))" , >, file
4. wykonuje podstawienia echo, a, b, c d 2+3=5 , >, file
5. ustawia przekierowaniaecho, a, b, c d 2+3=5
6. uruchamia komendę

Oddzielanie, grupowanie poleceń

Polecenia można oddzielać przez:

  • ;cmd ; … wykonana cmd i przejdzie dalej
  • &cmd & … uruchomi w tle cmd i przejdzie dalej
  • operatory logiczne:
    • &&a && b wykona a i jeśli a zakończy się powodzeniem, uruchomi b
      ewaluuje do prawdy wtedy i tylko wtedy gdy a i b zakończą się powodzeniem
    • ||a || b wykona a i jeśli a zakończy się błędem, uruchomi b
      ewaluuje do fałszu wtedy i tylko wtedy gdy a i b zakończą się błędem

Polecenia można grupować przez:

  • { … } – grupuje polecenia w tej powłoce,
    Uwaga: polecenia wewnątrz { … } muszą być zakończone przez ; lub &
    Uwaga: między nawiasami wąsatymi i poleceniem muszą być spacje
  • (…) – uruchamia polecenia w osobnej powłoce ("podpowłoce").

Przykłady:

  • { cd /tmp; pwd; }; pwd – wejdzie do /tmp i wypisze dwa razy katalog roboczy /tmp
  • (cd /tmp; pwd); pwd – uruchomi podpowłokę w której wejdzie do /tmp, wypisze katalog roboczy /tmp w podpowłoce i wypisze bieżący katalog roboczy (np. katalog domowy) w powłoce

Przykłady

Zadanie 8 Napisz polecenie które spróbuje usunąć plik plik i jeśli to się uda, to wyświetli udało się

Zadanie 9 Napisz polecenie które spróbuje usunąć plik plik i jeśli to się nie uda, to wyświetli nie udało się

Zadanie 10 Policz łączną ilość znaków w wynikach poleceń uname -a oraz date.

Zadanie 11 Ustaw zmienną środowiskową wewnątrz (…) i wyświetl jej wartość po wykonaniu (…).
Następnie powtórz zadanie dla { … }.

Zadanie 12 Uruchom w tle grupę poleceń która za pięć sekund wykona program fortune.

Podstawienia

Podstawienia (shell expansion / word expansion) polegają na zastąpieniu tekstu (pasującego do konkretnego wzorca) przez określoną wartość (wg. POSIX, wg. podręcznika Basha).

Dostępne podstawienia (w kolejności wykonywania przez BASH):

  • {…} – zakres lub lista (Uwaga: POSIX nie definiuje tego podstawienia, jest ono dostępne w Bashu i niektórych innych powłokach)
  • ~ i ~username – katalog domowy
  • ${…} – zmienna / parametr
  • $((…)) – arytmetyka (POSIX wymaga tylko wsparcia dla arytmetyki całkowitoliczbowej)
  • $(…) i `…` – podstawia wynik komendy
  • globy (*, ? i […]) – dopasowuje nazwy plików (było na pierwszych zajęciach)

Wewnątrz podwójnych cudzysłowów są wykonywane tylko podstawienia zaczynające się od $ oraz `.
Wewnątrz pojedynczych cudzysłowów nie są wykonywane żadne podstawienia.
W Bashu funkcjonują też cudzysłowy $'…' które pozwalają na wprowadzanie sekwencji poprzedzanych przez odwrócony ukośnik takich jak np. \n; patrz dokumentacja Basha.

Jeśli wyniki podstawienia (poza dopasowaniem nazw plików) zawierają spację i nie są wewnątrz cudzysłowów, to ich wynik jest rozbijany na osobne tokeny (słowa).
Np: ls $(echo dwa słowa) spróbuje wypisać katalog dwa i katalog słowa, a ls "$(echo dwa słowa)" spróbuje wypisać katalog dwa słowa

Zakres / lista – nawiasy wąsate

liczby (lub litery) z podanego zakresu
format: {początek..koniec..krok}
{1..5}1 2 3 4 5
file{15..20}.txtfile15.txt file16.txt file17.txt file18.txt
{0..9..3}0 3 6 9
{a..z..2}a f k p u z
wymienione po przecinkach elementy
format: {element1,element2,…}
{a,b,d,f}a b d f
/tmp/{ala,ma,kota}.txt/tmp/ala.txt /tmp/ma.txt /tmp/kota.txt
file{,.gz,.bzip2,.xz}file file.gz file.bzip2 file.xz

Zadanie 13 Stwórz puste pliki plik_1, plik_2, ..., plik_9 (używając nawiasów wąsatych do stworzenia listy plików).

Zadanie 14 Przeanalizuj co robi polecenie: echo -e " " {A..H} '\n'{8..1}

Zadanie 15 Wykonaj komendę stat dla plików /var/log/btmp, /var/log/mtmp, /var/log/wtmp (używając nawiasów wąsatych do stworzenia listy plików).

Katalogi domowe

katalog domowy bieżącego użytkownika ~/home/username
katalog domowy użytkownika username~username/home/username

Zadanie 16 Wypisz ścieżkę do swojego katalogu domowego korzystając z ~.

Zadanie 17 Wejdź do katalogu domowego użytkownika wwwrun.

Zmienne / parametry

Poza podstawianiem wartości zmiennej przez $ZMIENNA można też użyć składni ${ZMIENNA}. Pozwala to np., na napisanie ${SIZE}MB.

Wyrażenie ${#ZMIENNA} podstawia długość (ilość znaków) zmiennej.
Np. X='żółć'; echo ${#X} wypisze 4.

Dodając za nazwą zmiennej, ale wewnątrz nawiasów modyfikatory, można uzyskać:

  • ${X:-wyrażenie} – podstawia wartość X lub, jeśli X nie istnieje lub jest puste, podstawia wartość wyrażenie
  • ${X:+wyrażenie} – podstawia wartość wyrażenie jeśli X ma niepustą wartość, inaczej podstawia pustą wartość
  • ${X:liczba} – podstawia wartość X pomijając liczba znaków
  • ${X::liczba} – podstawia pierwsze liczba znaków z wartości X
  • ${X:ile_pominąć:ile_wypisać} – podstawia pierwsze ile_wypisać znaków z wartości X zaczynając od znaku ile_pominąć+1
  • ${X%wzorzec} – ucina z końca najkrótsze dopasowanie do wzorzec (o ile takie jest)
    ${X%%wzorzec} – ucina z końca najdłuższe dopasowanie do wzorzec (o ile takie jest)
  • ${X#wzorzec} – ucina z początku najkrótsze dopasowanie do wzorzec (o ile takie jest)
    ${X##wzorzec} – ucina z początku najdłuższe dopasowanie do wzorzec (o ile takie jest)
  • ${X/wzorzec/wyrażenie} – zamienia pierwsze wystąpienie wzorzec przez wyrażenie
    ${X//wzorzec/wyrażenie} – zamienia wszystkie wystąpienia wzorzec przez wyrażenie
    Uwaga: ${X/…} i ${X//…} są rozszerzeniem Basha

Przykłady

Zadanie 18 Wpisz do zmiennej FILE nazwę pliku. Następnie wykonaj polecenie które zmieni nazwę tego pliku dodając na koniec rozszerzenie .txt.

Zadanie 19 Czy rozwiązanie poprzedniego zadania zadziała dla nazwy pliku ze spacją? Sprawdź. Jeśli nie - popraw je.

Zadanie 20 Załóż że w zmiennej M jest numer miesiąca (np. 05), a w zmiennej D jest numer dnia (np. 08). Wykorzystując te zmienne przypisz wartość zmiennej LOGFILE tak, żeby miała postać myprog_miesiąc_dzień.log.
Następnie przekieruj wynik polecenia echo hello world do wartości tej zmiennej.

Zadanie 21 Napisz komendę, która przeniesie pliki file1 i file2 do katalogu wskazanego w zmiennej TARGET lub, jeśli ta zmienna jest pusta, do katalogu /tmp.

Zadanie 22 Przyjmij, że w zmiennej S jest pełna ścieżka do pliku (np. /home/user/some dir/some file.sh).
Do zmiennej D przypisz katalog w którym znajduje się plik wskazany przez S, a do F przypisz samą nazwę pliku wskazanego przez S.
Następnie wypisz wartość D oraz S.

Zadanie 23 Przygotuj komendę która zmienia nazwę pliku wskazanego przez zmienną F tak, by nazwa nie zawierała spacji.

Podstawianie wyników poleceń

Wyrażenia $(cmd) oraz `cmd` zostaną zastąpione wynikiem polecenia cmd.
Trzeba pamiętać że w linii cmd … $(sub) … najpierw zostanie w całości wykonane polecenie sub, a potem jego wynik będzie podstawiony w miejsce $(sub).

Zaleca się używać składni $(cmd), składnia `cmd` jest wspierana dla kompatybilności wstecznej.
Wyrażenia $(…) można dowolnie zagnieżdżać w sobie.

Zadanie 24 Napisz komendę która wyświetli napis W bieżącym katalogu znajduje się N plików, gdzie w miejsce N zostanie wstawiona faktyczna liczba plików.

Zadanie 25 Komenda readlink -f nazwa_pliku (i realpath nazwa_pliku) rozwiązuje wszystkie symlinki i pokazuje kanoniczną ścieżkę do pliku. Przypisz do zmiennej DIR kanoniczną ścieżkę do .. (do katalogu nadrzędnego).

Zadanie 26 Komenda date +%H_%M_%S wypisuje bieżący czas. Napisz komendę która przekierowuje wynik programu pstree -au do pliku procesy_CZAS.log, gdzie w miejscu CZAS ma pojawić się bieżący czas.

Zadanie 27 Komenda iconv -t ascii//TRANSLIT zamienia znaki ze standardowego wejścia (lub wskazanych plików) na kodowanie ASCII, zamieniając niekodowalne znaki na najbliższe odpowiedniki. Przygotuj komendę która zmienia nazwę pliku wskazanego przez zmienną F tak, by nowa nazwa składała się tylko ze znaków ASCII.

Arytmetyka

Powłoka wspiera obliczenia (przynajmniej) całkowitoliczbowe.
Standard POSIX definiuje tylko składnię $(()).
Bash dodatkowo posiada polecenie let … wykonujące podane działania.

Wewnątrz $((…)) / let … można:

  • pomijać $ przed nazwami zmiennych, np. x=$((x+2))
  • używać operatora przypisania, np. echo $((y=2**5, z=10^6)) przypisze do y wartość 25 = 32, przypisze do z wartość 10 xor 6 = 12, wyliczy 32, 12 = 12 (operator przecinka z C) i wykona echo 12
  • zawartość $((…)) jest traktowana jakby była w podwójnych cudzysłowach,
    zawartość let … liczy każdy z argumentów z osobna,
    np: X=$(( ( 2 + 2 ) * 2 )), let "X = ( 2 + 2 ) * 3", let X=(2+2)*3 i let X=(2+2)*3 Y=2*X+1 są poprawne, ale let X = ( 2 + 2 ) * 3 już nie
  • wewnątrz let … trzeba escape'ować znaki specjalne, np. let X=0xff\&1066 / let "X = 0xff & 1066"

POSIX standaryzuje też program expr który wykonuje podane obliczenie i wypisuje jego wynik na standardowe wejście.

Wyżej wymieniona funkcjonalność powłoki / program należy traktować jako narzędzia pomocnicze do pisania skryptów, a nie narzędzia do obliczeń.
Proste, sensowne kalkulatory dla powłoki to np. bc, calc i qalc.

Zadanie 28 Ustaw zmienne X i Y na wybrane dwucyfrowe liczby, a następnie:
      • zwiększ X o 1
      • zwiększ Y o 2
      • ustaw zmienną Z na iloczyn X i Y
      • wylicz resztę z dzielenia Z przez 128.

Zadanie 29 Przygotuj polecenie, które:
      • przypisze bieżący czas w nanosekundach (wynik komendy date +%s%N) do zmiennej START
      • wykona komendę sleep 1s
      • przypisze bieżący czas w nanosekundach (wynik komendy date +%s%N) do zmiennej END
      • wypisze różnicę między END a START

Aliasy

Alias (POSIX, Bash) to słowo, które jeśli wystąpi w miejscu komendy, to zostanie zastąpione wcześniej ustalonym tekstem.
Przykładowo: wiele dystrybucji Linuksa automatycznie ustawia alias la na wartość ls -la i aliasuje ls na ls --color=auto.
Przy takich ustawieniach po wpisaniu la najpierw następuje zmiana la na ls -la (i wyłączenie dla przetwarzania tego polecenia aliasu la), potem ls na ls --color=auto (i wyłączenie dla przetwarzania tego polecenia aliasu ls).

Aby utworzyć nowy alias, należy wykonać komendę:
alias słowo=na_co_ma_się_tłumaczyć
Np: alias la="ls -la"
Alias można usunąć komendą unalias słowo.

Wpisanie komendy alias bez argumentów wypisze wszystkie ustawione aliasy.
Żeby sprawdzić czy dany wyraz co jest programem, aliasem czy jeszcze czymś innym, można użyć komendy type co.

Aliasy, podobnie jak zmienne, są ustawiane dla bieżącej powłoki.

Zadanie 30 Stwórz alias year który będzie równoważny cal -my.
Użyj tego aliasu. Użyj tego aliasu żeby wyświetlić kalendarz na rok 2025.

1) set służy do wielu rzeczy naraz; z argumentami zmienia zachowanie powłoki.
2) env służy do uruchamiania procesów ze zmienioną listą zmiennych środowiskowych, natomiast bez argumentów wypisuje listę eksportowanych zmiennych.
so/variables_substitutions.txt · ostatnio zmienione: 2023/05/15 13:09 przez jkonczak