Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Методичка ОС.doc
Скачиваний:
4
Добавлен:
01.05.2025
Размер:
919 Кб
Скачать
☆

Лабораторна робота № 10

Тема: Програмування на мові В- Shell. Керуючі структури Shell.

Мета: Вивчити основні змінні OS UNIX, навчитися розробляти складні сценарії та команди редагування OS UNIX за допомогою керуючих структур B Shell.

Завдання:

1. Змініть первинну підказку таким чином щоб вона була схожа до підказки OS DOS.

2. Змініть вторинну підказку на будь-яке повідомлення.

3. Вивчення змінної PATH

4. Створіть shell-програму, яка виконує дії аналогічні до дії команди TREE MS-DOS.

5. В своєму домашньому каталозі та його підкаталогах знайти всі файли з розширенням .atc і склеїти їх в один файл, який необхідно розмістити в новому каталозі. Відсортувати і вивести вміст файлу на екран.

6. Перебрати в своєму домашньому каталозі, його підкаталогах всі файли і знайти той, який містить вказане слово, введене з клавіатури.

7. Відкрити текстовий файл, рахувати з нього 20 символів і записати їх в новий файл. Вивести на екран вміст старого і нового файлу.

8. Ввести з клавіатури ім'я файлу.

Якщо він існує, то на екран видається меню:

1 - Проглядання файлу;

2 - Редагувати файл (редактором ed);

3 - Сортувати файл;

4 - Пошук у файлі;

5 - Видалити файл;

6 - Вихід з програми.

Якщо заданий файл не існує, то програма запрошує дозвіл на створення файлу з вказаним ім'ям. Якщо «так», то створюється порожній файл і на екран видається меню:

1 - Редагувати файл (редактором ed);

2 - Проглядання файлу;

3 - Вихід з програми.

Меню повинне бути організовано в циклі.

9. Порівнюються два каталоги.

Знайти файли з однаковими іменами і порівняти їх вміст. Якщо вони ідентичні один одному, то вивести місце їх розташування і запит на видалення одного з них. Якщо «так», то програма видаляє файл з того місця, яке вказав користувач. Якщо вони різні по вмісту, то вивести повідомлення про це і вказати місце їх розташування.

Обладнання та матеріали: ПК, ОС UNIX, методичні вказівки до лабораторних робіт.

Хід роботи :

  1. Ознайомитись з теоретичними відомостями.

  2. На комп’ютері з операційною системою UNIX, запустити командний інтерпретатор В- Shell.

  3. Виконти дії з первинними та вторинними підказками, відповідно до завдання.

  4. Створіть shell-програму, яка виконує дії аналогічні до дії команди TREE MS-DOS.

  5. Виконати дії з каталогами та підкаталогами, відповідно до завдання.

  6. Виконати пошук файлів, відповідно до завдання.

  7. Виконати дії з каталогами, відповідно до завдання.

  8. Організувати меню, відповідно до завдання.

  9. Виконати порівняння каталогів, відповідно до завдання.

  10. Оформити та захистити звіт лабораторної роботи.

Теоретичні відомості

Shell і команди

Shell - це просто програма, яка сприймає введене користувачем, (тобто команди, які ви надрукуєте) і транслює це в команди системі. Це можна порівняти з програмою COMMAND.COM під MS-DOS, яка робить щось схоже. Shell - це лише один з інтерфейсів UNIX.

Як тільки ви ввійшли, система запускає shell, і ви можете вводити для нього команди. Ось короткий приклад. Якраз Larry увійшов до системи, і система знов видала підказку:

mousehouse login: larry

Password: larry's password

Welcome to Mousehouse!

/home/larry#

/home/larry#" це підказка shell, що показує, що він готовий приймати команди. /home/larry# make love

make: *** No way to make target 'love'. Stop.

"make" - це ім'я існуючої в системі програми і shell намагався виконати цю команду.

Перше слово командного рядка "make" це ім'я команди, яку передбачається виконати. Все інше в командному рядку сприймається як аргументи команди.

Приклади:

/home/larry# cp foo bar

Тут ім'я команди "cp", а аргументи "foo" і "bar".

Коли ви вводите команду, shell робить декілька речей. По-перше, дивиться на те, що може (повинно) бути ім'ям команди і є це внутрішньої для shell командою. Shell також перевіряє, чи не є команда синонімом іншої або потрібен підстановка імені. Якщо цього не треба робити, shell шукає відповідну цьому імені програму на диску. Якщо shell знаходить таку програму, він її виконує, передаючи їй аргументи з командного рядка.

В нашому прикладі shell шукає програму на ім'я make і намагається виконати її з аргументом love. make - це програма, яка часто використовується при компіляції великих програм, вона бере як аргумент ім'я "цільового файлу" компіляції. У разі "make love" ми наказали команді make відкомпілювати love. Оскільки make не зміг знайти файлу з таким ім'ям, він повідомив (дещо забавним чином) про неможливість виконати команду і повернувся в підказку.

Shell - інтерпретатор командної мови

Метасимволи

Сім віл

Функція

* ? [ ]

Ці метасимволи дозволяють вказувати скорочені імена файлів при пошуку за шаблоном

&

Означає, що команда виконуватиметься у фоновому режимі

;

Крапка з комою розділяє команди в командному рядку

\

Відміняє спеціальне значення символів, таких як * ?, [ ] & ; < >

‘.’

Одиночні лапки відміняють значення пропуску як роздільника і спеціальне значення всіх символів

“.”

Подвійні лапки відміняють значення пропуску як роздільника і спеціальне значення всіх символів, за виключенням $ і \

>

Перенаправляє висновок команди у файл

<

Перенаправляє введення для команди з файлу

»

Перенаправляє висновок команди, який повинен бути доданий в кінець існуючого файлу

|

Створює канал, направляюче виведення однієї команди у введення іншої команди

ММММ.М

Використовується в парі; дозволяє використовувати висновок як аргументи в командному рядку

$

Використовується з позиційними параметрами і визначеними користувачем

змінними; також використовується за умовчанням як підказка, shell

Метасимволи використовуються для пошуку імен файлів, за допомогою їх спрощується задача вказівки файлів або груп файлів як аргументів команди.

Пошук всіх символів (метасимвол *)

Метасимвол * здійснює пошук будь-якого рядка символів, включаючи нульовий (порожнію) рядок. Ви можете використовувати * для позначення повного або часткового імені файлу. Просто символ * шукає всі імена файлів і довідників в поточному довіднику, за винятком тих, які починаються з крапки. Щоб подивитися метасимвол * у дії, введіть його як аргумент в команді echo:

echo *<CR>

У відповідь система роздрукує перелік всіх імен файлів у вашому поточному довіднику.

Символ * може представляти символи в будь-якій частині імені файлу.

Якщо у вашому довіднику знаходяться файли FATE, FE, FADED_LINE, FIG3.4E, FINE_LINE, FAST_LINE, то для відображення всіх цих файлів на екрані введіть команду:

Is F*E<CR>

Ви можете, наприклад, за допомогою метасимвола "' знайти всі файли з іменами memo в системному довіднику: ls */memo

Пошук по одному символу (метасимвол ?)

Метасимвол ? здійснює пошук будь-якого одного символу в імені файлу за винятком лідируючої крапки. Припустимо, ви маєте книгу, в якій 12 глав і хочете отримати список глав до 9-го розділу. Якщо ваш довідник містить наступні файли:

Chapter 1

Chapter2

Chapter5

Chapter9

Chapter 11

то введіть команду ls з метасимволом ? для отримання всіх глав, які починаються з рядка "Chapter" і закінчуються одним символом:

$ Is Chapter?<CR>

Chapter 1

Chapter2

Chapters

Chapter9

$

Хоча метасимвол здійснює пошук одного символу, ви можете використовувати його для пошуку більше одного символу в імені файлу. Наприклад, ви отримаєте перелік всієї решти розділів в поточному довіднику, якщо введете наступну команду:

ls Chapter??<CR>

І, звичайно, щоб отримати список всіх глав в поточному довіднику, використовуйте метасимвол *:

ls Chapter*<CR>

Пошук одного набору (метасимвол [ ])

Якщо ви хочете, щоб shell знайшов будь-який символ з перерахованих вами символів, то укладете ці символи в квадратні дужки. Припустимо, ваш довідник містить наступні файли: cat, fat, mat, rat. Якщо ви скористаєтеся як частина імені файлу шаблоном [erf], то shell шукатиме імена файлів, в які входять або буква "с", або буква "r", або буква "f" у вказаній позиції. Приклад:

$ Is [crf]at<CR>

cat

fat

rat

$

Символи, які можуть бути згрупований в дужки, називаються класом символів.

Дужки можуть також використовуватися для позначення діапазону символів, цифр або букв. Припустимо у вашому довіднику містяться наступні файли: chapteri, chapter2, chapters, chapter4, chapter5, chapter6. Якщо ви вкажете:

chapter[1-5]

то shell знайде файли з chapteri по chapter5.

Клас символів можна також вказати за допомогою діапазону букв. Якщо ви вкажете [A-Z], то shell шукатиме тільки великі букви, якщо [а-z] - то малі букви.

Створення простих програм shell

Почнемо опис створення простих програм shell, які виконують задачі:

  • друк поточного довідника;

  • список вмісту цього довідника;

  • відображення наступних повідомлень на вашому терміналі: "This is end shell program."

За допомогою редактора створіть файл dl і введіть в нього рядки:

pwd<CR>

ls<CR>

echo This is end shell program.<CR>

Тепер ви маєте програму shell. Ви можете за допомогою cat відобразити вміст файлу:

$ cat dl<CR> pwd

ls

echo This is end shell program.

$

Виконання програм shell

Виконати shell програму ви можете за допомогою команди sh. Введіть:

sh dl<CR>

Коли команда dl виконується за допомогою sh, то спочатку друкується ім'я шляху поточного довідника, потім список файлів в поточному довіднику і в кінці коментар: "This is end shell program."

За допомогою команди chmod ви можете зробити файл виконуваним:

$ chmod u+x dl<CR>

$ls-KCR>

total 2

-xw—— 1 login login 3661 Nov 2 10:28 mbox

-xwx-— 1 login login 48 Nov 15 10:50 dl

$

Зверніть увагу, що chmod включає дозвіл на виконання (+х) для користувача (и). Тепер dl є виконуваною програмою. Спробуйте виконати її. Введіть:

dl<CR>

Створення довідника bin для виконуваних файлів

Щоб зробити shell програми доступними зі всіх ваших довідників, ви можете створити довідник bin в своєму реєстраційному довіднику і переписати shell програми в цей довідник.

За допомогою змінної PATH ви можете включити ваш довідник" bin:

PATH = $PATH:$HOME/bin

Як у всякій мові програмування в тексті на мові shell можуть бути коментарі. Для цього використовується символ "#". Все, що знаходиться в рядку (в командному файлі) ліворуч цього символу, сприймається інтерпретатором як коментар. Наприклад

# Це коментар.

## І це.

### І це теж.

Як у всякій процедурній мові програмування, в мові shell є оператори. Ряд операторів дозволяє управляти послідовністю виконання команд. В таких операторах часто необхідна перевірка умови, яка і визначає напрям продовження обчислень.

Умовний оператор if

В загальному випадку оператор "if має структуру

if умова

then список

[elif умова

then список]

[else список]

fi

Тут "elif скорочений варіант від "else if може бути використаний разом з повним, тобто допускається вкладення довільного числа операторів "if (як і інших операторів). Зрозуміло "список" в кожному випадку повинен бути осмислений і допустимий в даному контексті.

Конструкції

[elif умова

then список]

і

[else список]

не є обов'язковими

Сама усічена структура цього оператора

if умова

then список

fi

якщо виконана умова (як правило це грудка отриманий код завершення "О", то виконується "список", інакше він пропускається.

Зверніть увагу, що структура обов'язково завершується службовим словом "fi". Число "fi", природно, завжди повинне відповідати числу "if.

Приклади.

Хай написаний розрахунок "if-1"

if[$l-gt$2]

then pwd

else echo $0 : Hello!

Fi

Тоді виклик розрахунку

if-1 12 11

дасть

/home/sae/STUDY/SHELL

а

if-1 12 13

дасть

if-1: Hello!

Ще приклад на вкладеність

###

# if-3: Оцінка досягнень

echo -n " А яку оцінку отримав на іспиті?: " readz

if[$z=5]

then echo Молодець ! elif[$z=4]

then echo Все одно молодець ! elif[$z=3] then echo Все одно ! elif[$z=2] then echo Все ! else echo ! fi

Можна звернути увагу на те, що бажано використовувати зсуви при записі програм, щоб краще виділити вкладеність структур.

Оператор вибору "case" має структуру:

Конструкція case ... esac дозволяє вибрати вам один з декілька шаблонів і потім виконати список команд для цього шаблона. Вираз-шаблон повинен починатися з ключового слова in, а права кругла дужка повинна бути поміщений після останнього символу кожного шаблона. Послідовність команд для кожного шаблона закінчується двома знаками ;;. Конструкція case повинна бути закінчений ключовим словом esac.

case рядок in

шаблон) список команд;;

шаблон) список команд;;

.

esac

Приклад.

###

# case-1: Структура "case".

# Вже що розглядався в зв'язку з

# структурою "if приклад простіше і

# наглядніше можна реалізувати з

# допомогою структури "case".

echo -n " А яку оцінку отримав на іспиті?: "

read z

case $z in

5) echo Молодець ! ;;

4) echo Все одно молодець ! ;;

3) echo Все одно ! ;;

2) echo Все ! ;;

#) echo ! ;; ^ esac

Незвикло виглядають в кінці рядків вибору ";;", але написати тут ";" було б помилкою. Для кожної альтернативи може бути виконано декілька команд. Якщо ці команди будуть записані в один рядок, то символ ";" використовуватиметься як роздільник команд.

Звичайно останній рядок вибору має шаблон "*", що в структурі "case" означає "будь-яке значення". Цей рядок вибирається, якщо не відбувся збіг значення змінної (тут $z) ні з одним з раніше записаних шаблонів, обмежених дужкою ")". Значення є видимими в порядку запису.

###

# case-2: Довідник.

# Для різних фірм на ім'я видається

# назва холдингу, в який вона входить

case $1 in

ONE|TWO|THREE) echo Холдинг: ZERO ;;

MMM|WWW) echo Холдинг: Not-Net;;

Hi|Hello[Howdoing) echo Холдинг: Привіт! ;;

*) echo Немає такої фірми ;;

esac

При виклику "case-2 Hello" на екран буде виведений:

Холдинг: Привіт!

А при виклику "case-2 HELLO" на екран буде виведений:

Немає такої фірми

Коли скоро слово "case" переводиться як "вибір", то це як би натяк на те, що можна цю структуру використовувати для реалізації найпростіших меню.

###

# case-3: Реалізація меню за допомогою команди "case echo" "Назвіть файл, а потім (через пропуск) наберіть цифру, відповідну необхідній обробці:

1 - відсортувати

2 - видати на екран

3 - визначити число рядків "

read х у # х - ім'я файлу, у - що зробити

case $y in

1)sort<$x„

2)cat<$x;;

3) we -1 < $x ;;

*) echo "

Ми не знаємо

такої команди ! " ;;

esac

Зрозуміло, бажання можуть бути складніші і на місці окремих команд можуть бути послідовності команд або виклики складніших розрахунків.

Напишемо команду "case-4", яка додає інформацію до файлу, вказаного першим параметром (якщо параметр один), із стандартного входу, або (якщо 2 параметри) з файлу, вказаного як перший параметр:

###

# case-4: Додавання у файл.

# Використовування стандартної змінної.

# "$#" - число параметрів при введенні розрахунку

# "»" - перенаправлення з додаванням у файл

case $# in

1)cat»$l ;;

2)cat»$2<$l ;;

*) echo "Формат: case-4 [звідки] куди";;

esac

"$1" (при "$#=1") - це ім'я файлу, в який відбувається додавання із стандартного входу.

"$1" і "$2" (при $#-2) - це імена файлів, з якого ("$!") і в який ("$2") додавати.

У всіх інших випадках (*) видається повідомлення про те, яким повинен бути правильний формат команди.

Оператор циклу з переліком ("for")

Оператор for виконує послідовність команд для кожного елемента списку. Для кожної ітерації циклу наступний елемент списку привласнюється змінній, даній в операторі for. Посилання на цю змінну може бути зроблено в будь-якому місці в командах усередині оператора do. При конструюванні кожної секції команд вам необхідно переконатися, що кожному do відповідає done в кінці циклу.

Оператор циклу "for" має структуру:

for ім'я [in список значень]

do

список команд

done

де "for" - службове слово визначаюче тип циклу, "do і "done" -службові слова", виділяючі тіло циклу. Не забувайте про "done"! Фрагмент "in список значень" може бути відсутній.

Часто використовується форма "for i in *", що означає "для всіх файлів поточного каталога".

Хай "proc-sort" у свою чергу представляється командним файлом

cat $ 1 | sort | tee /dev/lp > ${ 1 }_sorted

тобто послідовно сортуються вказані файли, результати сортування виводяться на друк ("/dev/lp") і прямують у файли fl_sorted f2_sorted і f3_sorted

Можна зробити більш універсальною команду "Isort", якщо не фіксувати перелік файлів в команді, а передавати довільне їх число параметрами.

Тоді головна програма буде наступною:

for i

do

proc-sort $i '

done

Тут відсутність після "i" службового слова "in" з переліком імен говорить про те, що список поступає через параметри команди. Результат попереднього прикладу можна отримати, набравши

Isort fl Ј2 f3

Ускладнимо задачу визначення холдингу фірми, що раніше розглядалася. Тепер можна при виклику указувати довільну кількість фірм. За відсутності в структурі оператора "for фрагмента" "in список значень", значення беруться з параметрів зухвалої команди.

###

# holding: Довідник.

# Для різних фірм на ім'я видається

# назва холдингу, в який вона входить

fori

do

case $i in

ONE|TWO|THREE) echo Холдинг: ZERO ;;

MMM|WWW) echo Холдинг: Not-Net;;

Hi|Hello|Howdoing) echo Холдинг: Привіт! ;;

*) echo Немає такої фірми ;;

esac

done

При виклику "holding Hello HELLO ONE" на екрані буде:

Холдинг: Привіт!

Немає такої фірми

Холдинг: Not-Net

Наступний розрахунок ілюструє корисний, хоча і з часткою трюкача, спосіб повторення одних і тих же дій кілька разів. Змінна "i" приймає тут п'ять значень: 1, 2, 3, 4, 5, але усередині циклу ця змінна відсутня і тому її значення ніякої ролі не грає і ні чого не міняє. З таким же успіхом змінна "i" могла приймати значення, скажемо ф про до у з, а в результаті точно також би було п'ять разів повторено одне і те ж обчислення вмісту циклу без змін.

###

# print-5: Організації п'ятикратного виконання команди

for i in 1 2 3 4 5

do

cat file-22 > /dev/lp

done

Розрахунок "print-n" ілюструє ще одну корисну можливість у використовуванні циклу "for". Тут, після "for i...", відсутні "in..." і перелік імен, тобто переліком імен для "i" стає перелік параметрів," а отже кількість друкованих екземплярів можна міняти.

###

# print-n: Завдання числа копій

# через параметри

for i

do

cat file-22 > /dev/lp

done

Значення не зміниться, якщо перший рядок розрахунку записати як

for i in $*

оскільки значення "$*" - є список значень параметрів.

Відзначимо відмінність в спеціальних змінних "$*" і "$@", що представляють перелік параметрів. Перший представляє параметри, як рядок, а другий, як сукупність слів.

Хай командний файл "сmр" має вигляд:

for i in "$*"

do

echo $i

done

echo

for i in "$@"

do

echo $i

done

При виклику

cmp aa bb cc

на екран буде виведений

аа bb cc

аа

bb

cc

Оператор циклу з істинною умовою ("while")

Структура "while", також забезпечуюча виконання розрахунків, переважно тоді, коли невідомий наперед точний список значень параметрів або цей список повинен бути отриманий в результаті обчислень в циклі.

Оператор циклу "while" має структуру:

while умова

do

список команд

done

де "while" - службове слово визначаюче тип циклу з істинною умовою. Список команд в тілі циклу (між "do" і "done") повторюється до тих пір, поки зберігається істинність умови (тобто код завершення останньої команди в тілі циклу рівний "О") або цикл не буде перерваний зсередини спеціальними командами ("break", "continue" або "exit"). При першому вході в цикл умова повинна виконуватися.

###

# print-50: Структура "while"

# Розрахунок дозволяє надрукувати 50

# екземплярів файлу "file-22"

n=0

while [ $n -It 50 ] # поки п < 50

do

n='expr $n+ Г

cat file-22 > /dev/lp

done

Звернемо увагу на те, що змінній "п" спочатку привласнюється значення 0, а не порожній рядок, оскільки команда "ехрr" працює з shell-змінними як з цілими числами, а не як з рядками.

n='ехрr $n+ 1’

тобто при кожному виконанні значення "n" збільшується на 1.

Як і взагалі в житті, можна реалізувати те ж саме і складніше. Розрахунок "pr-br" приведений для ілюстрації нескінченного циклу і використовування команди "break", яка забезпечує припинення циклу.

###,

# pr-br: Структура "while" з "break"

# Розрахунок дозволяє надрукувати 50

# екземплярів файлу "file-22 n=0"

while true

do

if[$n-lt50] #якщо n<50

then n=’expr $n+1'

else break

fi

cat file-22 > /dev/lp

done

Команда "break [n]" дозволяє виходити з циклу. Якщо "п" відсутній, то це еквівалентно "break I", "n" указує число вкладених циклів, з яких треба вийти, наприклад, "break 3" - вихід з трьох вкладених циклів.

На відміну від команди "break команда" "continue [n]" лише припиняє виконання поточного циклу і повертає на ПОЧАТОК циклу. Вона також може бути з параметром. Наприклад, "continue 2" означає вихід на початок другого (якщо вважати з глибини) вкладеного циклу.

Команда "exit [n]" дозволяє вийти взагалі з процедури з кодом повернення "О" або "n" (якщо параметр "n" вказаний). Ця команда може використовуватися не тільки в циклах. Навіть в лінійній послідовності команд вона може бути корисний при відладці, щоб припинить виконання (поточного) розрахунку в заданій крапці.

Оператор циклу з помилковою умовою ("until")

Оператор циклу "until" має структуру:

until умова

do

список команд

done

де "until" - службове слово визначаюче тип циклу з помилковою умовою. Список команд в тілі циклу (між "do" і "done") повторюється до тих пір, поки зберігається помилковість умови або цикл не буде перерваний зсередини спеціальними командами ("break", "continue" або "exit"). При першому вході в цикл умова не повинна виконуватися.

Відмінність від оператора "while" полягає в тому, що умова циклу перевіряється на помилковість (на ненульовий код завершення останньої команди тіла циклу) перевіряється ПІСЛЯ кожного (у тому числі і першого!) виконання команд тіла циклу.

Програмістів, знайомих з операторами "until" в інших мовах може спочатку збивати така семантика цього оператора.

Приклади.

until false

do

readx

if[$x=5]

then echo enough ; break

else echo some more

fi

done

Тут програма з нескінченним циклом чекає введення слів (повторюючи на екрані фразу "some more"), поки не буде введений "5". Після цього видається "enough" і команда "break" припиняє виконання циклу.

Інший приклад ("Очікування півдня") ілюструє можливість використовувати в умові обчислення.

until date | grep 12:00:

do

sleep 30

done

Тут кожні 30 секунд виконується командний рядок умови. Команда "date" видає поточну дату і час. Команда "grep" одержує цю інформацію через конвейєр і намагається сумістити заданий шаблон "12:00:" з часом, видаваним командою "date". При неспівпаданні "grep" видає код повернення "I", що відповідає значенню "брехня", і цикл "виконує очікування" протягом 30 секунд, після чого повторюється виконання умови. Опівдні (можливо з декількома секундами) відбудеться порівняння, умова стане істинною, "grep" видасть на екран відповідний рядок і робота циклу закінчиться.

Контрольні питання:

  1. Що таке Shell?

  2. Основні мета символи Shell?

  3. Як працюють мета символи *, ?, []?

  4. Як відбувається створення та виконання програми Shell?

  5. Умовний оператор?

  6. Оператор вибору?

  7. Оператор циклу з переліком?

  8. Оператор циклу з істинною умовою?

  9. Оператор циклу з помилковю умовою?

  10. Як створити довідник для виконуваних файлів?

Література:

    1. Паркер Тим. Linux 5.2. Энциклопедия пользователя: Пер. с англ./Тим Паркер – К.: Издательство «ДиаСофт», 1999. – 688 с., стор. 176-191.