...

Nessun titolo diapositiva

by user

on
Category: Documents
8

views

Report

Comments

Transcript

Nessun titolo diapositiva
1*
2*
3*
4*
Questo capitolo tratta di sistemi di numerazione a base diversa da quella decimale alla
quale siamo abituati. Impareremo i numeri binari vale a dire quelli con base 2, i numeri
ottali, cioe’ quelli con base 8, ed i numeri esadecimali, cioe’ quelli con base 16.
Vedremo che questi sistemi di numerazione sono piu’ utili di quello decimale per descivere
il contenuto di una qualunque cella di memoria o registro del computer. Questo poiche’
questi ultimi sono sempre composti o da circuiti elettronici o da dispositivi magnetici o da
dispositivi ottici che possono assumere solo 2 possibili stati (ON ed OFF; magnetizzazione
YES or NO; superficie riflettente o non riflettente etc.) Cosi’ il sistema binario, cioe’ quello
che usa solo 2 cifre per descrivere i numeri, diventa il modo piu’ naturale da usare con un
computer, per contare i numeri. L’utilita’ della numerazione ottale ed esadecimale
discende in sostanza dal fatto che sono sistemi di numerazione piu’ sintetici (uno stesso
numero in ottale od esadecimale e’ molto piu’ corto del corrispondente binario) che si
possono molto facilmente e direttamente trasformare nel corrispondente numero binario.
5*
7.1 Numerazioni con basi 2, 8, 16
Base 10
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
ho finito le cifre, metto 1 in una
colonna piu’ a sinistra e nella
colonna piu’ a destra riparto da 0
La base di un sistema di numerazione
e’ il numero di simboli (cifre) usati
per descrivere i numeri. Il sistema
binario usa solo due cifre : 0 ed 1 ;
quello ottale usa otto cifre : 0, 1, 2, 3,
4, 5, 6, 7 ; quello decimale, come e’
noto, ne usa dieci , dallo 0 al 9 ; infine
quello esadecimale ne usa sedici : 0, 1,
2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E, F.
In tutti i sistemi di numerazione,
analogamente al caso della
numerazione decimale, si usa la
notazione posizionale
Numeri decimali, notazione posizionale :
173.2 = 1x102 + 7x101 + 3x100 + 2x10-1
ho finito le cifre, metto 2 nella
colonna piu’ a sinistra e nella
colonna piu’ a destra riparto da 0
6*
7.1 Numerazioni con basi 2, 8, 16
Base 10
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Base 2
0
1
10
11
100
101
110
111
1000
1001
1010
1011
1100
1101
1110
1111
10000
10001
10010
10011
10100
ho finito le cifre, metto 1 in una colonna piu’ a sinistra e
nella colonna piu’ a destra riparto da 0
ho finito le cifre, metto 1 in una colonna piu’ a sinistra e
nelle colonne piu’ a destra riparto da 0, etc.
Numeri binari
traduzione in numero decimale :
1011.1(2)
1x23 + 0x22 + 1x21 + 1x20 + 1x2-1
= 11.5(10)
7*
7.1 Numerazioni con basi 2, 8, 16
Base 10
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Base 2
Base 8
0
1
10
11
100
101
110
111
1000
1001
1010
1011
1100
1101
1110
1111
10000
10001
10010
10011
10100
0
1
2
3
4
5
6
7
10
11
12
13
14
15
16
17
20
21
22
23
24
Numeri ottali
traduzione in numero decimale :
172.6(8)
1 x 82 + 7 x 81 + 2 x 80 + 6 x 8-1
= 122.75 (10)
ho finito le cifre, metto 1 in una colonna piu’
a sinistra e nella colonna piu’ a destra riparto
da 0
ho finito le cifre, metto 1 in una colonna piu’ a
sinistra e nelle colonne piu’ a destra riparto da
0, etc.
8*
7.1 Numerazioni con basi 2, 8, 16
Base 10
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Base 2
Base 8
0
1
10
11
100
101
110
111
1000
1001
1010
1011
1100
1101
1110
1111
10000
10001
10010
10011
10100
0
1
2
3
4
5
6
7
10
11
12
13
14
15
16
17
20
21
22
23
24
Base 16
0
1
2
3
4
5
6
7
8
9
A
B
C
D
E
F
10
11
12
13
14
Numeri esadecimali
traduzione in numero decimale :
1B2.6(16)
1 x 162 +11 x 161+2 x 160+6x16-1
= 434.375 (10)
ho finito le cifre, metto 1 in
una colonna piu’ a sinistra e
nelle colonne piu’ a destra
riparto da 0, etc.
9*
7.2 Come passare da un numero decimale al
corrispondente binario, ottale, esadecimale
Direttamente con degli esempi, facciamo vedere coma passare da un numero decimale
al corrispondente binario, ottale, esadecimale.
Esempio : passare da 29.2 (decimale) al corrispettivo binario
1
Si considera prima la parte intera, eseguendo divisioni successive per
2 fino a quando il risultato fa 0. Le cifre ottenute sono la parte
intera del numero binario corrispondente a quello decimale.
29 : 2 = 14
1
Il resto della
divisione diventa
una cifra binaria
14 : 2 = 7
0
7 :2= 3
1
3 :2= 1
1
1:2= 0
1
ultimo resto : cifra
piu’ significativa
1
1
primo resto : cifra
meno significativa
1
0
1
il risultato della
divisione e’ 0, il
procedimento e’
finito
10*
2
Si considera poi la parte decimale, eseguendo moltiplicazioni successive per 2 fino
a quando il risultato fa 0 oppure finche’ si e’ raggiunta la precisione desiderata.
Le cifre ottenute sono la parte a destra del punto.
0.2 x 2 = 0.4 + 0
La parte intera del
risultato diventa una
cifra binaria. La parte
decimale viene ancora
moltiplicata per la
base 2
0.4 x2 = 0.8 + 0
.
0
0
0.8 x 2 = 0.6 + 1
1
1
primo parte intera : cifra
decimale piu’ significativa
0.6 x 2 = 0.2 + 1
cifra decimale
meno significativa
La parte decimale del risultato
della moltiplicazione non e’ 0,
ma la precisione raggiunta mi
soddisfa. Termino il procedimento.
Risultato finale : 29.2 decimale  11101.0011 binario
11*
Esempio : passare da 139 decimale al corrispettivo ottale
E’ gia’ un numero intero, cosi’ dovro’ solo eseguire il passaggio 1
dell’esempio precedente. Ora eseguo divisioni successive per 8 fino a
quando il risultato fa 0. Le cifre ottenute sono il numero ottale
corrispondente a quello decimale.
139 : 8 = 17
3
17 : 8 = 2
1
2 :8= 0
2
il risultato della
divisione e’ 0, il
procedimento e’
finito
ultimo resto : cifra
piu’ significativa
2 1 3
primo resto : cifra
meno significativa
Risultato finale : 139 decimale  213 ottale
12*
Esempio : passare da 139 decimale al corrispettivo esadecimale
E’ gia’ un numero intero, cosi’ dovro’ solo eseguire il passaggio 1
dell’esempio precedente. Ora eseguo divisioni successive per 16 fino a
quando il risultato fa 0. Le cifre ottenute sono il numero esadecimale
corrispondente a quello decimale.
139 : 16 = 8
11
8 : 16= 0
8
il risultato della
divisione e’ 0, il
procedimento e’
finito
ultimo resto : cifra
piu’ significativa
8
B
primo resto : cifra
meno significativa
Risultato finale : 139 decimale  8B esadecimale
13*
7.3 Come passare da un numero ottale od
esadecimale al corrispondente binario e viceversa
Passare da un numero ottale od esadecimale al corrispondente binario e’ molto facile e
viene illustra to negli esempi che seguono. Anche il viceversa non comporta calcoli
particolarmente difficili. Capiamo cosi’ anche perche’ i numeri ottali od esadecimale
vengano preferiti, quando possibile, ai binari : sono molto piu’ sintetici di quest’ultimi
(necessitano di minori numero di digits per descrivere lo stesso numero) e si possono
all’occorrenza trasformare in binari molto facilmente.
14*
Esempio : passare da 172 ottale al corrispettivo binario
per ogni cifra
ottale scrivo i
corrispondenti
3 digits binari
1728
001 111 010
= 11110102
Risultato finale : 172 ottale  1111010 binario
il numero binario
corrispondente si
ottiene accostando
nell’ordine i digits
binari
Esempio : passare da 1010001 binario al corrispettivo ottale
Inizio suddividendo, PARTENDO DA DESTRA, il numero binario di 3 cifre in 3 cifre.
Ad ogni terzina sostituisco la corrispondente cifra ottale.
1 010 001 2
001
001 010 001
1 2
1
faccio l’operazione inversa a quella
di prima. Sostituisco ai 3 digits binari
il corrispondente numero ottale
Risultato finale : 1010001 binario  121 ottale
15*
Esempio : passare da 1D8 esadecimale al corrispettivo binario
1D816
per ogni cifra
esadeciamle scrivo
i corrispondenti
4 digits binari
0001 1101 1000
= 1110110002
Risultato finale : 1D8 ottale  111011000 binario
il numero binario
corrispondente si
ottiene accostando
nell’ordine i digits
binari
Esempio : passare da 10111100110 binario al corrispettivo esadecimale
Inizio suddividendo, PARTENDO DA DESTRA, il numero binario di 4 cifre in 4 cifre.
Ad ogni quaterna sostituisco la corrispondente cifra esadecimale.
0101
101 1110 0110 2
0101 1110 0110
5
E
6
faccio l’operazione inversa a quella
di prima. Sostituisco ai 4 digits binari
il corrispondente numero esadecimale
Risultato finale : 10111100110 binario  5E6 esadecimale
16*
7.4 Somma tra numeri binari, ottali, esadecimali
Valgono la stesse regole di somma e di riporto valide pei numeri decimali. Ancora una
volta chiariamo queste regole con degli esempi.
Esempio : eseguire la somma (decimale) 29 + 233 coi corrispondenti
numeri binari, ottali, esadecimali
Base 10
riporti
1
29 +
233 =
2 62
Base 2
1 1 11 1
1
11101 +
11101001 =
1 00 00 0 1 1 0
Base 8
1
35 +
351 =
4 06
Base 16
11
1D +
E9 =
1 06
17*
7.5 Moltiplicazione tra numeri binari, ottali,
esadecimali
Valgono la stesse regole di moltiplicazioni parziali valide pei numeri decimali. Ancora
una volta chiariamo queste regole con degli esempi.
Esempio : eseguire la moltiplicazione (decimale) 20 * 21 coi corrispondenti
numeri binari, ottali, esadecimali
Base 10
20 x
21 =
20
40
420
Base 2
10100 x
10101 =
10100
00000
10100
00000
10100
Base 8
Base 16
24 x
25 =
144
50
14 x
15 =
64
14
644
1A4
110100100
18*
Computer : insieme di circuiti elettronici + sistemi elettromeccanici (tastiera,
stampante, monitors). Puo’ eseguire calcoli ed operazioni basandosi su istruzioni che
vengono messe nella memoria allo scopo di manipolare dati (input) e produrre risultati
(output)
Sequenza di istruzioni = programma
Un computer e’ formato (almeno) dalle seguenti parti essenziali
1) Memoria : insieme di dispositivi magnetici (nastri, dischi) ottici (dischi laser) o di
circuiti elettronici (ad es. la RAM = random access memory) dove vengono conservate le
informazioni (istruzioni dei programmi, dati di input, dati di output). La memoria a
rapido accesso di solito e’ di dimensioni non molto grandi ed e’ di tipo transitorio. Vi
accede di solito la CPU durante il processo di calcolo. La memoria di massa invece e’
di tipo permanente, e serve per immagazzinare grandi quantita’ di dati, e vi si accede
in modo piu’ lento. Ciascun insieme di dati e’ chiamato file.
19*
2) CPU (central processor unit) costituito da (almeno) due parti : una parte che
acquisisce le istruzioni del programma e le decodifica, una parte aritmetica che fa i
calcoli.
3) Dispositivo di input : tastiera del computer, lettore di nastri, lettore di dischi etc.
Serve per dare comandi e fornire dati
4) Dispositivo di output : video, stampante etc. Dispositivi per raccogliere i risultati.
Parte centrale
Memoria RAM
periferica
periferica
ingresso
CPU
uscita
Memoria di massa
periferica
20*
La parte centrale (CPU, RAM) e’ costituita da circuiti elettronci veloci, al giorno
d’oggi i clock piu’ veloci raggiungono 3.0 GHz. La memoria di massa ed i dispositivi di
input/output possono essere costituiti anche da parti meccaniche (tastiera, dischi) e
l’accesso e’ piu’ lento. Di solito il passaggio dei dati tra unita’ lente ed unita’ veloci
vengono gestiti in modo automatico senza usare la CPU. Le unita’ piu’ lente in linea di
principio potrebbero essere staccate senza pregiudicare il funzionamento della parte
centrale e per questo vengono dette unita’ periferiche.
Le memorie e la CPU sono composte da parole (da registri nel caso della CPU). Ogni
parola e’ composta da bytes ed ogni byte e’ composto da 8 bits. Un bit e’ un oggetto (ad
es. un microcircuito elettronico bistabile; del materiale magnetizzabile di un disco o di
un nastro etc.) che puo’ trovarsi in DUE stati i quali simboleggiano la cifra 0 e la cifra 1
rispettivamente. In tal modo ad ogni parola o registro (che spesso al giorno d’oggi e’
composta da 8 bytes, cioe’ 64 bits) e’ associabile un numero binario. Tutti i dati (numeri,
lettere e caratteri, istruzioni di un programma) vengono codificati in numeri binari.
21*
Il numero 19(10) viene messo in una parola di 32 bits col suo equivalente binario :
00000000000000000000000000010011
La parola Roma viene immagazzinata usando per ciascuna lettera 1 byte e codificando con
il codice ASCII
R
01010010 ; o
01101111 ; m
01101101 ; a
01100001
I bytes vengono ‘accostati’ l’uno all’altro formando una parola di 32 bits in totale.
Nell’accostarli il carattere piu’ a sinistra viene messo dalla parte dei bits meno significativi
(cioe’ quelli per cosi’ dire ‘piu’ a destra’) compiendo cosi’ in un certo senso una ‘inversione’.
Quindi alla fine Roma viene immagazzinata in 32 bits come segue :
01100001011011010110111101010010
Il codice ASCII originariamente era uno standard USA; oggi e’ diventato internazionale.
La codificazione dei caratteri e’ ‘machine independent’ e quindi permette di trasportare
facilmente qualsiasi file di informazione da un computer ad un altro.
22*
Tabella ASCII X3.4-1977
http://www.cs.utk.edu/~shuford/terminal/ascii_table.txt
23*

Istruzioni e linguaggi dei computers
Il computer per eseguire il programma obbedisce ad una sequenza di istruzioni. Le
istruzioni, al livello piu’ basso, vengono scritte in ciascuna parola del file contenente il
programma, in CODICE MACCHINA, che dipende dal particolare computer. Ad
esempio, una parola del tipo 011000000000011001010000 potrebbe significare : prendi il
contenuto della locazione di memoria chiamata B e copialo nel registro n. 3 della CPU.
Storicamente il codice macchina fu il primo linguaggio sviluppato. In seguito, per
motivi di praticita’ fu introdotto il linguaggio assemblatore (ASSEMBLER) che usa forme
mnemoniche piu’ facili da ricordarsi. Ad esempio, l’istruzione precedente potrebbe avere
il suo equivalente assembler in LDX 3 B dove LDX sta per load (carica). Anche
l’assembler dipende dal particolare computer, ed una istruzione assembler corrisponde
ad una operazione della CPU.
24*
Successivamente all’assembler furono inventati i linguaggi ad alto livello che hanno una
sintassi indipendente dal particolare computer e permette al programmatore di scrivere
istruzioni senza dover conoscere alcunche’ del linguaggio macchina. Il programmatore
dovra’ dunque scrivere un file ASCII in cui sono contenute le istruzioni del programma.
Ciascun computer d’altra parte, dovra’ essere dotato di un COMPILATORE cioe’ di un
programma in grado di trasformare automaticamente qualunque file ASCII di istruzioni
del linguaggio ad alto livello in un file contenete l’equivalente in codice macchina.
Le istruzioni del linguaggio ad alto livello avranno una sintassi facile da ricordare ed
usare, con comandi che corrispondono a piu’ comandi di codice macchina. Sara’ cosi’
possibile usare un programma su qualunque macchina, a patto che abbia il compilatore
adatto, e verra’ facilitato lo sviluppo di programmi (software) anche complessi da parte di
piu’ persone.
Il FORTRAN 77 (ForTran = Formula Translation) e’ un linguaggio ad alto livello. Altri
esempi sono : COBOL, PASCAL, BASIC, C, C++. Il Fortran 77 venne codificato nel 1980.
E’ specialmente adatto per fare calcoli numerici per progetti, simulazioni, etc. Per questo
linguaggio esistono inoltre molte librerie, cioe’ raccolte di programmi gia’ scritti nel corso
degli anni che semplificano ed alleviano la mole di lavoro al programmatore.
25*

Multitasking e time sharing
I computers odierni in generale sfruttano il principio della multiprogrammazione
(multitasking) che si basa sul fatto che il tempo con cui una CPU esegue calcoli
matematici o logici e’ molto inferiore al tempo con cui il computer trasferisce i dati
dall’input alla CPU o dalla CPU all’output. Si risparmia tempo complessivamente se si
eseguono piu’ programmi in una volta e mentre i dati di un programma vengono
trasferiti (in maniera automatica che non coinvolge la CPU) la CPU esegue calcoli per un
altro programma.
Un altro principio oggi seguito e’ quello del time sharing che permette l’uso del
computer da parte di piu’ utenti alla volta che di solito agiscono da terminale (modo
interattivo). Ciascun utente ha il diritto di usare il computer per una frazione di tempo,
che dipende dal numero totali di utenti presenti in quel momento, ed interagisce
direttamente col computer. Dato che il terminale ha bassa velocita’ di input (dovuto
soprattutto alla lentezza umana ma anche alla bassa velocita’ intrinseca del terminale
rispetto ad una CPU) il computer puo’ servire piu’ utenti alla volta senza che quest’ultimi
in pratica ne risentano troppo.
26*

Sistema operativo
Ogni computer usa un proprio sistema operativo che non e’ altro che un programma
sempre in funzione sulla macchina quando l’utente non sta facendo girare il proprio. Il
sistema operativo permette al programmatore di definire tutte le operazioni che la
macchina deve fare, come ad esempio compilare un file di istruzioni fortran (simbolico),
eseguirlo, creare dei files, fare una lista dei files presenti in memoria, spedire un messagio
per posta elettronica (e-mail) e mille altre funzioni (applicazioni). Quando un utente
incomincia una sessione sul computer (login) il sistema operativo viene messo
automaticamente in funzione. Il sistema operativo riconosce il linguaggio di controllo del
lavoro (JCL) che l’utente dovra’ usare. Sfortunatamente fino a pochi anni fa ogni computer
aveva JCL propri, e l’utente doveva impararsi i linguaggi di controllo per ciascun
computer.

Unix
Un grosso passo avanti nella standardizzazione e’ stato compiuto con l’introduzione di
UNIX, un sistema operativo concepito inizialmente nel 1969 da Ken Thompson e da allora
sviluppato da molti ed oggi usato quasi universalmente. Una versione di Unix molto usata
oggigiorno (ad es. sui PC) e’ LINUX .
Esistono diverse versioni di JCL per Unix, che tra loro non differiscono moltissimo. Quelle
oggi piu’ in auge si puo’ dire siano la Bourne shell (sh) , la C shell (csh) , la Korn shell
27*
(ksh)). Noi useremo la C shell.

Come cominciare una sessione dal PC del laboratorio
a) Cercare l’applicazione Telnet e connettersi ad axppv1.pv.infn.it
b) Eseguire il login :
Trying 192.84.142.1 …
Connected to decux1.pv.infn.it
Escape character is ‘^]’
Digital UNIX (decux1.pv.infn.it) (ttyp1)
username
Password (non compare)
login: boca
Password:
Last login: Wed Dec 29 20:09:56 from axppv1.pv.infn.it
Digital UNIX V4.0D (Rev. 878); Tue Dec 28 16:36:44 MET 1999
*******************************************************************
decux1>
28*
D’ora in avanti la notazione in blu verra’ usata per indicare i caratteri che vengono
scritti al terminale in input dall’utente, in verde i caratteri scritti in risposta dal
computer, mentre la notazione in corsivo verra’ usata per simboleggiare dei caratteri da
scrivere o per indicare cose da fare da parte dell’utente

Cambiare la password
La password deve avere da 6 a 8 caratteri (in molti computers puo’ essere piu’ lunga).
Comando : passwd
L’utente BOCA vuole cambiare la sua password
passwd
Changing password for boca.
Old password: vecchia password
New password: nuova password
Verification: riscrivo la nuova password per sicurezza
29*

Directories
In memoria, per esigenze di ordine e comprensione, e’ molto utile organizzare gruppi di
files in directories. Questo significa che ogni file viene associato ad una directory.
In UNIX ciascun file viene di conseguenza identificato come segue :
directoryname/filename
Dopo che si e’ fatto il login nel computer ci si trova automaticamente nella home directory
che, ad esempio, per l’utente boca su axppv1.pv.infn.it si chiama
/home/boca
Se a questa directory fosse associato ad esempio il file prova allora il nome completo del
file sarebbe /home/boca/prova Esistono comandi per associare un file ad una particolare
directory, per fare la lista di tutti i files che appartengono ad una data directory, ed un
comando per sapere in che directory ci si trova (cioe’ sapere qual’e’ la directory di
default ). Directory di default significa la directory che viene sottointesa automaticamente
- a meno che essa venga esplicitamente indicata - in tutti i comandi Unix. Percio’ se non ci
sono esplicite indicazioni, quando si crea un nuovo file esso viene associato alla directory
di default; quando si fa una lista di files esistenti tale lista e’ quella dei files associati alla
direcotry di default ecc. ecc.
30*

Sapere in che directory ci si trova (directory di default)
Si usa il comando pwd
pwd
/home/boca

questo e’ il nome della corrente directory di default
Creazione di una nuova directory
L’utente puo’ creare una nuova directory col comando mkdir
pwd
/home/boca
mkdir dimostrazione
A questo punto e’ stata creata una nuova directory il cui nome completo e’ :
/home/boca/dimostrazione
31*
cioe’ alla directory di default e’ stata aggiunta una / e poi il nome dimostrazione

Cambio di directory
Per cambiare la directory di default di usa cd
pwd
/usr1/users/boca
cd dimostrazione
pwd
/usr1/users/boca/dimostrazione
L’utente boca si trovava inizialmente nella directory /usr1/users/boca, quindi col comando
cd ha definito come directory di default quella vecchia (/usr1/users/boca) + /dimostrazione
e quindi ora si trova nella directory /usr1/users/boca/dimostrazione come e’ dimostrato dal
susseguente comando pwd

Elenco dei files appartenenti ad una data directory
e/o aventi un certo nome
Si usa il comando
ls nomedirectory oppure ls nomefile
32*
ESEMPIO
ls /usr1/users/boca/cestino
prova
prova.bak prova1
prova1.bak
L’utente boca ha richiesto l’elenco dei files appartenenti alla directory
/usr1/users/boca/cestino ed il computer ha elencato i files esistenti cioe’ prova prova.bak
prova1 e prova1.bak
ESEMPIO
pwd
/usr1/users/boca/cestino
ls
prova
prova.bak prova1
prova1.bak
In questo secondo esempio l’utente boca si trovava gia’ nella directory
/usr1/users/boca/cestino (come testimonia il comando pwd) ed ha mandato il comando ls
senza specificare alcuna directory : il computer percio’ ha assunto come directory quella di
default. Il risultato dell’elenco e’ percio’ identico a quello dell’esempio precedente.
ESEMPIO
ls /usr1/users/boca/cestino/prova
prova
In questo esempio l’utente ha richiesto una lista di uno specifico file.
ESEMPIO
ls /usr1/users/boca/cestino/pro*
prova
prova.bak prova1
prova1.bak
In questo esempio si e’ richiesto l’elenco di tutti i files che iniziano per pro nella directory
33*
/usr1/users/boca/cestino Si noti l’uso dell’asterisco (carattere speciale o metacarattere)
che
significa qualunque numero e tipo di carattere di seguito ai caratteri pro

Compilazione di simbolici Fortran
Per produrre un programma fortran bisogna tradurre il file ASCII che contiene le
istruzioni in un file che contiene le istruzioni macchina. Per fare questo in UNIX c’e’ il
comando
f77 -static -o nomeoutput nomeinput
ls
prova.for
f77 -static -o prova.exe prova.for
ls
prova.for prova.exe
L’utente ha compilato (e ne ha anche fatto il linking) del simbolico (scritto in ASCII)
contenuto nel file prova.for il risultato (programma eseguibile) e’ stato messo nel nuovo file
prova.exe
34*

Stampa del contenuto di un file ASCII a terminale
Si possono usare diversi comandi per farlo. Ad esempio c’e’
cat nomefile
oppure
more nomefile
con cat il file viene stampato interamente e di seguito, con more il file viene interamente
stampato, ma con la possibilita’ di vederlo per pagine. Nomefile puo’ essere
sia il nome completo del file (cioe’ con all’inizio la directory alla quale appartiene) oppure
puo’ non avere la directory di appartenenza, nel qual caso il computer assume la directory
di default.
35*

Richiesta di istruzioni sull’uso di un comando
In UNIX esite la possibilita’ di richiedere informazioni su come funziona un dato
comando. L’istruzione da dare a terminale e’
man nomecomando
Ad esempio, se si vogliono informazioni dettagliate sul comando ls basta battere man ls ed
una lunga lista di istruzioni comparira’ sul terminale, con la possibilita’ di vederlo per
pagine.

Rimozione di un file
Si usa il comando
rm nomefile
Al solito, se nomefile non e’ il nome completo di directory, viene assunta la directory di
default.
ls
prova
prova.bak prova1
prova1.bak
rm prova.bak
ls
prova
prova1
prova1.bak
36*
L’utente ha rimosso dalla corrente directory il file prova.bak dalla directory di default,
come e’ testimoniato dal comando ls eseguito dopo la rimozione

Creazione di un file ASCII con un text editor
Una necessita’ che si presenta spessissimo
nell’uso di un computer, e’ il creare o
modificare dei files ASCII. Il text editor e’ un programma che fa questo. Ci sono svariati tipi
di text editors, noi useremo vi oppure nedit Il comando e’
vi nomefile oppure nedit nomefile
dove nomefile puo’ essere sia un file nuovo che un file gia’ esistente. Come sempre, se la
directory non e’ esplicitata nel nome del file, quella di default viene assunta. L’uso ed i
comandi di vi ed nedit sono articolati e complessi e se ne puo’ avere il dettaglio con
i comandi
man vi
oppure
man nedit
37*
Unix e’ concepito specialmente per macchine multiuser e multitasking

Architettura di un sistema operativo
Schematicamente un sistema operativo e’ fatto a strati, con un nocciolo di funzioni e
programmi piu’ interne (kernel) e 3 strati via via piu’ esterni.
Le funzioni del kernel controllano
direttamente l’hardware del computer user interface
utilities and tools
(controllo della memoria e della
system services
CPU e delle varie periferiche).
kernel
Le funzioni dello strato system
services chiamano le funzioni
del kernel. Il linguaggio
ASSEMBLER fa uso delle
funzioni di questo strato.
38*
A volte anche linguaggi a piu’ alto livello chiamano queste routines per ottenere maggiore
rapidita’ di esecuzione. Il software dello strato utilities and tools rende la complessita’ delle
chiamate alle routines del system service trasparente all’utente. In questo strato ci sono ad
esempio i compilatori dei linguaggi ad alto livello ( fortran, C, C++, cobol, pascal, etc. ), la
utilities mail od il tool dbx ( debugger di programmi fortran). Distinguiamo le utilities dai
tools sulla base della maggior complessita’ delle prime rispetto ai secondi. Nello strato piu’
esterno infine, c’e’ l’interfaccia con l’utente cioe’ la shell o command language interpreter,
che viene usato per impartire i comandi al computer.
Le shell che sono diventate d’uso piu’ comune in Unix sono :
Bourne shell
C shell
Korn shell
( sh )
storicamente la prima disponibile, che viene inclusa in tutte le versioni
di Unix
( csh ) standard nei sistemi che usano il software Berkeley Software
Distribution
( ksh ) standard per il software Sistem V ( AT&T)
Le varie Unix shells differiscono tra loro per le funzioni che svolgono e per la sintassi dei loro
comandi, ma tutte passano il controllo alle stesse funzioni al momento dell’esecuzione, con
l’eccezione di alcuni comandi tipici di quella shell.
39*

Come cambiare la shell di default
Per cambiare la shell di default si usa il comando :
chsh
chsh
changing shell for studente.
Password:
New shell [/bin/bash: /bin/tcsh
Shell changed.
40*

Processi e loro priorita’
Chiamiamo process un programma attivo. Quando un utente incomincia una nuova
sessione a terminale, viene attivato il programma costituito dalla shell usata per default, che
attende ed esegue i comandi dati da terminale. Questo e’ un esempio di process a cui il
sistema assegna un numero ( process identifier ) che unicamente lo identifica.Questo process
ha accesso alle risorse della macchina ( CPU, memoria, periferici ) con una certa priorita’
che gli viene assegnata dal sistema stesso. La parte del kernel responsabile dello scheduling
la assegna dinamicamente, aggiornandola ogni pochi secondi, calcolandola con un
algoritmo complesso, che si basa anche su una priorita’ di base data dal system manager
all’utente.

Parent process e child process
Come gia’ detto, al momento del login viene attivato un process ( la shell ). Questo e’ un
parent process . Quando diamo un comando da terminale, il process della shell viene
interrotto ed un nuovo process, che esegue il comando, viene attivato. Quando quest’ultimo
termina, il comando viene restituito alla shell, che riprende a funzionare. In Unix si dice che
e’ stato generato un child process (quello che esegue il comando) da parte di un
parent process (la shell).Questo meccanismo vien detto forking . Al child process viene
assegnato un proprio process identifier number. Un child process puo’ a sua volta iniziare
41*
un altro process, diventando a sua volta parent process di un child process.

Multitasking in UNIX
Multitasking ( o multiprocessing ) significa l’attivazione, da parte di un solo utente, di piu’
programmi contemporaneamente. In Unix il multitasking si ottiene quando un parent
process fa il forking di uno o piu’ child process e tutti i process sono attivi
contemporaneamente. Un esempio di multitasking e’ la stampa di un file alla line printer,
durante la quale si possono eseguire altri comandi. In Unix ci possono essere piu’ process
attivi o sospesi contemporaneamente, ma solo uno puo’ ricevere input da terminale.
Questo si dice process in foreground mentre gli altri sono in background .

NOTA BENE 
I processi attivi in background continuano anche quando il parent process che li ha lanciati
esegue un logout dal computer. Se invece ci sono processi sospesi al momento del logout,
allora un messaggio di avviso viene mandato a terminale ed il logout non viene eseguito. Se
l’utente ripete il comando logout allora la sessione termina ed i processi interrotti vengono
persi.
42*
I comandi per fermare, mettere in background o portare in foreground un processo sono :
1) <ctrl>c termina un child process ( job ) che e’ attivo in foreground
2) <ctrl>z sospende l’esecuzione (ma non la termina) di un job che e’ attivo in foreground
3) &
lancia un child process in background
4) fg n oppure fg %n porta in foreground un child process sospeso od attivo in background
5) bg n oppure bg %n fa diventare attivo un process sospeso e lo porta in background
f77 -static -o myfile.x myfile.f
compilazione e link del file fortran myfile.f
<ctrl>z
la compilazione viene sospesa
Stopped
messaggio a terminale, mandato del sistema, che avvisa della sospensione
cat myfile.f
stampa a terminale di myfile.f
fg
riporta in attivita’ in foreground, il process sospeso
f77 -static -o myfile.x myfile.f
messaggio a terminale che avvisa della ripresa della
compilazione e link
43*

Shell scripts
Si definisce una shell script un ASCII file contenente dei comandi Unix.
il seguente ASCII file e’ un esempio di shell script :
ls -l *
cat pippo
mv pippo pluto
In Unix si puo’ attivare una shell script semplicemente battendone a terminale il nome
del file ASCII che la la contiene. Quando si attiva uno script, il sistema esegue ciascun
comando dello script come se lo stessimo battendo da terminale

Il comando <<
In una shell script, si usa il comando
<< label
per indicare ad un programma quando finisce l’input che deve leggere.
44*
immaginiamo di avere il programma myprogram.x che legge 5 numeri da terminale e ne fa
la media. Si consideri la seguente shell script :
….
myprogram.x << end
9.1 2.4 5.6
7.8 9.2
end
….
Questo script, arriva all’esecuzione del comando myprogram.x ed il << fa si’ che tutte le
righe a partire dalla successiva, fino a quella che precede la label end vengano considerate
come dati in ingresso per il comando stesso. Se non ci fosse << end lo script prenderebbe
input per myprogram.x da terminale (standard input).

Piping
La creazione di una pipe e’ un tipo particolare di attivita’, sincronizzata dal kernel, che
coinvolge piu’ processes, nella quale l’output di un comando diventa input del comando che
segue, senza bisogno di creare un file intermedio. Il piping e’ indicato dalla barra
verticale | Questo comando e’ particolarmente utile e conferisce ad Unix una flessibilita’
45*
sconosciuta ad altri sistemi operativi.
anticipiamo qui che il comando who elenca gli usernames che hanno attualmente una
sessione aperta sul computer, mentre sort ordina alfabeticamente le righe di un testo
ASCII. Infine more stampa il contenuto di un file (interpretato come file ASCII) ad una
pagina per volta.
who | sort | more
questi tre comandi fan si’ che il kernel inizi 3 child process contemporaneamente,
corrispondenti ai comandi who , sort , more. Tuttavia more aspettera’ input da sort che
aspettera’ input da who . Quando l’output di who sara’ passato a sort , il child process
responsabile di who finira’, e cosi’ quando in seguito sort avra’ passato tutto l’output
a more, cessera’. Infine quando more avra’ finito di mandare output allo standard
output, terminera’ ed il controllo ritornera’ al parent process.
46*

Ridirezionamento dello standard input, output, error
Come gia’ detto piu’ sopra, in Unix vengono definiti
stdin
input stream, solitamente la tastiera del terminale
stdout
output stream, solitamente lo schermo del terminale
stderr
device o file dove vengono mandati i messaggi di errore, di solito
lo schermo del terminale.
In Unix e’ possibile, in modo semplice, comodo ed elegante, ridirezionare stdin , stdout ,
stderr su devices o files che non siano quelli dati di default all’inizio della sessione
(terminale), con i simboli della seguente tabella
47*
simbolo
>
>!
>>
>>!
>&
>&!
>>&
>>&!
<
<< xxx
|
| tee nomefile
|&
significato
ridireziona stdout
ridireziona stdout, senza tenere conto di noclobber
ridireziona ed appendi stdout
ridireziona ed appendi stdout senza dare errore e creando un nuovo file
se ancora non esiste
ridireziona stdout e stderr
ridireziona stdout e stderr, senza tenere conto di noclobber
ridireziona ed appendi stdout e stderr
ridireziona ed appendi stdout e stderr senza dare errore e creando un
nuovo file se non esiste di gia’
ridireziona stdin
leggi l’input fino alla linea identica con xxx
ridireziona stdout al prossimo comando (piping)
ridireziona stdout, oltre che alla schermo, anche ad un file
ridireziona stdout e stderr al prossimo comando
48*
ls * > output
questo comando fa si’ che l’output di ls * venga messo nel file (ASCII) output invece che
visualizzato al terminale. Se il file output esistesse gia’, verrebbe sovrascritto dalla nuova
versione ( in gergo Unix : clobbering ) e la vecchia versione verrebbe persa.
L’utente puo’ impedire il clobbering (per evitare che uno sbaglio faccia perdere un file)
con il comando
set noclobber
cosi’ che il sistema avvisa che il file esiste gia’ ed impedisce l’esecuzione del comando.
Un altro esempio e’ dato da :
ls -l * >! output
ls -l pippo* >>& output
dove prima viene ridirezionato l’output del comando ls -l * nel file output , facendo
eseguire l’operazione ( grazie a ! ) anche se e’ stato fatto precedentemente set noclobber .
Il secondo comando appende ( aggiunge ) il risultato del comando ls -l pippo* al file output.
Anche eventuali messaggi di errore generati dal comando ls verrebbero stampati in output .
49*

Nomi dei files in UNIX
I nomi dei files e dei comandi Unix sono case sensitive . Le MAIUSCOLE precedono le
minuscole. Esistono delle convenzioni, non obbligatorie, ma generalmente seguite, riguardo
alle estensioni che si danno ai files
estensione
.a
.bas
.c
.cc
.f
.h
.l
.o
.p
.s
.y
a.out
significato
libreria di objects
source code di basic
source code di C
source code di C++
source code di fortran
header file per il C
programma di lex
object file ottenuto dalla compilazione del source code
source code per pascal
source code di assembler
programma id yacc
programma eseguibile
50*

Struttura dei comandi Unix
Con poche eccezioni, la forma di un comando Unix e’ la seguente :
nomecomando [ opzioni ] [ argomenti ]
dove le [ ] significano che puo’ anche non esserci, e :
• nomecomando sono generalmente lettere minuscole che caratterizzano il comando ;
• le opzioni modificano l’azione del comando e di solito sono singole lettere precedute da - ;
si possono combinare assieme e di seguito piu’ opzioni facendole precedere da un unico oppure separatamente, con uno spazio in mezzo e precedute da -
Il comando
ls -l -t
fa una lista lunga ( opzione l ) di tutti i files presenti nella current directory ordinandoli
temporalmente ( opzione t , i files piu’ recenti vengono elencati per primi). Stesso risultato
si otterrebbe con
ls -lt
51*
L’argomento e’ generalmente l’oggetto su cui agisce il comando
nomecomando , opzioni , argomento devono essere separati da spazi o tab che, tranne
poche eccezioni, sono gli unici delimitatori validi in un comando Unix.
Si definisce word quei caratteri compresi tra due delimitatori consecutivi. Un semplice
comando Unix percio’, e’ una sequenza di una o piu’ words comprese tra spazi o tabs.
Vengono definite words separate (anche se sono in compagnia di altri caratteri) i caratteri
& |
< > ; ( ) #
I caratteri
&& ||
<<
>>
vengono considerate come una ( non due ) word.
il comando
ls -lt
e’ formato da 2 words, mentre il comando
ls -lt | more
e’ per Unix composto da 4 words.
52*
Si possono mettere piu’ comandi su una stessa linea, separandoli con ; che, in questo
caso, ha la stessa funzione del carriage return.
i seguenti comandi
pwd ; ls -lt
sono equivalenti a
pwd
ls -lt
Per continuare un comando sulla prossima riga si usa \
prima del return che termina la
linea ( deve essere l’ultimo carattere prima del return ).
53*

Devices, directories e struttura dei files
In Unix un file e’ identificato in maniera piu’ generale da
host:/ directory / filename
dove
host:
nome del computer dove il file risiede. Di solito host: si omette
e viene usato solo da comandi come rcp o scp
directory nome della directory alla quale il file appartiene
filename nome del file
• Si definisce file system un insieme di files e directories organizzato gerarchicamente, con
una directory principale in cui ci possono essere files ed altre directories ; in quest’ultime
ci possono essere altre directories, etc.
• /
e’ il
root file system
54*
In Unix non c’e’ la necessita’ di esplicitare il nome del device dove il file fisicamente risiede
(tranne nel caso sia un nastro). Il sistema Unix determina dove si trova il file andando a
leggere /etc/fstab che e’ il file sysem table, dove sono registrati su quali dischi stanno
fisicamente tutti i file systems.
il seguente e’ un esempio di /etc/fstab
55*
Il sistema utilizza /etc/fstab ad ogni reboot del computer per montare (assegnare) i vari
devices fisici sugli appropriati file systems.
L’utente puo’ controllare con
df
i file systems montati ed anche la percentuale di spazio rimasto a disposizione.
questo e’ un esempio del printout generato da df
56*

Nomi comunemente dati ad alcuni devices
I devices piu’ comunemente usati, hanno in Unix nomi leggermente variabili a seconda
della particolare implementazione e computer. Un esempio e’ dato nella seguente tabella
nome device
/dev/ra0
/dev/rra0
/dev/console
/dev/tty01
/dev/printer
/dev/mt0
/dev/rmt0
/dev/null
descrizione
disk drive ( block )
disk drive ( character )
system console
asynchronous terminal
default system printer
tape drive ( block )
tape drive ( character )
cestino
Da notare l’esistenza di /dev/null che funziona da cestino. Mandandogli dell’output od
un file, questo viene perso. Analogamente, se si legge da /dev/null si ha subito un
end of file. Il comando
cp /dev/null myfile
57*
ha l’effetto di creare il file myfile che e’ vuoto.

Nomi comunemente dati ad alcuni directories
In Unix vi sono delle convenzioni, solitamente seguite, sul nome da dare a directories che
contengono particolari files, vedi tabella seguente.
nome
directory
/bin
/dev
/etc
/lib
/tmp
/usr/adm
/usr/bin
/usr/dict
/usr/share/man
/usr/spool
/usr/tmp
contenuto
files eseguibili di sistema, frequentemente usati
files speciali, che indirizzano devices
miscellanea di files vari
files di librerie
files temporanei ( scratch files )
files amministrativi di sistema
files eseguibili di sistema, meno frequentemente usati
files del dizionario
files del manuale man
files che devono essere spooled ( scaricati ) alle code stampanti
files di swap e page
58*

Definizioni assolute e relative di files
La definizione esplicita di un file Unix per mezzo del nome completo a partire dalla root
directory / e’ detta definizione assoluta del file. Come gia’ detto altre volte, delle /
delimitano il directory pathway attraverso tutte le sottodirectories. Tutte le definizioni di
files che cominciano con / sono assolute. Invece, le definizioni che partono dalla current
directory si dicono definizione relativa di un file e non cominciano mai con la barra.
/home/boca/cestino/prova
cd /home/boca/cestino
ls prova
e’ un esempio di definizione assoluta di un file
questo e’ un esempio di uso della definizione relativa di un file
59*
ls -l /home/boca/cestino
questo e’ un esempio di ricerca dei files contenuti nella
directory, indicata con definizione assoluta, /home/boca/cestino
cd /home/boca
ls -l cestino
questo e’ un esempio di ricerca di files contenuti nella stessa
directory indicata, questa volta, con una definizione relativa a partire dalla directory
/home/boca
ls ~boca
la ~ seguita da uno username ( boca ) indica la home directory dell’utente
( in questo caso /home/boca ). Questo e’ un esempio di filename substitution (globbing ).
Questo comando e’ in definitiva equivalente a ls /home/boca
cd /home/boca/cestino
ls -l ../bin
il doppio punto ( .. ) indica la directry appena sopra ( altro esempio
di globbing). Il comando percio’ equivale a ls -l /home/boca/bin
cd /home/boca
ls -l .
il singolo punto indica la presente directory. Il comando percio’
equivale a ls -l Anche questo e’ un altro esempio di globbing.
60*

Tipi di files in Unix
Ci sono 3 tipi di files in Unix : i files speciali , i files ordinari ed i directory files.
a) Tutti i devices ( dischi, tape drivers, printers, terminali, e pseudoterminali - quelli usati
durante le connessioni alla rete ) vengono trattati come files speciali i quali, come gia’
visto in precedenza, risiedono nella directory /dev Si ottiene un printout sulla line printer,
ad esempio, scrivendo allo special file che individua la line printer. Questo normalmente
viene fatto tramite i comandi della C-shell, ma in alcuni casi l’utente lo puo’ fare anche
direttamente.
b) I files ordinari contengono caratteri ASCII o binari. Copiando un file ordinario in uno
special file, si otterra’ l’output del contenuto sul device associato allo special file. Di default
Unix NON formatta il file ( cioe’ non aggiunge bits al contenuto del file ) tranne per un
<ctrl>D ( end of file ) alla fine del file. Casomai puo’ essere il comando o programma usato
dall’utente ad interpretare o scrivere in certo modo i dati ( si pensi alla scrittura ASCII dei
caratteri col Fortran 77, ad esempio ).
c) Dei directoy files si e’ gia’ parlato. Un directory file ha una entry per ciascun file
contenuto nella directory ed oltre al nome del file ed altre informazioni, contiene anche l’
inode del file. Quest’ultimo e’ un numero che unicamente identifica ciascun file ( si puo’
vedere l’ inode con il comando ls -i nomefile ).
61*

Hidden files
Sono una particolare classe di files ordinari, e cominciano il loro nome con un punto ( . )
Il loro nome e’ dovuto al fatto che non vengo listati dal comando ls a meno che non si usi
l’opzione -a ( list all ). La tabella che segue fa un sommario dei principali hidden files e
della loro funzione. Il motivo per cui sono ‘nascosti’ e’ che cosi’ l’utente ha meno
probabilita’ di danneggiarli …. In realta’ l’utente li puo’ modificare per farli aderire alle
proprie esigenze. Generalmente si trovano tutti nella directory $HOME dell’utente.
62*
nome
hidden file
funzione
eseguito all’inizio della sessione, ma dopo aver eseguito il .login di sistema e
prima di aver chiamato il file $HOME/.login Solo se si usa la C-shell viene
chiamato .cshrc Usualmente si usa per definire environmentals, alias e
definire altre opzioni e paramentri.
.exrc
definizione degli environmentals per l’editor ex
.forward
definisce il forwarding address per il mailer
.history
contiene la history list
.hushlogin disabilita alcuni messaggi di login
.login
viene eseguito all’inizio della sessione, qualunque sia la shell di default
usata dall’utente. Qui si definiscono environmentals e si settano preferenze
etc. che vanno usate indipendentemente dalla particolare shell usata.
.logout
viene eseguito subito prima del termine della sessione. Qui l’utente mette
tutto cio’ che vuole eseguire appena prima della chiusura della sessione.
.mailrc
contiene le definizioni degli environmentals per il programma mail
.netrc
contiene i parametri per il programma ftp
.profile
analogo al file .cshrc tranne che viene eseguito ( dopo il .login sistema) se
si usa la Bourne shell
.rhosts
vengono indicati gli utenti e macchine remote alle quali lo user permette di
accedere al computer tramite il proprio account.
63*
.cshrc

Caratteri speciali
In Unix alcuni caratteri vengono interpretati in modo speciale dalla shell e vengono chiamati
metacaratteri. La tabella che segue ne elenca alcuni di quelli non citati precedentemente per
il redirecting ; quelli asteriscati hanno un significato speciale solo per la C-shell. Da notare
che il significato di un metacarattere puo’ variare a seconda che venga interpretato dalla
C-shell o da una Unix utility.
64*
Il metacarattere * ( wildcard ) ha in generale il significato di sostituzione di un numero
arbitrario di caratteri arbitrari (vedi in seguito) ; il suo effetto tuttavia puo’ differire
leggermente a secondo del comando Unix che lo usa.
ls *
questo comando produce la lista di tutti i files della directory corrente e delle directories
ad un livello piu’ basso nella gerarchia delle directories ( in questo caso * ha un effetto
maggiore che la semplice sostituzione ).
Invece il comando
wc * produce il word counting per tutti e solo i files della directory corrente.
Il comando
ls
.
invece, fa la lista della directory corrente soltanto, mentre
wc . interpreta il
(se esiste).
.
letteralmente andando a fare il word counting di un file di nome
65*
.
TABELLA DEI METACARATTERI ( I )
metacarattere
&
&&
=
==
!=
=~
!~
<=
>=
||
;
\
\m
‘
`
“
#
!
%
*
?
funzione
esegue il comando in background
and Booleano
operatore di assegnazione
uguale a ; e’ una comparazione di stringhe di caratteri
diverso da ; e’ una comparazione di stringhe di caratteri
simile a ; e’ una comparazione di stringhe di caratteri
dissimile da ; e’ una comparazione di stringhe di caratteri
minore od uguale a
maggiore od uguale
doppia barra ; or Booleano
separatore di comandi
comando di continuazione della linea di comando
traduzione letterale del metacarattere m
togli il significato speciale
esegui immediatamente
raggruppa i caratteri in un unico comando
seguono dei commenti fino al prossimo carriage return
history substitution
significa un job in background
wildcard , sostituzione di qualunque numero e tipo di caratteri
wildcard, sostituzione di un singolo carattere
66*
TABELLA DEI METACARATTERI
metacarattere
$
$#
$$
$?
$<
@
~
[]
.
{}

( II )
funzione
segue una sostituzione di argomento
numero di argomenti passati ad uno shell script
Process ID
Exit status
legge una linea da stdin
esegui un calcolo numerico
home directory substitution
filename selective substitution
current directory
delimitatore usato in vari comandi
NOTA BENE 
• Facendo precedere un metacarattere da \ ha l’effetto di toglierne il significato speciale
(il metacarattere viene interpretato come carattere normale).
• Facendo precedere \ ad un carriage return si fa diventare quest’ultimo equivalente ad
uno spazio.
• I caratteri racchiusi tra “ (double quotes) oppure ` (grave accents) oppure ‘ (single
quotes) formano UNA word. I metacaratteri racchiusi non formano word separate.
E’ possibile includere il carattere carriage return tra apici o apici doppi, a patto67*
di
farlo precedere da \

Wildcards
In Unix alcuni metacaratteri vengono usati come wildcards, tipicamente per indicare
nomi di files. La wildcard non viene presa letteralmente dal sistema, ma ad essa vengono
sostituiti uno o piu’ caratteri.
Le wildcard in uso nella C shell sono indicate nella tabella seguente
TABELLA DELLE WILDCARDS
wildcard
*
*.com
pipp*
*.*
?
?.com
prova[xyz]
prova[a-z]
prova[a-z4]
prova{o,f}
funzione
nome composto da un qualunque numero di caratteri qualunque
qualunque nome di file che termini in .com
qualunque nome di file che inizia con pipp
qualunque nome di file che contenga almeno un .
sostituzione di UN (solo uno!) carattere qualunque
qualunque nome di file che termini in .com preceduto da un carattere
qualunque
le [] indicano sostituzione di uno dei caratteri contenuti nelle parentesi.
Quindi in questo caso indica il nome di file provax oppure provay o
oppure provaz
un qualunque nome tra quelli da provaa fino a provaz
un qualunque nome tra quelli da provaa fino a provaz piu’ prova4
68*
stesso significato di prova[of]
Quando si inizia una sessione Unix, occorre definire un certo numero di environmentals
o variabile di ambiente indispensabili per poter lavorare (vedi qualche trasparenza piu’
sotto la spiegazione delle variabili d’ambiente).
Fortunatamente, in genere l’utente non deve preoccuparsi di queste definizioni che vengono
effettuate dal login di sistema, e dalla esecuzione automatica della .cshrc e del .login che
risiedono nella propria home directory.
69*

Operazioni del sistema al momento del login
Quando il prompt del login appare sullo schermo, e l’utente fa il login, il sistema Unix
compie un certo numero di operazioni :
il programma /etc/init legge una lookup table che si trova in /etc/ttys e che contiene una
stringa per ogni device del tipo terminale ( /dev/tty ) o pseudo-terminale ( /dev/ptty )
disponibi le al sistema.
Unix usa un descrittore di 5 caratteri : tty che indica terminale, poi un esadecimale per il
numero di controller, un altro esadecimale per il numero di linea ( ad es. tty01 o ttyff ).
Si puo’ usare il comando
tty
per sapere il nome del proprio terminale.
Poi /etc/init passa la stringa corrispondente al terminale al programma /etc/getty che
controlla se al nome del terminale corrisponde un’entry nella lookup table /etc/gettytab
ed in caso positivo legge i parametri del terminale ( baud rate, parity, funzione del tasto
<break> , etc. etc. ) altrimenti ne assegna di default.
70*
Quindi /etc/getty passa il controllo a /bin/login che chiede all’utente la password e la
confronta con quella ( incriptata ) contenuta nel file /etc/passwd e quindi, in caso positivo,
assicura il permesso ad entrare nel sistema. Inoltre /bin/login updata le informazioni di
accounting e cerca nel file /etc/group a quale gruppo l’utente appartiene. Un utente Unix
puo’ appartenere a piu’ gruppi. L’appartenere ad un certo gruppo fa si’ che tutti i files
dell’utente abbiano di default un certo tipo di protezione group level distinta da quella
world level e da quella user level . Si puo’ usare il comando
groups per sapere a
che gruppo si appartiene. Quindi /bin/login invoca il programma /etc/environ che
assegna le variabili di ambiente ( environmentals ) del sistema.
Infine /bin/login sempre grazie all’informazione contenuta in /etc/passwd assegna una
copia della shell di default al’utente. Normalmente la Bourne shell ha come prompt il $ ,
mentre la C-shell ha il %
In Unix tutti gli utenti hanno lo stesso tipo di privilegi, eccetto il superuser con login
name root che ha tutti i privilegi possibili ( e che normalmente e’ il manager del sistema).
Quando un utente si collega, appaiono allo schermo un certo numero di messaggi di
sistema che si possono eliminare creando il file ( anche vuoto ) .hushlogin nella propria
home directory.
71*
Come detto, il file /etc/ttys contiene le informazioni relative al terminale usato dalla
presente sessione, incluso il tipo di terminale ( ad es. vt100 ). A questo terminal descriptor
corrisponde una entry in un altro file, /etc/termcap nel quale ci sono altre informazioni
su un gran numero di tipi di terminali di marche diverse. Queste informazioni sono in
genere sufficienti perche’ la shell funzioni adeguatamente su quel terminale. In ogni
momento della sessione l’utente puo’ cambiare quelle specifiche.
Nelle situazioni in cui terminali differenti usano la stessa porta del computer (ad es. linee
per modem, network connections, etc.) Unix fa corrispondere una generica definizione
in /etc/ttys (ad es. dialup o network) ad una generica definizione in /etc/termcap . Poi
l’utente potra’ modificare le caratteristiche del proprio terminale usando i comandi
tset
(che assegna le caratteristiche di input/output ad una sessione da terminale) e/o
stty
(che assegna le caratteristiche alla tastiera).
Tali comandi sono piuttosto complicati. Ricordiamo qui solamente che setty e tset senza
opzioni fanno una lista delle caratteristiche correnti assegnate al terminale ed alla tastiera.
72*

Variabili d’ambiente (environmentals) e shell variables
Definizione di environmental o ( variabile d’ambiente ) :
e’ una variabile, assegnata ad un process, che viene conservata in una locazione di memoria
del computer. Questa varibile ha un valore, assegnato dall’utente o dal sistema; le varibili
d’ambiente valgono qualunque sia la shell usata dall’utente.

Come assegnare, deassegnare, stampare il valore di una
variabile d’ambiente
L’utente puo’ definire e/o assegnare un valore ad un environmental col comando
setenv ENVIRON valore
dove ENVIRON e’ il nome della variabile, valore e’ il valore dato alla variabile.
Una convenzione spesso seguita in Unix e’ quella di usare tutte lettere maiuscole per i nomi
degli environmentals.
Si puo’ eliminare una variabile d’ambiente con
unsetenv ENVIRON
e si puo’ stampare il valore di un environmental con
printenv ENVIRON
mentre printenv senza argomenti, stampa a terminale tutti gli environmentals definiti per
il processo corrente. Si puo’ anche usare il comando :
echo $nomeenvironmental
dove nomeenvironmental e’ il nome della variabile. Si noti l’uso del metacarattere $ che
73*
attua un argument substitution .
setenv DEMO pincopallino
printenv DEMO
pincopallino
unsetenv DEMO
printenv DEMO
l’ultimo comando non produce output dato che la variabile DEMO e’ stata appena cancellata dall’utente col comando unsetenv
L’utente boca ottiene la seguente stampa dopo aver dato printenv senza argomenti :
74*

Shell variables
Queste variabili sono analoghe agli environmentals eccetto che vengono definite ed hanno
validita’ solo nell’ambito della shell correntemente usata dall’utente ( ad es. la C-shell )
cessando di esistere, per esempio, se l’utente cambia shell.

Come assegnare, deassegnare, sampare il valore
di una variabile di shell
Nella C-shell l’utente puo’ usare il comando
set shellvar = valore
E’ una convenzione spesso usata in Unix di adoperare le lettere minuscole per definire le
variabile di shell . Per eliminare una variabile di shell si usa
unset shellvar
e per stampare il valore di una shell varible si usa
echo $shellvar
( notiamo il $ che e’ quello special character usato per l’ argument substitution ) mentre
set senza argomenti stampa il valore di tutte le shell variables definite.
75*
set prompt = “`hostname` >”
decux1.pv.infn.it>
l’utente ha posto nella shell variable prompt (che poi viene stampata automaticamente dal
sistema all’inizio di ogni nuova linea di comando) il valore dato dal risultato del comando
hostname piu’ il simbolo >
76*
L’utente boca ottiene la seguente stampa dopo aver dato il comando set senza argomenti
77*

Environmentals piu’ comunemente definiti al momento
del login di sistema
Come visto precedentemente, il file /etc/environ
viene eseguito dal sistema al momento del login per assegnare gli environmentals di sistema necessari per far funzionare la
sessione. Nella tabella seguente sono elencati nome e significato di quelli piu’ comunemente
definiti.
TABELLA DEGLI ENVIRONMENTALS COMUNEMENTE
DEFINITI DAL SISTEMA
nome
environmental
HOME
SHELL
TERM
USER
LOGNAME
PATH
EDITOR
MAIL
significato
home directory
pathname per la shell usata di default
tipo di terminale
user name
login name
directories in cui cercare al momento di eseguire comandi non built-in
editor di default
78*
directory dove controllare se ci sono mail messages
Particolare importanza riveste l’environmental PATH che e’ usato dal sistema quando
l’utente manda un comando che non sia built-in. In questo caso il comando (che altro non e’
che un programma) viene cercato nelle directories specificate da PATH, nell’ordine con cui
sono scritte . Ciascuna directory e’ separata dalle altre da : (due punti).

Variabili di shell comunemente impiegate quando
si usa la C-shell
Molte delle shell variables assegnate dal sistema quando un’utente invoca la C-shell
hanno lo stesso nome (ma scritto in minuscole) e stesso significato degli environmentals
corrispondenti. Un esempio e’ la variabile home che solitamente corrisponde a HOME
Nella tabella seguente sono elencate le variabili piu’ comunemente definite nella
C-shell ed il loro significato.
Per togliere l’effetto di tali variabili bisogna usare il comando
unset
79*
TABELLA DI ALCUNE SHELL VARIABLES COMUNEMENTE DEFINITE
nome della
significato
shell variable
set autologout = n
specifica il numero di minuti di idle time prima che una shell
interattiva termini
set echo
ripete i comandi dati dall’utente
set history = n
ricorda gli ultimi n comandi impartiti dall’utente
set home = string
assegna la home directory per la C-shell
set ignoreeof
impedisce che <ctrl>D faccia il logout della sessione
set mail = string
assegna la directory dove vengono messi i mail messages
set noclobber
impedisce la sovrascrittura accidentale durante la redirection
set noglob
impedisce l’espansione dei filenames
set notify
avvisa di quando un job e’ finito
set path = string
path in cui ricercare i comandi della C-shell
set prompt = string
assegna il prompt per la C-shell
set savehist = n
ricorda gli ultimi n comandi all’inizio di una nuova sessione
set shell = string
file dove si trova la shell
status
variabile che viene messa = 0 ( = buon esito del comando) od
ad un valore diverso da 0 (errore) quando finisce l’esecuzione
di determinati comandi
set time = n
per ogni comando che duri piu’ di n secondi viene riportato il
CPU time e l’elapsed time
set verbose
le parole usate per ciascun comando vengono ripetute 80*

Funzione degli hidden files .login, .cshrc e .profile
L’hidden file .cshrc viene eseguito dopo il login di sistema, e nel caso che l’utente usi la
C-shell per default.
Se invece viene usata la Bourne shell, allora viene eseguito il file .profile
In entrambi i casi, successivamente viene eseguito un altro hidden file, il .login
Tutti questi file si trovano nella propria home directory e l’utente puo’ modificarli per far
eseguire quei comandi o assegnare environmentals o shell variables all’inizio della sessione.
Ogni volta che c’e’ un forking il child process riceve tutti gli environmentals definiti
nel login di sistema, nel .login e nel .cshrc (inoltre riceve tutte le definizioni di comandi
definiti con alias , vedi seguito).
Questo succede ad es. quando l’utente impartisce un comando che non sia built-in nella shell
in uso causando cosi’ il forking di un child process che esegue il comando.

Comando alias
Serve per abbreviare o comunque dare un nome equivalente ad un comando. Sintassi :
alias
nickname
comando
dove nickname e’ il nuovo nome del comando comando.
81*
alias ll “ls -l”
dopo questo aliasing quando l’utente impartisce il nuovo comando ll
il comando ls -l
e’ come se battesse
Esempio di .cshrc file
Il seguente .cshrc file assegnera’ nuovi valori alle varibili sevehist , mail e prompt e
definisce i nuovi comandi ll e ce
set
savehist = 50
set
mail = $MAIL
set
prompt = “! $USER”
alias
ll ls -l
alias
ce
“cd ~boca/cestino ; pwd”
Esempio di .login file
Qui vengono ridefiniti gli environmentals SHELL , TERM , EDITOR , MAIL
setenv SHELL /bin/csh
setenv TERM vt100
setenv EDITOR /usr/local/bin/X11/nedit
setenv MAIL /usr/spool/mail/boca
82*

Operazioni del sistema al momento del logout
L’utente puo’ finire la sessione in due modi : con il comando logout o con il comando
<ctrl>D se ignoreeof non e’ stato assegnato (vedi sopra). <ctrl>D e’ un marker di end
of file e percio’ quando la shell lo vede termina di funzionare (e cominciano le operazioni
di logout).
In ogni caso, prima di terminare la shell esegue (se c’e’) una altro hidden file che risiede
nella home directory che e’ .logout
In questo file l’utente puo’ mettere quei comandi
che vuole che siano eseguiti prima che termini la sessione, come ad es. clear che
‘rinfresca’ lo screen del terminale.
Dopo aver eseguito il .logout il sistema esegue il file /etc/logout per le eventuali ultime
operazioni richieste dal sistema ed infine ripassa il comando al programma /etc/init
(lo stesso che era stato attivato al momento del login ) per finire la sessione in modo
standard.
Come gia’ accennato precedentemente, non e’ possibile il logout se ci sono
stopped process (il comando jobs fa una lista di tutti i process attivi e stopped). Tuttavia
se il comando logout viene ripetuto la seconda volta, la sessione finisce ed gli stopped
83*
processes vengono persi.

Come richiamare i comandi precedenti
Trattiamo qui quali sono le possibilita’ di history substitution in Unix.
Comandi di history substitution in Unix (I)
comando
history
!!
!n
!string
!?string?
!-n
significato
fa una lista degli ultimi comandi impartiti (history list)
esegue il comando precedente
esegue l’ n-esimo comando nella lista della storia dei comandi
esegue l’ultimo comando che incomincia con string
esegue l’ultimo comando che contiene string
esegue l’ n-esimo comando precedente
84*
history
1
18:30
ls -l -t
2
18:34
set ignoreeof
3
18:35
ls prova.f
4
18:36
more prova.f
5
18:40
vi prova.f
6
18:43
history
se ora l’utente impartisce da tastiera l’ordine
!!
ritornera’ ad eseguire il comando history che aveva precedentemente eseguito.
Se invece impartira’ il comando
!1
tornera’ ad eseguire
ls -l -t
Se invece battesse a terminale
!ls
avrebbe come effetto di ripetere il comando ls prova.f
Se battesse invece il comando
!?rov?
ritornerebbe ad eseguire il comando
vi prova.f
mentre se battesse
!-5
verrebbe eseguito ancora
set ignoreeof
85*
Negli esempi seguenti vengono elencati comandi di history substitution in cui vengono
invece richiamate words appartenenti a comandi precedenti
history
1
18:30 ls
file1
file2
file3
Nel comando precedente, ls e’ la word n. 0 , file1 e’ la word n. 1 etc.
Se ora l’utente impartisce da tastiera l’ordine
cat
!1:1
ottiene come effetto l’equivalente di cat file1 ovvero viene sostituita, al posto di !1:1 ,
la word 1 del comando n. 1 della history list. Se invece impartisce l’ordine
cat !1:*
ottiene
cat file1
file2
file3
(sostituzione di tutte le words da 1 in avanti del
comando n. 1); invece, con
cat !1:$
si ottiene
cat file3
(sostituzione dell’ultima word);
mentre con
cat !1:2-3
si ottiene
cat file2 file3 (sostituzione delle words da 2 a 3); infine con
cat !1:2-3 file10
si ottiene l’equivalente di cat file2 file3 file10 (espansione della linea
86* di
comando con nuovi argomenti).
Infine, supponendo di impartire il comando
cat file1
file2
file3
e susseguentemente
ls !*
si ottiene
ls file1 file2 file3
cioe’ la sostituzione di tutte le words > 0 del comando precedente.
87*
Gli esempi che ora seguono implicano la sostituzione di nuove words in comandi
precedenti.
sintassi :
^string1^string2
esempio :
cat file1
^cat^ls
ls file1
!n:s/string1/string2/
history
….
7 18:31 cat file1
….
!7:s/cat/ls/
ls file1
!n:p:s/string1/string2/
sintassi :
esempio :
sintassi :
esempio :
!!
!7:p:s/cat/ls
ls file1
!!
ls file1
sostituisce string2 a string1 nel comando
precedente
sostituisce string2 a string1 nel comando n
sostituisce string2 a string1 nel comando n
ma senza eseguire il comando risultante,
solo facendolo vedere comunque
aggiungendolo alla history list
esegui il comando precedentemente mostrato
88*

Help online ( comando man )
In Unix esiste il comando man per ottenere informazione su un comando, una
funzione, etc. L’output di questo comando ha in generale la forma (ma non per tutti i
comandi e’ uguale, ci possono essere piu’ o meno dei paragrafi qui elencati) :
NAME
SYNOPSIS
OPTIONS
OPERANDS
DESCRIPTION
SEE ALSO
EXAMPLES
BUGS
RESTRICTIONS
AUTHORS
nome del comando e suo proposito
sommario del suo uso
elenco delle possibili opzioni usabili con questo comando
elenco degli operandi su cui agisce il comando
descrizione in piu’ dettaglio del comando
altri luoghi nel manuale dove trovare informazioni relate
esempi d’uso del comando
descrizione di bachi conosciuti, deficienze e modi di aggiustarli
se sono disponibili
limitazioni che si conoscono
autori del codice del comando
Le pagine di man risiedono nelle directories da /usr/share/man/man1 a
/usr/share/man/man8 secondo la classificazione mostrata nella seguente tavola.
Ad es. la man page per il comando cat si trova in /usr/man/man1/cat.1.gz
89*
Tavola delle pagine di man
numero di pagina
1
2
3
4
5
6
7
8
contenuto
comandi della shell
funzioni di sistema (kernel access points)
librerie di subroutines
descrizione degli input/output device driver
include files e formats
computer games
special files
system procedures
Inoltre, le sezioni 1 e 3 sono suddivise come segue
1
comandi general purpose
1c
comandi relati alla comunicazione
1g
comandi relati alla grafica
1m
comandi di system maintenance
3
3f
3m
3r
3s
3x
libreria standard di subroutines
routines di supporto del FORTRAN 77
subroutines di matematica
librerie per internet network
subroutines di input/output
subroutines varie
90*
Ci sono 4 modi di usare man :
• sintassi
man comando
esempio
man cat
nell’esempio sopra riportato, il computer cerca le pagine di man che si riferiscono al
comando cat e l’output viene mandato a terminale
• sintassi
man -k keyword
esempio
man -k terminal
in questo esempio vengono listate tutte le informazioni relative alla parola chiave terminal.
Il comando man -k puo’ anche essere sostituito dal comando apropos
• sintassi
man -f comando
esempio
man -f more
questo comando produce una breve descrizione del comando more. Il comando man -f e’
equivalente al comando whatis
• sintassi
man sezione comando
esempio
man 3 stty
in quest’ultimo esempio l’utente sa gia’ in quale sezione di man si trova l’informazione
cercata e ne fa il display a terminale.
91*
Unix possiede numerosi comandi ed utilities per la creazione, modifica, il display di
files e directories.
La tabella che segue riassume i comandi e le routines chiamabili da
un programma scritto in Fortran 77 oppure da un programma scritto in C , per il file
management.
Sono sottolineati quei comandi di cui in particolare tratteremo, gli altri si
possono approfondire con le pagine di man .
Nella tabella vengono anche divisi i comandi che fanno un display di files o di loro
caratteristiche, da quelli che li manipolano.
L’utente novizio puo’ usare i primi in tutta sicurezza in quanto i files non vengono
modificati, mentre per quanto riguarda i secondi, si dovra’ prestare piu’ cura poiche’
il contenuto dei files potrebbe essere modificato.
92*
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Display commands
nome comando
o routine
cat
col
colcrt
fmt
fold
head
ls
more
od
pr
tail
significato
stampa allo standard output del contenuto di un file
filtra i reverse line feed
filtra nroff output per CRT (cathodic ray tube)
text formatter
spezza linee lunghe di un file in piu’ linee di larghezza prefissata
stampa le prime linee di un file
lista dei file esistenti e/o del contenuto di directories
stampa allo standard output del contenuto di un file, a pagine per volta
stampa allo standard output del contenuto di un file in ottale, decimale,
esadecimale od ASCII
stampa files allo stdout
stampa l’ultima parte di un file allo stdout
93*
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Manipulation commands riguardanti directories
nome comando
significato
cd
chdir
getdirentries
cambia la current directory
cambia la current directory - anche C callable routine
trova le directory entries con formato indipendente dal file system
C callable routine
getwd
trova il path name del current directory - C callable routine
mkdir
crea una nuova directory
pwd
stampa il path name della current directory
rmdir
rimuove una directory
scandir, alphasort
esamina una directory - C callable routine
unlink
rimuove una directory entry in una directory ; sia comando che
C callable routine
Manipulation commands riguardanti files (I)
ar
comando che opera su librerie
awk
pattern scanning and processing language
basename
isola la base di un filename
bcopy, bcmp, bzero, ffs
operazioni con stringe di bit o byte ; C callable routines
94*
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Manipulation commands riguardanti files (II)
nome comando
significato
checknr
controlla files prodotti da nroff e/o troff
chgrp
cambia il gruppo associato con un file o con una directory
chmod
cambia la protezione di un file o directory ; sia comando che C routine
cmp
confronta due files per scoprirne le differenze
comm
seleziona od elimina linee comuni a due files
cp
copia di un file o directory
creat
crea un nuovo file ; C callable routine
crypt
comando per incrittare o decriptare files
crypt, setkey, encrypt
operazioni per incrittare / decriptare
ctags
creazione di un tag file
dd
conversione e copia di un file
diff
confronto di 2 files ASCII
diff3
confronto di 3 files ASCII
expand, unexpand
sostituisce gli spazi con i tabs o viceversa
file
determina il tipo di file (ASCII, eseguibile, command file etc.)
find
trova files
flock
applica o rimuove un advisory lock su un file aperto ; C callable 95*
routine
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Manipulation commands riguardanti files (III)
nome comando
ftp
grep, egrep, fgrep
ident
link
ln
lockf
look
merge
mknod
mktemp
mv
ncheck
nroff
open
qsort
ranlib
significato
programma per trasferire files da un computer ad un altro
ricerca di un pattern in un file
identifica files
crea un link ad un file - C callable routine
crea links per files
crea un nuovo file ; C callable routine
trova linee che cominciano con una certa stringa di caratteri, in files
merge di files
crea special files ( character, block, fifo )
crea un file il cui nome sia unico - C callable routine
rinomina un file
elenca inode numbers e nomi di tutti i files in un file system
formatta del testo
apre un file per read o write ; C callable e Fortran callable routine
ordina una tabella ; C callable routine
converte archivi in random libraries veloci da consultare da parte
96* di un
linker
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Manipulation commands riguardanti files (IV)
nome comando
significato
rcp, scp
copia di files su una macchina remota
read
legge una linea di input da stdin
readv
legge input da stdin ; C callable routine
readlink
stampa il contenuto di un file symbolic link (a che punta il link)
rename
cambia nome ad un file; C callable routine
rev
scrive al contrario le linee di un file
size
scrive la grandezza di un object file
sort
ordina o fa il merge di files
split
spezza files in piu’ pezzi
stat, lstat, fstat
ottiene informazioni sullo stato di un file ; C callable routine
strncpy, strlen, undex, rindex
operazioni con le stringhe di bytes ; C callable routine
strings
conversione e copia di un file
sum
somma e conta i blocchi in un file
swab
fa lo scambio di bits ; C callable routine
symlink
crea crea symbolic links ad un file ; C callable routine
tar
tape archiver
tr
character translator
touch
crea un file vuoto od updata la data dell’ultima modifica di un file
97*
troff
formattamento di un testo
TABELLA DEI COMANDI O ROUTINES PER IL MANAGEMENT DI FILES
E DIRECTORIES
Manipulation commands riguardanti files (V)
nome comando
significato
truncate, ftruncate
tronca un file ad una lunghezza prefissata ; C callable routine
tsort
ordinamento topologico
umask
definisce le protezioni di default per i files creati
uniq
riporta e/o cancella le linee che si ripetono in un file
utime
assegna la data di accesso e di modifica ad un file ; C callable routine
utimes
assegna la data di accesso e di modifica ad un file ; C callable routine
wc
conteggio delle parole in un file
what
mostra che versioni di objects sono state usate per costruire un file
which
trova il file corrispondente ad un comando, incluso alias e path
98*

Elenco del contenuto di una directory ( ls )
Il comando ls viene usato per elencare files, directories e loro caratteristiche.
Sintassi
ls [-options] [arguments]
Negli esempi che seguono, supponiamo di essere in una directory che contiene 4 files :
myfile.txt , program.f , .login (hidden file) e tmp (una directory). Quest’ultima a sua
volta, contenga un file di nome test .
ls
myfile.txt program.f tmp
ls -a
.login myfile.txt program.f
ls -R
myfile.txt program.f tmp
tmp
tmp:
test
nell’ultimo esempio, la lista include non solo il contenuto della current directory (esclusi gli
hidden files) ma anche tutti i files di tutte le sottodirectories piu’ basse nella gerarchia delle
99*
directories.
ls -l
total 1
-rwxr-xr-x
1
user1
GR1
1024
24 Aug 13:40
myfile
-rwxrwx--x
1
user1
GR1
512
10 Jul 21:10 program.f
drwxr-xr-x
2
user1
GR1
30
12 Sep 04:10
tmp
il comando ls -l fa il long listing dando informazioni addizionali sul tipo di file (vedi dopo
la sezione sulle caratteristiche di un file)
ls *
questo comando fa la lista della current directory piu’ dei files contenuti nelle directories
UN livello piu’ in basso. In modo analogo, ls */* fa la lista dei files nella current directory
e nelle directories UNO e DUE livelli piu’ in basso.
ls -F
myfile.txt
program.f*
tmp/
questo comando indica anche il tipo di file : * e’ un file che ha la protezione x (puo’ essere
eseguito) , / indica che e’ una directory, @ significa un symbolic link mentre = significa
che e’ un socket .
ls -1
myfile.txt
program.f
100*
tmp
ls -C
questo comando forza il formato a multicolonne (che e’ comunque il default)
ls -t
questo comando elenca i files in ordine temporale tenendo conto della data di ultima
modifica ( i files piu’ recenti vengono elencati prima )
ls -r
elenca i files in ordine alfabetico inverso
ls -rt
elenca i files in ordine temporale inverso
Ordine seguito nel produrre le liste
A meno che non venga modificato da un’opzione, l’ordinamento dei files elencati e’ :
1)
files che cominciano con un punto
2)
files che cominciano con un numero
3)
le maiuscole
4)
le minuscole
Esempio :
101*
ls -a
.123 .Test .test 123 Prova prova

Combinazioni di piu’ opzioni
Le opzioni di ls possono essere combinate tra loro, ad es.
ls -a -l ( equivalente a ls -al ) produce una long list di tutti i files, anche gli hidden.

Caratteristiche dei files
Si consideri il seguente esempio :
ls -l
-rwxr--r-1
danny staff
1000
10 Aug 12:20 testfile
questo e’ un full listing delle caratteristiche, che ora esamineremo, del file testfile
1) Il primo carattere e’ la descrizione del tipo di file :
d
directory file
b
block-type special file
c
character-type special file
l
symbolic link
s
socket
file normale (ASCII o binario)
2) I 9 caratteri seguenti ( rwxr--r-- ) definiscono le protezioni del file per l’utente,
il gruppo, tutti gli altri. In Unix e’ sottinteso che il system manager abbia tutti i privilegi.
Protezione r significa possibilita’ di leggere il file, w di scrivere o cancellare,102*
x
di eseguire.
3) Il secondo campo nell’esempio, indica il numero di links che il file possiede ( 1 ) ; un file
ha sempre almeno 1 link alla directory alla quale appartiene ; una directory ha sempre
almeno 2 links, uno alla directory della quale e’ sottodirectory, un altro ai files contenuti
in essa. Altri links possono essere definiti col comando ln
4) il terzo campo e’ l’owner del file
5) il quarto campo e’ il gruppo al quale l’owner appartiene ( e di conseguenza anche il file )
6) segue poi la grandezza del file espressa in bytes
7) seguono quindi data di ultima modifica del file ( eventualmente data di creazione del file )
ed ora
8) nell’ultimo campo c’e’ il nome del file.
103*

Comando umask
Questo comando assegna il tipo di protezioni od accessi di default per la current shell,
per tutti i files creati susseguentemente.
Sintassi :
umask [opzione] [value]
Senza argomenti, mostra la file creation mask di default. Con l’argomento value la assegna.
Mask e’ data come valore ottale.
Bisogna tenere presente che la mask effettiva assegnata ad un nuovo file e’
mode & ~value
dove mode e’ una maschera aggiuntiva data dal sistema, di solito 666
umask
022
assegna accesso 666 & ~ 022 = 644
vale a dire r , w per user
e r access per group ed other ( tutti gli altri utenti ).
104*

Current directory, cambio di directory
Current directory
Il comando che mostra la current directory e’
pwd
pwd
/home/boca
Cambio di directory
Sintassi :
cd directory oppure
chdir directory
dove directory puo’ essere sia un relative directory path che un absolute directory path
pwd
/home/boca/dimostrazione
cd
../cestino
la nuova directory e’ /home/boca/cestino
cd
/home/boca
la nuova directory e’ /home/boca
cd
senza argomenti, indica la home directory. Dopo questo
comando, la directory e’ /home/boca
105*
La C-shell estende l’uso di cd
per mezzo della shell variable
cdpath ; infatti se
directory non e’ un sottodirettorio del current directory, e non incomincia per / , ./
oppure
../ , allora ciascun componente della shell variable cdpath
viene controllato
per vedere se ha come sottodirectory directory e se si’ tale sottodirectory diventa la
current directory.
Infine se anche questo fallisce, la C-shell controlla se directory non sia una shell variable il
cui nome incomincia per / , ed in tal caso fa diventare tale nome la current directory (se
esiste).
set cdpath = /usr/test
pwd
/programs/new
cd temp
pwd
/user/test/temp
set cdpath = (/usr/doc /user/com)
106*

Directory stack
E’ una lista di directories definito dalla C-shell solo per la sessione corrente.
La current directory e’ sempre in cima alla lista. L’utente puo’ costruire ed utilizzare il
directory stack coi comandi pushd , popd , dirs
Sintassi :
pushd directoryname
Azione
mette in cima al directory stack la directory directoryname e fa
:
diventare directoryname la current directory
Sintassi :
dirs
Azione
mostra il directory stack
:
Sintassi :
pushd +n
Azione
ruota lo stack n volte
:
Sintassi :
popd
Azione
elimina il current directory dalla cima della stack, lasciando invariati
:
gli altri ; fa diventare il prossimo directory dello stack il current
107*
directory
pwd
/user2/programs/new
pushd /usr
/usr /user2/programs/new
pwd
/usr
dirs
/usr /user2/programs/new
pushd /etc
/etc /usr /user2/programs/new
pushd +1
/usr /user2/programs/new /etc
pwd
/usr
popd
/user2/programs/new /etc
108*
Per ultimo si noti che il comando
cd ( o chdir ) ha l’effetto sul directory stack di
cambiare solo la directory in cima nel current directory, lasciando le altre directories della
lista invariate
dirs
/user2/programs/new
cd
/etc
/tmp
dirs
/tmp
/etc
109*

Creazione di directories
Sintassi :
mkdir [opzioni] directoryname
Azione
crea la nuova directory directoryname . Quest’ultimo puo’ essere sia un
:
pathname relativo ( alla current directory ) sia un pathname assoluto.
pwd
/user2/programs/new
mkdir tmp
pathname relativo
ls
/user2/programs/new/tmp
pwd
/user2/programs/new
mkdir /user2/programs/new/test
ls
/user2/programs/new/tmp
pathname assoluto
110*
/user2/programs/new/test

Rimozione di files e directories
Sintassi :
rm [opzioni] nomefile
Azione
rimuove nomefile ( dove quest’ultimo puo’ essere un pathname
:
assoluto o relativo )
-i -r
Opzioni :
l’opzione
-i
fa si’ che prima di rimuovere il file un messaggio appaia a terminale per
chiedere conferma di voler cancellare il file l’opzione -r rimuove una directory con
tutto il suo contenuto ( incluse eventuali altre directories con i loro contenuti )
ls
file1 file2 pippo prova tmp.f
rm
file1
rm -i p*
rm : remove pippo ?
rm : remove prova ?
In questo esempio l’uso dell’opzione i fa apparire il messaggio di conferma
111*
al quale l’utente deve rispondere con un yes o y

NOTA BENE 
Per poter rimuovere un file occorre che esso abbia la permission di tipo w (write e
delete permission). Inoltre se la directory contenente il file non ha write
access da parte dell’ owner allora compare il messaggio :
Permission denied
ed il
comando non viene eseguito.
ls -l
-r--r--r--
1
boca
GR1
189
May
18
22;56
prova.f
rm prova.f
rm : override protection 444 for prova.f ?
Il file prova.f ha permission di read only e quindi non viene cancellato. Il sistema
chiede esplicitamente all’utente se vuole rimuovere il file , lo user deve rispondere con yes
112*
o y per poter cancellare il file effettivamente.
ls -l
-r--r-xr-x
1
boca
GR1
189
May
18
22:56
prova.f
drwxr--r--
1
boca
GR1
512
May
19
13:14
cestino
rm -r cestino
Questo comando rimuove la directory cestino e tutto il suo contenuto
113*

Copia di files e directories
Sintassi :
cp [opzioni] file1
Azione
copia file1 su file2 . Se file2 esiste gia’, la vecchia versione viene
:
file2
sovrascritta
Opzioni :
-i -r
L’opzione -i fa si’ che qualora file2 esista gia’, venga richiesta all’utente conferma prima
di copiare. L’opzione -r serve per copiare directory intere ( con tutto il loro contenuto ).
ls -1
file1
file2
cp -i file1 file2
overwrite file2 ?
114*
ls -R
pippo
lista recursiva del contenuto della current directory
pluto
user1 user2
user1 e’ a sua volta una directory
./user1:
program.f
dati.dat
user2 e’ a sua volta una directory
./user2:
campo.FOR prog.c
cp -r user1 user2
copia la directory user1 in user2
ls -R
pippo
pluto
user1 user2
./user1:
program.f
dati.dat
./user2:
campo.FOR prog.c user1
./user2/user1:
program.f
dati.dat
in user2 c’e’ anche user1 con tutto il suo contenuto
115*

Cambiare nome ad un file
Sintassi :
mv [opzioni] file1 file2
Azione
muove files da una directory ad un’altra ovvero cambia nome a files e
:
directories
Opzioni :
-i
-f --
L’opzione -i , come gia’ visto per il comando cp , fa si’ che qualora file2 esista gia’, venga
richiesta all’utente conferma prima di sovrascriverlo.
L’opzione -f al contrario, forza la sovrascrittura di file2 qualora esista gia’, cancellando
l’effetto di un’eventuale opzione -i precedentamente definita ( con un alias ad es. )
L’opzione --
fa si’ che tutti gli argomenti del mv che seguono vengano interpretati
come filenames. Questo permette ai filenames di cominciare con un -
116*
ls
file1
file2
mv -i file1 file2
overwrite file2 ? y
ls
file2
ls
file1
file2
mv -- file1 -pinco
l’opzione -- permette di dare a file1 un nome che comincia
con -
ls
file2 -pinco
117*

Display di un file
I comandi piu’ usati per mostrare il contenuto di un file sono : cat , more ( o page ) ,
head , tail , pr , od
Comando cat
Sintassi :
cat [opzioni] filename(s)
Azione
stampa a terminale il contenuto del file filename(s) facendo
:
automaticamente lo scroll del terminale.
Opzioni :
-n
L’opzione -n fa il display del file numerando ciascuna linea in modo progressivo.
118*
Comando more ( o page )
I comandi more e page sono equivalenti.
Sintassi :
more [opzioni] filename(s)
Azioni
mostra il contenuto del file filename(s) una pagina alla volta, per
:
default sono 2 linee in meno (22) di quante ne puo’ mostrare il terminale
Opzioni :
tra le molte opzioni, citiamo solo -number che fa il display con number
linee, e +number che comincia il display a partire dalla linea number.
Questi comandi mostrano una pagina alla volta, indicano la percentuale di file gia’ mostrata
ed attendono il responso dell’utente. Battendo <cr> verra’ mostrata una linea in piu’,
mentre battendo la barra dello spazio, viene mostrata la nuova paginata.

NOTA BENE 
Questi comandi hanno alcune delle possibilita’ dell’editor vi , come ad es. la possibilita’ di
andare avanti con f e tornare indietro con b , quella di pattern matching etc.
assomigliando quindi molto ad un line editor read only. Per avere l’elenco completo di
119*
queste possibilita’ basta battere h dopo aver attivato il comando more .
Comando head
Sintassi :
head [opzioni] file(s)
Azione
fa il display della prima parte di file(s)
:
Opzioni :
-number
che fa il display delle prime number linee. Per default
vengono mostrate le prime 10 linee
Comando tail
Sintassi :
tail [opzioni] file(s)
Azione
fa il display dell’ultima parte di file(s)
:
Opzioni :
-number
che fa il display delle ultime number linee. Per default
vengono mostrate le ultime 10 linee
120*
cat
file
linea1
linea2
linea3
linea4
head
-3
file
|
tail
-1
linea3
121*
Comando pr
Sintassi :
pr [opzioni]
Azione
stampa un file allo standard output, con vari formattamenti. Se il file da
:
file(s)
stampare non viene specificato, o e’ un
- , il comando prende input
da standard input.
Opzioni :
citiamo solo le opzioni -number e -m
Senza opzioni, pr stampa file(s) a pagine di 66 linee ciascuna aggiungendo per ogni
pagina, nome del file stampato, data e numero di pagina, ed uno header ed un trailer di 5
righe vuote.
Con l’opzione -number file(s) viene stampato in number colonne.
Con l’opzione -m e nella forma
pr -m file1 file2 vengono stampati file1 e file2 uno
accanto all’altro ( utile per fare confronti di files ). E’ da notare che per default pr tronca
le linee troppo lunghe.
122*
Comando od
Sintassi :
od [opzioni] file(s)
Azione
stampa il contenuto ( dump ) a terminale di file(s) in formato ottale,
:
decimale, esadeciamale, ASCII
Opzioni :
dipendono da macchina a macchina, per OSF1 citiamo -o -O -a -h
-H -i
-I
L’opzione -o ( default ) stampa il file in short words ( parole da 16 bits ) stampando il
contenuto in ottale. L’opzione -O fa lo stesso, ma stampa il file in long words ( 32 bits ).
L’opzione -a stampa file(s) a bytes, e rappresentando ciascun byte col carattere ASCII
corrispondente. Le opzioni -h e -H stampano in esadecimale, il file suddiviso
rispettivamente in short e long words. Infine -i e -I stampano short e long words
interpretate come interi ( senza segno ).
123*
cat
file
line1
od -a
file
0000000
l
i
n
e
1
nl
0000006
od -o
la colonna piu’ a sinistra e’ un numero
ottale che esprime il numero di bytes
finora stampati
file
0000000
064554
062556
005061
0000006
od -h
0000006
file
696c
656e
0a31
124*

Cambio di protezione di files e directories
Come gia’ detto, ogni file e directory ha 3 tipi di protezioni od accessi ( r , w , x ) per 3 tipi
di utenti ( owner , group , all ) mentre il superuser ( system manager ) ha sempre tutti gli
accessi disponibili.
Il comando chmod permette
all’utente owner di un file o
directory di cambiare queste
protezioni , mentre umask
assegna le protezioni di default
per la current shell.
Sintassi :
chmod [opzioni] mode file(s)
Il livello di protezione (mode)
puo’ essere dato in 2 modi, in
forma assoluta od in forma
simbolica.
user
group
world ( other )
rwx
rwx
rwx
421
421
421
da cui
7 = 4+2+1
read, write , execute access
6 = 4+2
read, write
5 = 4+1
read, execute
4 = 4
read only
3 = 2+1
write , execute
2 = 2
write only
1 = 1
execute only
125*
ls -l
a.dat
-r-x------
1
chmod 755
a.dat
ls -l
boca
GR1
1954
May
3
18:31
a.dat
forma assoluta, codice ottale
a.dat
-rwxr-xr-x
1
chmod
u-w,g+w,o=r
ls -l
a.dat
-r-xrwxr--
1
chmod
a=rx
a.dat
ls -l
a.dat
-r-xr-xr-x
1
boca
GR1
1954
a.dat
May
3
18:31
a.dat
forma simbolica
boca
GR1
1954
May
3
18:31
a.dat
boca
GR1
1954
May
3
18:31
a.dat
126*

Cambio di proprieta’ di gruppo di files e directories
Il comando chgrp cambia la proprieta’ di gruppo ( lo user titolare del file rimane lo stesso)
di files e directories. Per applicare questo comando, chi lo fa deve essere il proprietario del
file e deve appartenere al gruppo che riceve la proprieta’ del file.
Sintassi :
chgrp [opzioni] newgroup
groups ;
admin
ls -lg
file
projecta
-rw-rw-r-chgrp
file
admin
-rw-rw-r--
2
system
file
2
;
system
projecta
ls -lg
1594
Feb 20 13:55
file
1594
Feb 20 13:55
file
file
admin
127*

Confronto tra files
In Unix si possono usare i comandi cmp e diff per stampare a terminale le differenze che
esistono tra due files.
Il comando cmp riporta solo la prima differenza trovata, e funziona anche con files non
ASCII. Il comando diff riporta tutte le differenze tra due ASCII files.
Sintassi :
cmp [opzioni] file1 file2
diff [opzioni] file1 file2
pr -m
file1
file2
Maine
Texas
Montana
Montana
Nebraska
Illinois
Illinois
Alabama
Iowa
Maine
cmp
file1
file1
file2
file2
differ:
char
1
line
1
128*
si considerino gli stessi files precedenti.
diff
file1
file2
1c1
<Maine
-->Texas
3d2
<Nebraska
5c4,5
<Iowa
---
>Alabama
>Maine
129*
Il significato delle linee di output e’ il seguente :
linea 1 : consiste di 3 campi
a) n. della linea o range dei n. delle linee nel primo file, prima del cambiamento
b) un carattere che descrive il tipo di cambiamento : a =append, c=change , d=delete
c) il n. della linea od il range dei n. delle linee dopo il cambiamento
linea 2 : le linea ( linee ) dal primo file, nel caso sia appropriato, identificate con <
linea 3 : se necessario, il delimitatore --- tra gli items del primo e del secondo file
linea 4 : se necessario, le linee del secondo file, identificate con >
Nell’ esempio quindi, il significato dell’output e’ : cambiare Maine in Texas in file1 , la
linea n. 1 rimane la linea n. 1. Cancellare la linea n. 3 ( Nebraska ) dal file1 cosi’ che
la linea 3 diventa la linea 2. Cambiare la linea 5 in file1 da Iowa in due nuove linee,
Alabama e Maine, cosi’ che la linea 5 diventa linea 4 e linea 5.
diff
-e
L’opzione
file1 file2
-e
produce in output i comandi da dare all’editor ed per far diventare
file1 identico a file2
130*
diff
-r dir1 dir2
L’opzione
-r permette confronti fra le directories dir1 e dir2 , riportando o
l’esistenza di un file in una sola delle directories o le differenze tra files che hanno lo
stesso nome ; questo tipo di confronto viene ripetuto per tutte le sottodirectories di dir1 e
dir2 .
131*

Ricerca di files
Si usa il comando
find
per cercare un file che si trova in una certa directory od in
una sua qualunque sottodirectory che si trovi piu’ in basso nella gerarchia delle directories.
ls -R visto in precedenza.
Questo comando offre piu’ funzionalita’ di
Con find si possono usare vari criteri per localizzare il file(s), si possono manipolare il file(s)
trovati oppure eseguire comandi se si e’ localizzato il file(s). Le ampie funzionalita’ di find
richiedono pero’ una sintassi piu’ complicata dei comandi fin qui visti ; tra l’altro le varie
opzioni devono venir date nel seguente ordine ( a differenza della maggioranza degli altri
comandi della C-shell )
Sintassi :
find
pathname
criterion
action
pathname : directory di partenza da cui iniziare la ricerca
criterion
:
criterio da usare nella ricerca del file(s) ad es. il nome del file(s)
action
:
quello che il sistema deve fare una volta trovato il file(s)
find
/
-name
ourfile
/user1/bin/ourfile
/user3/progs/ourfile
-print
132*
find / -name myfile -exec file {} \;
/user1/bin/myfile:
executable
/usr/local/myfile:
directory
/etc/myfile:
empty
/user3/myfile:
ascii text
/user4/data/myfile:
data
/user5/scripts/myfile:
commands text
trova a partire da / i files di nome myfile e per ognuno di essi esegue il comando file .
Si noti l’uso delle parentesi { } e di \; obbligatorio quando si usa l’opzione -exec .
find /user1 -mtime +45 -print
trova i files con modification time maggiore di
45 giorni e stampali a terminale. Da notare che qui modificato significa scritto.
find /user1 -name ‘*.f’ -atime -45 -print
.f
trova i files che terminano con
e che hanno access time ( cioe’ l’ultima volta che sono stati letti ) minore di 45 giorni.
find /usr -name ‘*.f’ \( -mtime -3 -o -atime -6 \) -exec rm {} \;
trova, a partire da /usr i files che terminano con .f scritti da meno di 3 giorni
133*
OPPURE ( OR logico, opzione -o ) letti da meno di 6 giorni, e cancellali ( -exec
rm {} )

Ricerca del contenuto di files
Il comando grep cerca una determinata stringa di caratteri in uno o piu’ files.
Sintassi :
grep [option(s)] pattern file(s)
cat file
George says :
hey, hello there, what a nice day!
And Ann answers : who cares ?
grep ‘hello there’ file
hey, hello there, what a nice day!
grep -i ‘HELLO there’ file*.txt
-i : ricerca case insensitive
file1.txt: hey, hello there, what a nice day!
file2 txt: hey, hello there, what a horrible day!
grep -n Goodbye file3
-n
: n. della linea(e) che ha la stringa cercata
12:Goodbye and have a nice day!
grep -c Goodbye file3
1
-c : n. di linee che hanno la stringa cercata
134*
grep -v hey file
-v : display delle linee che NON corrispondono
George says :
And Ann answers : who cares ?
grep -l hey fil*
-l : mostra solo il nome del file (1 volta sola) nel
quale una o piu’ corrispondenze sono state trovate
file
grep -e hello -e George
file
-e
: opzione che serve per cercare
uno o piu’ patterns
George says :
hey, hello there, what a nice day!
Per cercare uno o piu’ patterns e’
possibile usare l’opzione -f ed un file
di testo. In tal caso ciascuna linea del
testo diventa la stringa di caratteri con
cui fare il confronto.
cat match
hello
George
grep -f match file
George says :
135* day!
hey, hello there, what a nice
Con grep e’ possibile usare le cosiddette regular expressions che sono stringhe composte di
normali caratteri e metacaratteri, che sono un potente mezzo per specificare i patterns con
cui cercare in un file. Le regole per formare regular expressions sono molto articolate, si
possono trovare ad es. con
man grep ,
qui daremo solo un paio di esempi.
grep mode$ file
ricerca del pattern mode posto alla fine della linea
grep ^the
ricerca del pattern the posto all’inizio di una linea
file
ls -l | grep ^d
ricerca delle sottodirectories contenute nella
current directory
136*

Sort e merge di files
In Unix viene usato il comando sort per ordinare ( sorting ) alfabeticamente un file di testo
e/o per congiungere ( merging ) piu’ files in un unico file.
Sintassi :
sort [option(s)] [+pos1] [-pos2]
file(s)
cat file1
aaaaa
123
Abbb
zzzzzz
sort file1
sorting nello stesso ordine usato da ls
123
l’output e’ lo standard output
Abbb
aaaaa
zzzzzz
137*
cat file2
Boca
gianluigi
sort file1 file2
ordina file1 e file2, considerandoli come un unico file,
123
e produce un unico output ( merging ) che va a stdout
Abbb
Boca
aaaaa
gianluigi
zzzzzz
138*
sort -o out file1
output va al file out (uguale a sort file1 > out )
sort -f file1 file2
non fa distinzione tra maiuscole e minuscole
123
al momento del sorting
aaaaa
Abbb
Boca
gianluigi
zzzzzz
cat prova
sedd 123 456 abc
ase 19 25 cccc xdrf
aaa 343 20 arrt eee
sort -k 4,6 prova
sedd 123 456 abc
sceglie il sort key field il quarto campo e, nel
caso di uguaglianza, il 5o ed il 6o. Se sono ancora uguali, si cons
aaa 343 20 arrt eee
tutta la riga. I campi vengono definiti dal delimitatore di
ase 19 25 cccc xdrf
default che e’ il blank ; un campo (in assenza dell’opzione
139*
-t ) e’ definito come una sequenza massimale di non-blanks piu’ tutti i blanks che precedon
sort -k 2n,2n prova
il sort key field e’ il secondo campo, e’
ase 19 25 cccc xdrf
numerico e l’ordinamento considera l’intero
sedd 123 456 abc
numero che c’e’ nella sort key ( opzione n )
aaa 343 20 arrt eee
cat prova
sedd:123:456:abc
ase:19:25:cccc:xdrf
aaa:343:20:arrt:eee
sort -t: -k 2n,2n prova
come il sort precedente, ma i campi ora
ase:19:25:cccc:xdrf
sono delimitati da : (opzione -t ); inoltre
sedd:123:456:abc
con questa opzione ogni delimitatore diventa
aaa:343:20:arrt:eee
significativo nel senso che due delimitatori
consecutivi definiscono un campo vuoto.
140*
cat prova
sedd:123:456:abc
sedd:123:46:abc
ase:19:25:cccc:xdrf
aaa:343:20:arrt:eee
sort -t: -k 2n,2n -k 3n,3n prova
esempio di multifield sort key.
ase:19:25:cccc:xdrf
Prima il confronto avviene con il sort key field
sedd:123:46:abc
n. 2, in caso di uguaglianza si passa al prossimo
sedd:123:456:abc
sort key field, che e’ il n. 3 ; entrambi sono
aaa:343:20:arrt:eee
numerici. Il delimitatore e’ :
sort -t: +1n -3
esempio di sort field dato con + -
prova
ase:19:25:cccc:xdrf
Il confronto avviene con il sort key field n. 1 numerico (1n)
sedd:123:46:abc
e termina col campo 2 (che viene prima del campo 3). Si
sedd:123:456:abc
noti che con questa opzione i campi si contano 141*
a partire da
aaa:343:20:arrt:eee
0.

Creazione od updating di un file : comando touch
Il comando touch aggiorna la modification date di un file ( data dell’ultima volta in cui il
file fu scritto ) se esiste gia’, oppure crea un file vuoto se esso non esisteva ancora.
Sintassi :
ls -l
touch [option(s)] file
a.out
-rwxr-xr-x
1
boca
GR1
24576
May
2
17:29
a.out
19:01
a.out
142*
ultima modification time
touch a.out
ls -l
a.out
-rwxr-xr-x
1
boca
GR1
24576
May
25
nuova modification time
ls
a.out
b.out
prova.f
touch pippo
;
ls
a.out
b.out
pippo
b.out
prova.f
prova.f
crea il file ( vuoto ) pippo
ls
a.out
touch -c pippo
a.out
b.out
;
ls
prova.f
l’opzione -c impedisce la creazione del file
pippo
143*

Character translator
Il comando tr
copia caratteri dallo stdin allo stdout con sostituzione o cancellazione dei
caratteri selezionati dall’utente.
Sintassi :
tr [option(s)]
char1 char2
char1 e’ il carattere che viene sostituito con char2
tr A a < file1 > file2
trasforma tutte le A maiuscole presenti in file1 in a minuscole, e mette l’output
in file2.
tr A-Z a-z < file1 > file2
trasforma tutte le maiuscole presenti in file1 in minuscole, e mette l’output in file2.
tr -d A < file1 > file2
cancella tutte le A maiuscole presenti in file1 e mette l’output in file2.
144*
Word counting

Il comando wc conta il numero di linee, parole, caratteri ( o bytes ) presenti in uno o piu’
file di testo ASCII e li scrive allo stdout. Nel caso di piu’ files in input ne stampa anche il
totale.
wc [option(s)] file(s)
Sintassi :
cat testo
sedd 123 456 abc
ase 19 25 accc xdrf
aaa 343 20 arrt eee
wc testo
3
14
57
testo
12
21
189
prova.f
4
7
47
prova1.f
wc prov*
16
28
236
total
145*

Link tra files
Un link e’ un nome diverso dato ad un file gia’ esistente. Un link non e’ una copia
separata dello stesso file, ma solo una directory entry in piu’ che conduce allo stesso file.
Dato che un file puo’ avere multipli links, puo’ succedere che users diversi leggano o
scrivano contemporaneamente lo stesso file e si possono percio’ avere problemi di
corruzione di files.
Ci sono due tipi di links : un hard link ( default ) ed uno soft o symbolic link. Lo hard link
crea una nuova directory entry per il medesimo file ( senza duplicarlo fisicamente ) cosi’ che
lo stesso file fisico e’ accessibile con due ( o piu’ ) nomi diversi. Se l’utente cancellasse il file
originario ( nome vecchio ) il file sarebbe accessibile allo stesso modo col nome nuovo e
finche’ anche il nome nuovo non e’ cancellato, il file non scompare dalla memoria.
Quando l’utente crea uno hard link il link count aumenta di uno, ma l’ inode del file e’
identico a quello vecchio. Uno hard link non puo’ abbracciare filesystems diversi.146*
Un symbolic link invece e’ solo un file che contiene il path per il file originale. Se il file
originario fosse cancellato, il link continuerebbe ad esistere, ma non ci sarebbe piu’ modo di
accedere all’informazione del file originario. Un link simbolico non incrementa il link count.
Un link simbolico puo’ abbracciare filesystems diversi.
147*
Sintassi :
ln [option(s)] name1 name2
dove name1 e’ il nome del file che esiste gia’ mentre name2 e’ il nome del nuovo file, link
del vecchio.
ls -li
1035465 -rw rw r--
1
system
2046
ln file1.dat foo
Feb 25 13:58
file1.dat
hard link
ls -il
1035465 -rw rw r--
2
system
2046
Feb 25 13:58
file1.dat
1035465 -rw rw r--
2
system
2046
Feb 25 13:58
foo
1
system
2046
Feb 25 13:58
file
ls -li
1035465 -rw rw r-ln -s file
foo
link simbolico
ls -il
1035465 -rw rw r--
1
system
2046
Feb 25 13:58
file
1024567 lrw rw r--
1
system
2046
Feb 25 13:58
foo 148*
-> file
Questo capitolo tratta di quei comandi che permettono di :
monitorare gli users ed i loro process
whoami
users (u)
who
w
rwho
ps
top
du
limit
displays the users’s name
monitorare il sistema
displays virtual memory statistics
displays statistics on free disk space
vmstat
df
displays a list of users who are on the system
identifies users currently logged in
modifica dei process
summary of current system activities
shows users logged in to hosts on the local network
kill
send a signal to a process
shows current process status
at
runs commands at a later time
crontab
display and update information
nice
submits a schedule of
about the top cpu processes
renice
commands to cron
displays a summary of disk usage
lists the system resources available to user lowers priority to a process to be executed 149*
or reduces resources limits of a process
alters priority to running processes
7.1 Monitorare gli users ed i loro process
Esaminiamo ora quei comandi che permettono di sapere quanti e quali utenti sono
collegati al sistema, quali process hanno ‘lanciato’, quanto spazio su disco e’ ancora
disponibile, quali sono i limiti di utilizzo delle risorse del computer imposti ad un certo
utente.
Comando whoami
Sintassi :
whoami
Azione
mostra lo username associato
:
con la sessione corrente.
Serve per esempio quando si utilizzano piu’ sessioni contemporaneamente se ci si
dimentica con quale username abbiamo aperto la sessione.
150*
Comandi users ( u ), who, w e rwho
Questi comandi forniscono informazioni, via via con maggiore dettaglio, sugli utenti
correntemente collegati in modo interattivo.
Sintassi :
users (oppure u )
Azione
stampa a terminale l’elenco alfabetico degli usernames degli utenti
:
interattivi che sono correntemente collegati
usernames degli utenti correntemente collegati in interattivo
151*
Sintassi :
who
Azione
stampa a terminale l’elenco degli usernames degli utenti
:
interattivi che sono correntemente collegati, il nome del device al
quale il terminale dell’utente e’ collegato, e l’ora del login.
device
username
login time
152*
Sintassi :
w [option(s)] [username]
Azione
stampa a terminale una linea di header con l’ora corrente, da quanto
:
tempo il computer e’ attivo, il numero di utenti, ed il load average, vale a dire il numero
di jobs nella run queue negli ultimi 5 secondi, 30 secondi o 60 secondi. Di ciascun utente
(se username manca) od eventualmente solo dell’utente username viene mostrato :
username, device, da quale computer e’ stato fatto il login, ora del login, da quanto tempo
l’utente e’ rimasto idle, il CPU time accumulato da tutti i process dell’utente dal momento
del login (JCPU) in minuti, il CPU time (in minuti) usato da(i) process(es) attivi
correntemente (PCPU), il nome del programma eseguito dal current process.
153*
Sintassi :
w [option(s)] [username]
Azione
stampa a terminale una linea di header con l’ora corrente, da quanto
:
tempo il computer e’ attivo, il numero di utenti, ed il load average, vale a dire il numero
di jobs nella run queue negli ultimi 5 secondi, 30 secondi o 60 secondi. Di ciascun utente
(se username manca) od eventualmente solo dell’utente username viene mostrato :
username, device, da quale computer e’ stato fatto il login, ora del login, da quanto tempo
l’utente e’ rimasto idle, il CPU time accumulato da tutti i process dell’utente dal momento
del login (JCPU) in minuti, il CPU time (in minuti) usato da(i) process(es) attivi
correntemente (PCPU), il nome del programma eseguito dal current process.
154*
Sintassi :
rwho [-a] [username]
Azione
comando che fornisce informazioni analogomente al comando who,
:
ma anche per users collegati su computers remoti facenti parte del
network locale. Se username viene specificato, solo su di esso
vengono date informazioni
Opzioni :
-a
per elencare tutti gli utenti sui computer remoti; altrimenti
sono segnalati solo quelli che hanno toccato la tastiera nell’ultima ora.
username
hostname
device
login time
idle time (in minuti)
155*
Comando ps
Questo comando (process status) mostra le risorse del sistema che vengono ‘consumate’
da uno o piu’ process.
Sintassi :
ps [option(s)]
Azione
stampa a terminale un elenco di risorse usate da uno o piu’ process
:
Opzioni :
ci sono molte opzioni, molte sono machine-dependent; qui di seguito
sono esemplificate le principali, valide per Linux. Per maggior dettagli : man ps
comando impartito
process ID number
terminale da cui e’
stato lanciato il
process
CPU time usato
dal process
156*
Sintassi :
ps -l
Azione
come ps ma con maggiori dettagli (long list)
:
status of process : R = running ; S = sleeping ; D = uninterruptible sleep (IO queues)
Z = zombie (stoppato in modo non appropriato dal parent process) ;
T = stopped ; W = swapped out ; C = negative nice values ; N = positive nice values
user ID number
parent process ID number
% CPU used
address of the name of the kernel function
the task currently is sleeping in
priorità (valori piu’ alti = minore priorita’)
nice value = process scheduling increment;
(valori piu’ alti = minore priorita’)
157*
Sintassi :
ps -f
Azione
come ps ma con maggiori dettagli (full list)
:
start time of the process
158*
Sintassi :
ps -v
Azione
come ps ma con maggiori dettagli; mostra lo stato della memoria
:
virtuale
percentage of physical memory used by the job
status of process
total amount of physical memory used by the task in Kbytes
159*
Sintassi :
ps -u username
Azione
mostra informazioni su tutti i process appartenenti a username,
:
anche quelli che non sono stati lanciati dalla sessione corrente.
job lanciato non dalla sessione corrente
e non ‘attaccato’ ad alcun terminale
job lanciato dalla sessione corrente ed
attaccato al suo terminale
160*
Sintassi :
ps -e
Azione
mostra informazioni su tutti i process presenti sul computer
:
con anche
opzione f
161*
Riassunto delle opzioni disponibil i con ps su Linux
162*
Comando top
Questo comando mostra l’attivita’ del processore in real time. Mostra una lista dei jobs
maggiormente CPU-intensive del sistema e fornisce un’interfaccia interattiva per
manipolare i process.
Sintassi :
top [option(s)]
Azione
produce una schermata che viene rinfrescata di default ogni 5 secondi
:
con informazioni sui process maggiormente CPU-intensive.
Opzioni : [-d delay
specifica che il display venga rinfrescato ogni delay
secondi
[-p ID
viene mostrato solo il process con ID number ID
[-q viene rinfrescato il display il piu’ velocemente possibile
[-n num
viene rifrescato il display num volte e poi top finisce.
163*
% CPU usata dagli utenti
numero e tipo di jobs
% CPU usata dal sistema
% jobs con NICE
negativa
% jobs idle
stato memoria
del sistema
stato swap
space
size of the job
code + data
+ stack,
in Kbytes
total physical
memory
used by job,
in Kbytes
total shared memory
status, < for processes with negative
nice, W for swapped processes (doesn’t
work correctly for kernel processes)
164*
Comando du
Sintassi :
Azione
:
du [option(s)] [file(s)] [directory(ies)]
segnala quanto spazio su disco e’ occupato dai files o directories
specificate (in unita’ di 1024 bytes  1 Kbyte) e per ciascuna
subdirectory.
Opzioni :
-a
se l’argomento e’ una directory mostra lo spazio occupato da
ciascun file, non solo dalla directory
-s summary, fa vedere lo spazio occupato in totale da ciascun
argomento.
165*
equivalente a
du .
dimensioni in Kbytes
directory
166*
Comando limit
Sintassi :
Azione
:
limit [resource] [value]
e’ un commando built-in nella C shell. Elenca le risorse di sistema
disponibili ai process di un utente. Si puo’ usare questo comando per diminuire
(non per aumentare !) i valori assegnati, specificando resource e value.
maximum CPU time assigned
maximum size in Kbytes of any one file
maximum size in Kbytes
of the core dump file
amount of maximum memory
(in Kbytes) a user can consume
maximum processes at the same time
maximum number open files at the same time
167*
pone a zero la massima grandezza
possibile del file core (cioe’ in
pratica impedisce la creazione di core ).
168*
7.2 Monitorare il sistema
Esaminiamo ora dei comandi che permettono di sapere come l’insieme di tutti gli utenti
usa le risorse di memoria virtuale e di memoria su disco ( comandi vmstat e df ).
Comando vmstat
Sintassi :
vmstat [option(s)] [delay [count]]
Azione
mostra la statistica della memoria virtuale del sistema, fornendo
:
anche informazioni sui process, su paging, block IO, traps ed attivita’
della CPU. Il primo output del comando fa una media a partire
dall’ultimo reboot del sistema, successivamente, se delay e’ stato
specificato, le varie quantita’ vengono calcolate ogni delay secondi,
per count volte. Se delay e’ stato specificato ma count no, il
display viene fatto fino ad interruzione del comando con <ctrlC>.
Opzioni :
-n lo header dell’output del comando viene fatto vedere una volta sola.
169*
process status
r : n. waiting for run time
b : n. in uninterruptible sleep
w : n. runnable but swapped out
memory (in Kb)
virtual memory used
free memory
memory used as buffers
amount of cache
170*
swap space
si : memory swapped in
from disk (Kb/s)
so : memory swapped out
to disk (Kb/s)
ogni 10 secondi, per 5 volte
system
in : n. interrupts per sec.
cs : number of context switch per sec.
us : % user CPU time
sy : % system CPU time
I/O
bi : blocks sent to a block device (blocks/s)
bo : blocks received from a block device (blocks/s)
171*
Comando df
Sintassi :
df [options] [file(s),directory(ies)]
Azione
mostra lo spazio su disco usato e disponibile. Senza argomenti, mostra la
:
quantita’ di spazio per tutti i file systems montati sulla macchina. Con
argomento file(s) o directory(ies) lista lo spazio disponibile ed
usato del filesystem al quale il file o la directory appartiene.
Opzioni :
-a
all, lista anche i filesystems che hanno dimensione 0
--block-size=SIZE usa come unita’ di misura blocchi da SIZE-byte
-k usa come unita’ di misura blocchi da 1024 bytes
-i
lista l’informazione sugli inodes al posto della dimensioni in blocchi.
172*
filesystems
spazio totale
disponibile in Kb
spazio
usato
(Kb)
spazio
disponibile
(Kb)
% spazio
usato
mount point
viene mostrato lo spazio su disco disponibile
ed usato del filesystem al quale la directory
/home/boca appartiene
173*
7.3 Modifica dei process
Unix possiede 5 comandi usati comunemente per modificare i process degli utenti :
kill , per terminare un process; at , per far partire un process piu’ tardi; crontab ,
per schedulare la partenza periodica di jobs, nice per modificare la priorita’ che il
systema assegna di default ad un process che parte; renice per modificare la priorita’
di un process gia’ lanciato e limit , che abbiamo gia’ visto, per ridurre le risorse
disponibili ad un process.
Comando kill
Sintassi :
kill [options] [-s signal] [PID] [%jobnumber]
Azione
comando built-in nella C shell. Manda il signal specificato al process
:
specificato da PID o da %jobnumber .
Opzioni :
segnalo l’opzione -9 per far terminare certamente un process.
174*
jobnumber
process identification
number (PID)
opzione -9 per eliminare
certamente il process
175*
Comando at
Sintassi :
at [options] time
command
...
command
<ctrlD>
Azione
:
esegue uno o piu’ comandi all’istante specificato da time . La lista dei
comandi da eseguire deve essere messa nelle linee che seguono
at [options] time e deve essere terminata da un <ctrlD>.
L’eventuale output dei comandi che normalmente verrebbe mandato a
stdout , viene invece spedito per mail all’utente. La data puo’ essere
specificata (in LINUX) in vari modi, vedi man at per la lista completa
delle possibilita’. Nel seguito vengono mostrati solo alcuni esempi.
176*
ora alla quale
il comando
verra’ eseguito
177*
data alla quale
il comando
verra’ eseguito
178*
comando da eseguire
179*
il <ctrl>D finale
per segnalare
che l’input di at
e’ finito
180*
ora alla quale il comando
verra’ eseguito, in questo
caso alle 16:00 (altri modi
ammessi sono : noon , midnight )
181*
Comando crontab
Sintassi :
crontab [options]
Azione
questo comando edita, lista o rimuove la tabella usata da cron, che e’
:
un programma daemon che permette di far partire programmi o
comandi in maniera automatica e periodica. Come at fa partire jobs
automaticamente, tuttavia li fa partire periodicamente, ad una data ora
di determinati giorni di determinati mesi dell’anno. Il programma cron
legge la tabella nella quale sono elencati i jobs da far partire, ad ogni
quanto tempo.
Opzioni :
-l
mostra la tabella usata da cron
-e edita la tabella usata da cron con l’editor di default
-r cancella la tabella usata da cron
182*
opzione -l : lista la tabella usata da cron
il giorno del mese (da 1 a 31)
in cui deve partire il job

il minuto (da 0 a 59)
in cui deve partire il job
l’ora (da 0 a 23) in cui
deve partire il job
NOTA BENE 
valori accettati nei campi numerici :
- un intero
- una lista di interi separati da virgole
- due interi separati da - per indicare
un range
- un * per indicare tutti i valori
possibili
183*
il mese dell’anno (da 1 a 12)
in cui deve partire il job
(* = ogni mese)

NOTA BENE 
si possono specificare i giorni in
cui far partire il job in due campi
(giorno del mese e giorno della
settimana). Si possono usare sia
entrambi i campi, che un campo solo.
Se si usa solo un campo, l’altro deve
avere l’asterisco.
nome del job da far partire
il giorno della settimana
in cui deve partire il job
(* = ogni giorno)
184*
Comandi nice e renice
Sintassi :
nice number [command]
Azione
questo comando fa partire il nuovo job command con scheduling
:
priority modificata aggiungendo number alla priorita’ normalmente
assegnata di default dal sistema. La priorita’ aggiuntiva va da -20 (il
job viene eseguito piu’ in fretta) a 19 (esecuzione piu’ lenta).
Tuttavia solo il superuser puo’ assegnare un nice negativo.
Opzioni :
-ADJUST priorita’ aggiuntiva; il normale utente puo’ usare solo un
valore positivo.
Sintassi :
renice number [PID] [-g [pgrp]] [-u [user] ]
Azione
altera la scheduling priority di uno o piu’ jobs che runnano. Per la
:
priority vale lo stesso discorso fatto per nice. Specificando PID si altera
il nice di un job, specificando -g pgrp si alterano le priorita’ di tutti
i process di quel gruppo, specificando -u user si alterano tutti
quelli di quell’utente.
185*
fa partire il job in normalmente e lo mette in background
Process ID number
priorita’ del job
fa partire il job con nice positiva e lo mette in background
Process ID number
186*
priorita’ del job
nice del job
modifica il nice del job 974 che gia’ runna
187*
Questo capitolo tratta della programmazione mediante comandi di shell, raggruppati in
in costrutti in un file chiamato shell script . Discuteremo solo la sintassi della C (tcsh) shell.
188*
8.1 Esecuzione di un shell script
E’ sufficiente scrivere a terminale il nome dello script. Se tale nome e’ dato in forma
relativa, la C shell usera’ la variabile di shell path per sapere in quali directories cercare
lo script. Lo script dovra’ avere la protezione x on per poter essere eseguibile.
directories nelle quali viene cercato lo script
unica eccezione : NON e’ una
Come tutti i comandi che non sono built-in
linea di commento ma la
nella shell, lo script viene eseguito da un
dichiarazione che il testo che
child process con un forking al momento
segue deve essere interpretato dal
dell’esecuzione del comando. Il child process
programma /bin/tcsh (la tc shell)
eredita tutte le variabili di shell definite per il #!/bin/tcsh -f
parent process. In piu’ per esso viene eseguito #questa e’ una linea di commento
exit
il file .cshrc (e .tcshrc) e quindi eredita tutte
il # serve per commentare
le definizioni ivi contenute. Quest’ultima
189*
cosa viene evitata con l’opzione -f (fast start) e far partire lo script piu’ velocemente
8.2 Variabili di shell
Sono gia’ state definite le variabili di shell precedentemente ed e’ gia’ stato detto che ad
esse si possono assegnare valori tramite il comando set. Riassumiamo qui alcuni concetti:
le variabili di shell sono valide solo per il process per il quale vengono assegnate
e per tutta la durata di quest’ultimo. Vengono perse quando si cambia shell.
ad una variabile di shell si possono assegnare sia numeri che caratteri
il contenuto di una variabile di shell si ottiene facendo precedere il nome della
variabile dal metacarattere $
valore numerico
ci si e’ dimenticati del $ !!
valore alfanumerico
190*
Variabili di shell preassegnate
il comando set senza argomenti
ci da’ la lista delle variabili di
shell preassegnate e di quelle
definite dall’utente
nome della variabile di shell
contenuto della
variabile di shell
191*
Forme speciali di una variabili di shell
La tavola qui sotto riporta le forme speciali che puo’ assumere una variabile di shell che,
tra l’altro, puo’ contenere piu’ valori, come un vettore. In questo caso (a differenza del
C) gli elementi del vettore vengono contati a partire da 1.
Tavola
0 se la variabile name non e’ definita, 1 se e’ definita
numero di elementi della variabile name
da’ l’elemento m -esimo della variabile
da’ gli elementi da m a n compresi della variabile name
da’ gli elementi da m (compreso) fino all’ultimo della variabile
name
$name[-m]
da’ gli elementi dal primo fino al m-esimo compresi
della variabile name
$name[*]
da’ tutti gli elementi della variabile name
$name[$#name] l’ultimo elemento della variabile name
$?name
$#name
$name[m]
$name[m-n]
$name[m-]
192*
Forme speciali di una variabili di shell
assegnazione di 8 valori
alla variabile di shell var
che cosi’ diventa un vettore.
Si notino le ( ) , obbligatorie.
la variabile var e’ stata definita
la variabile var e’ un array di 8 valori
dal secondo al sesto valore
della variabile var
dal terzo all’ultimo valore della variabile var
tutti i valori della variabile var
ultimo valore contenuto nella variabile var
193*
Comando shift
Shift opera sulle variabili di shell riducendone il
numero di elementi di uno, scartandone ogni
volta il primo elemento.
Sintassi
:
shift variable
#!/bin/tcsh
set z = ( uno due 3 )
echo “Before using shift there are $#z elements :$z”
while ($#z>0)
echo $z[1]
shift z
end
echo “After using shift there are $#z elements”
exit
194*
Passare variabili ad uno script
Nella tavola qui sotto vengono indicate i nomi della varibili che possono essere passate al
runtime, piu’ altre utili variabili di shell. Negli esempi ne viene illustrato un possibile uso.
Tavola
$n o $argv[n]
$*
da’ il valore della n-esima variabile passata allo script
da’ il valore di tutte le variabili passate allo script
$$
$<
$0
$?0
da’ il process number (PID) della shell corrente
accetta input dal terminale
variabile contenente il nome dello script che viene eseguito
da’ 0 se il nome dello script che viene eseguito e’ conosciuto,
1 altrimenti
195*
Passare variabili ad uno script
continuazione del
#!/bin/tcsh
commento alla
# returns variable passed \
prossima riga
to script
echo $argv[1]
echo $2
echo $argv[$#argv]
echo -n “Enter Text String:”
set name = $<
echo “This script is called $0”
argomenti passati
echo “This script is being processed by PID $$”
a test_script3
echo “The string entered has $#name elements”
echo “The first word is $name[1]”
echo “The last word is $name[$#name]”
exit
input dato da terminale
si notino le parentesi tonde,
obbligatorie per poter far
diventare name un vettore
196*
8.3 Filename modifiers
I filename modifiers fanno si che il sistema ritorni porzioni di un filename relativo od
assoluto, come esemplificato dalla tabella qui sotto, e dallo script test_script4.
Tavola
:r
:e
:h
:t
da’ la parte del filename che precede
il . , se non contiene il . , ritorna il
nome completo
da’ la parte del filename che segue
il . , se non contiene il . , da’ NULL
da’ la prima parte del nome assoluto
del file (head) quella formata dalle
directories.
da’ l’ultima parte del nome assoluto
del file (tail) cioe’ il nome vero e
proprio del file.
#!/bin/tcsh
echo -n “Enter filename”
set filename = $<
echo $filename:r
echo $filename:e
echo $filename:h
echo $filename:t
exit
197*
8.4 Variable expansion
Si e’ gia’ visto precedentemente la funzione dei 3 tipi di quotes usati in Unix : ’ ’ single
(forward ) quotes, “” double quotes, `` single backward quotes o backticks.
Viene qui riassunto il loro comportamento con le variabili di shell :
le ’ ’ prevengono ogni tipo di variable expansion la variabile ritorna cosi’
com’e’ scritta
le “” raggruppano tutti i caratteri contenuti in esse in un’unica word, permette
la variable expansion ma NON il globbing della wildcard ( * ).
le `` causano l’immediata esecuzione del comando corrispondente, ed il suo
198*
(eventuale) stdout viene sostituito al posto delle ``.
le “” impediscono il globbing
dello *, quindi il valore dato a
name e’ ls test*
> set name = ls test*
> echo $name
ls test_script2 test_script3 test_script4
> echo '$name'
e’ come se scrivessi echo ls test* (cioe’
$name
al posto di $name viene messo il suo
> echo “$name”
valore) e quindi ora c’e’ globbing dello *
ls test*
> echo `$name`
test_script2 test_script3 test_script4
le ’ ’ prevengono ogni tipo di variable expansion la variabile ritorna cosi’
com’e’ scritta
le “” raggruppano tutti i caratteri contenuti in esse in un’unica word, permette
la variable expansion ma NON il globbing della wildcard ( * ).
le `` causano l’immediata esecuzione del comando corrispondente, ed il suo
199*
(eventuale) stdout viene sostituito al posto delle ``.
> set name = ls test*
> echo $name
ls test_script2 test_script3 test_script4
> echo '$name'
le ‘’ impediscono la variable
$name
sostitution
> echo “$name”
ls test*
le “” permettono la
variable sostitution
> echo `$name`
test_script2 test_script3 test_script4 ma poi impediscono
il globbing dello *
le ’ ’ prevengono ogni tipo di variable expansion la variabile ritorna cosi’
com’e’ scritta
le “” raggruppano tutti i caratteri contenuti in esse in un’unica word, permette
la variable expansion ma NON il globbing della wildcard ( * ).
le `` causano l’immediata esecuzione del comando corrispondente, ed il suo
200*
(eventuale) stdout viene sostituito al posto delle ``.
> set name = ls test*
> echo $name
ls test_script2 test_script3 test_script4
> echo '$name'
i backtics `` interpretano il
$name
comando racchiuso tra di
> echo “$name”
essi, lo eseguono e sostituiscono
al loro posto un eventuale output
ls test*
mandato a stdout .
> echo `$name`
test_script2 test_script3 test_script4
le ’ ’ prevengono ogni tipo di variable expansion la variabile ritorna cosi’
com’e’ scritta
le “” raggruppano tutti i caratteri contenuti in esse in un’unica word, permette
la variable expansion ma NON il globbing della wildcard ( * ).
le `` causano l’immediata esecuzione del comando corrispondente, ed il suo
201*
(eventuale) stdout viene sostituito al posto delle ``.
8.5 Operatori di comparazione
Gli operatori di comparazione servono nei costrutti di flow control che vedremo in
seguito, come if, while etc. e sono elencati nella tabella. Negli esempi invece, viene
usato il costrutto if completo solo per il primo esempio, negli altri il costrutto corretto
e’ sottinteso.
Tavola
=
==
!
!=
&&
||
>
<
>=
<=
assign value to variable
equal to
Boolean NOT
NOT equal to
Boolean AND
Boolean OR
greater than
less than
greater or equal to
less or equal to
si noti la negazione
dell’operatore logico
che sta in parentesi
# assignment
set string = pippo
# equal to
if( $i == 10 ) then
echo “numero uguale a 10 “
endif
if( $string == pippo ) then
# not equal to
if( $i != 2 ) then
if( $string != pippo) then
# greater than 1 and less than 10
if( $i > 1 && $i < 10 ) then
# equal to 0 or 1
if( $i == 0 || $i == 1) then
# not less than nor equal to 10
if(!($i <= 10)) then
202*
8.6 Files operators
La tavola che segue riassume i tipi di file operators ammessi dalla C shell. Essi ritornano
un valore true o false e vengono quindi usati nei costrutti logici (ad esempio in costrutti
con if).
Tavola
-d
-e
-f
-o
-r
-w
-x
-z
true if file is a directory
true if file exists
true if file contains text
true if executor of file is owner
true if file is readable by executor
true if file is writable by executor
true if file is executable by executor
true if file is empty
# true if /usr/fred is a directory
if( -d /usr/fred ) then
# true if /tmp/file exists
if ( -e /tmp/file) then
# true if /usr/fred/text contains text
if ( -f /usr/fred/text ) then
# true if fred owns /usr/fred/file
if ( -o /usr/fred/file) then
#true if /usr/fred/file is readable
if( -r /usr/fred/file) then
#true if /usr/fred/file is writeable
if( -w /usr/fred/file) then
# true if /usr/fred/file is executable
if( -x /usr/fred/file) then
#true if /usr/fred/file is empty
if( -z /usr/fred/file) then
203*
8.7 Operatori matematici
Tavola
Affrontiamo ora quegli operatori che
permettono di eseguire calcoli
aritmetici con variabili di shell che
contengano valori interi.
Nella tavola che segue, sono
raggruppati prima gli operatori
aritmetici, poi quelli che agiscono sui
bit di tali variabili.
Integers
=
+
*
/
++
-%
Assign
Add
Subtract
Multiply
Divide
Increment by 1
Decrement by 1
Modulo
Bits
>>
<<
~
!
|
^
&
Right bit shift
Left bit shift
1’s complement
Logical negation
Inclusive OR
Exclusive OR
AND
204*
si noti @ piu’ lo spazio bianco che indica che la
variabile di shell k deve avere come valore il
risultato dell’operazione a destra dell’uguale.
#!/bin/tcsh
set i = 15
@j=3
echo “i :$i ; j :$j”
# addition
@ k = $i + $j
echo “addition : $k”
#subtraction
@ k = $i - $j
echo “subtraction : $k”
#division
@ k = $i / $j
echo “division : $k”
# multiplication
@ k = $i * $j
echo “multiplication : $k”
# modulo
@ k = $i % $j
echo “modulo : $k”
# autoincrement
set k = 10
@ k++
echo “autoincrement : $k”
205*
# autodecrement
set k = 10
@ k- echo “autodecrement : $k”
# right bit shift
@ k = ( $i >> 2 )
echo “right bit shift i by 2 : $k”
# left bit shift
@ k = ( $i << 2 )
echo “left bit shift i by 2 : $k”
# invert bits
@ k = ~ $i
echo “invert bits : $k”
# logical negation
@ k = ! $i
echo “logical negation : $k”
# bitwise inclusive OR
@ k = ( $i | $j )
echo “bitwise inclusive OR : $k”
# bitwise exclusive OR
@ k = ( $i ^ $j )
echo “bitwise exclusive OR : $k”
# bitwise AND
@ k = ( $i & $j )
echo “bitwise AND : $k”
206*
8.8 Flow control
Gli statements di flow control servono a direzionare la
sequenza di istruzioni da eseguire in dipendenza dal
verificarsi di determinate condizioni.
Nella C shell questi comandi sono molto simili a quelli del
linguaggio C e sono elencati nella tavola qui sotto.
Tavola degli statements
di flow control
if
while
foreach
switch
goto
207*
Comando if
Come nel linguaggio C, questo comando provoca un branching semplice, doppio o
multiplo.
oppure :
Sintassi
oppure :
:
if ( condition ) statement
if
( condition ) then
[statements]
endif
oppure :
if
( condition ) then
[statements]
else
[statements]
endif
if
( condition ) then
[statements]
else if ( condition ) then
[statements]
…
[ else if ( condition ) then
statements
]
...
[ else
statements ]
endif
208*
Comando if
#!/bin/tcsh
# report a file executable satus
echo -n “enter filename”
set a = $<
if (-x $a) then
echo “$a is an executable”
else
echo “$a is not an executable”
endif
exit
piccolo script che riporta se il file
che diamo come input da terminale,
e’ un eseguibile
file operator che rende vera
l’espressione se $a e’ un eseguibile
file operator che rende vera
l’espressione se $a e’ vuoto
piccolo script che riporta se il file
che diamo come argomento, e’ non
vuoto ed in tal caso lo stampa a
terminale.
#!/bin/tcsh
# displays a non-empty file
if(-z $1) then
echo “File $1 is empty”
exit
endif
more $1
exit
209*
Comando while
Come nel linguaggio C, questo e’ un
comando di loop, che viene eseguito
finche’ una certa condizione e’ vera.
Sintassi
:
while ( condition )
...
[statements]
...
end
#!/bin/tcsh
# displays calendar by month
set i = 1
while ($i != 13)
se $i non e’ uguale a 13
cal $i 2002
@ i = ($i + 1)
end
echo “Calendar complete”
exit
210*
Comando foreach
Anche questo e’ un comando di loop che
esegue un blocco di statements per ogni
componente di una lista di elementi.
Sintassi
:
foreach variable ( list )
...
[statements]
...
#!/bin/tcsh
# displays all .txt files
foreach i ( *.txt )
cat $i
end
exit
l’uso di * crea una lista di
files che terminano con .txt
La variabile di shell i assume,
uno per volta, tutti i valori di
tale lista.
end
#!/bin/tcsh
# displays characteristics
# of files of the list
set files = ( test1 test2 test3 )
foreach i ( $files )
ls -l $i
end
in questo esempio, la lista di
exit
valori che i assume, e’ stata
definita direttamente
nello
211*
script.
Comando switch
Questo e’ un comando di flow control del tutto analogo al corrispondente
comando in C. Il flusso di istruzione da eseguire viene diretto a quella case
label la cui label corrisponde al valore della variabile dello switch. Si puo’ poi
definire anche una label (comando default:) per i casi in cui la variabile dello
switch non corrisponda a nessuna altra label. Infine il comando breaksw
serve per far saltare fuori dal costrutto di switch e far eseguire la prima
istruzione che segue endsw.
Sintassi
:
switch ( string )
case string1:
[statements]
[breaksw]
case string2:
[statements]
#!/bin/tcsh
echo “select printer ; l or <cr> for laser, p for plotter”
set var = $<
var e’ la variabile dello switch
switch ( $var )
case l:
se var ha valore p il programma salta qui
lpr -Plaser $1
ed esegue tutti i comandi che seguono
breaksw
case p:
lpr -Pplotter $1
il programma salta alla prima istruzione
breaksw
dopo endsw poiche’ qui c’e’ breaksw
default:
lpr -Plaser $1
se var NON ha ne’ valore p ne’ valore l
endsw
il programma salta qui ed esegue tutti i
exit
comandi che seguono
[breaksw]
...
case stringn:
[statements]
[breaksw]
[default:]
[statements]
endsw
212*
Comando goto
Il flusso d’esecuzione dei comandi viene ridiretto
all’istruzione marcata dalla label label. Anche questo
e’ un comando che ha una eguale controparte nel C.
Sintassi
:
goto label
In questo esempio viene stampato
a terminale il valore della prima
variabile passata allo script, se l’utente
l’ha passata effettivamente.
Nel caso contrario, viene stampato
il messaggio :
Variable 1 is undefined
#!/bin/tcsh
if ($1 == “” ) goto undefined
echo “the value of variable 1 is :$1”
exit
undefined:
echo “Variable 1 is undefined”
exit
si noti che la label undefined
deve essere seguita da :
213*
Error handling and flow control
Error handling significa dirigere il flusso di istruzioni a seconda che un comando vada
a buon fine o abbia esito negativo. In Unix questo si puo’ fare almeno in due modi, sia
usando gli operatori logici || e && , sia usando direttamente la varibile di shell status ,
che assume generalmente valore 0 quando comando va a buon fine.
Cominciamo con gli operatori logici
Funzionamento degli operatori
logici usati con comandi
command 1
succeeds
yes
no
yes
no
operator
||
||
&&
&&
command 2
executes
no
yes
yes
no
Sintassi OR logico :
command1 ||
command2
Sintassi AND logico :
command1 && command2
214*
Error handling and flow control
se la compilazione del programma
in C test.c NON va a buon fine …
#!/bin/tcsh
cc test.c >& error || mail studente < error
… spedisci un mail con gli errori di
compilazione all’utente studente
se nel file delle passwords esistono
utenti che usano la tcsh shell …
#!/bin/tcsh
grep tcsh /etc/passwd > lista && mail studente < lista
… spedisci un mail con l’elenco di
215*
tali utenti
Error handling and flow control
Uso della variable di shell status
La variabile status viene ridefinita dopo
l’esecuzione di ogni comando o shell
script.
Sfortunatamente il valore assunto non
e’ consistente per tutti i comandi ed e’
generalmente anche dipendente dai vari
flavours di Unix. In generale si tenga
presente che se status e’ 0 vuol dire che
l’esecuzione del comando ha avuto
successo, se status =1 vuol dire che la
sintassi era giusta, ma il comando non
ha in qualche modo raggiunto lo scopo
che si era prefisso, infine se status ha
qualche altro valore vuol dire che la
sintassi non era corretta o qualche file
non esiste. Ad ogni modo e’ buona
norma controllare sempre come si
comporta status quando lo si vuole
usare in uno script.
Il comando
ha avuto
successo,
status e’ 0
Sintassi giusta,
ma pallino non e’
stato trovato ;
status e’ 1
Il file prrrr.txt
non esiste; status e’ 2216*
Error handling and flow control
Uso della variable di shell status
Ecco un esempio di script in cui viene eseguito il comando grep sui due argomenti
passati allo script. Viene quindi sfruttata la variabile status per fare un minimo di
error handling.
Lo script vuole due
argomenti nella chiamata :
$1 e’ il pattern da cercare,
$2 e’ il file in cui cercare.
Gli argomenti
passati a grep
generano un
errore di
sintassi !
#!/bin/tcsh
grep $1 $2
set error = $status
if( $error == 0) then
echo “execution successful”
Il pattern non c’e’ nel
else if ($error == 1 ) then
file; status e’ 1.
echo “nothing found”
else
echo “severe error found you, idiot !”
endif
exit
217*
8.9 Comandi built-in nella C shell
E’ gia’ stato detto precedentemente dei comandi built-in nella C shell. Esempi di
di tali comandi sono alias, bg, cd, dirs, echo, fg, history, if (else etc. ), jobs, kill, limit,
logout, nice, popd, pushd, set, setenv, shift, switch, umask, unalias, unlimit, unset,
unsetenv, which, while.
Vengono introdotti qui altri comandi built-in utili nella programmazione della C shell.
Si tratta di :
ridireziona il flusso di
istruzioni quando viene
mandato un interrupt allo
script
determina quant’e’ il tempo
di esecuzione di un comando
onintr
eval
time
source
forza l’esecuzione di un
comando interpretando
eventuali metacaratteri
presenti nel comando
prende i comandi da eseguire da una sorgente
(source, appunto; tipicamente un ASCII file).
Eventuali definizione di shell variables e di alias
NON vengono perse dopo l’esecuzione di tutti i
218*
comandi contenuti nella sorgente
Comando onintr
Questo comando ridirige il flusso dello script quando l’utente da’ un <ctrl>C interrupt
da tastiera. Il flusso di comandi dello script, invece di interrompersi semplicemente,
salta alla label indicata ed esegue i comandi a partire da li’ come indicato nell’esempio
seguente.
#!/bin/tcsh
# partial example of interrupt handling
onintr pippo
Se l’utente da’ un <ctrl>C
…
exit
il comando salta alla label
pippo:
indicata (pippo) ed esegue
echo “script terminated abnormally” i comandi che seguono
exit
219*
Comando eval
E gia’ stato detto precedentemente che generalmente per eseguire dei comandi che non
siano built-in, la C shell genera un child process. Nei casi pero’ in cui il comando sia
contenuto ad esempio in una shell variable, il child process NON interpreta eventuali
metacaratteri in esso presenti, ma prende ogni elemento letteralmente e questo puo’
produrre risultati del tutto non voluti. Il comando eval e’ utile in questo caso, poiche’
forza l’esecuzione da parte della current shell (cioe’ senza forking) interpretando
eventuali metacaratteri presenti nel comando. L’esempio che segue dovrebbe chiarire il
problema.
220*
Comando eval
Il comando (command string)
e’ stato depositato nella variabile test
Qui l’intenzione e’ di far eseguire
il comando ls -l | grep example_10
Il metacarattere | non viene
riconosciuto come tale ma
letteralmente come nome di file!
eval ci viene in soccorso
interpretando | come
metacarattere di piping
ed eseguendo il comando
come volevamo !
221*
Comando time
Sintassi :
time [command]
Il comando time lancia un comando od uno script e ne fornisce anche il tempo che ci
vuole per eseguirlo. Se non gli viene dato un argomento, time riporta il tempo usato
dal parent process e da tutti i suoi child processes dall’inizio della sessione.
0 minuti e 22.21 secondi
2.801 secondi
lancia lo script myscript e ne calcola il tempo
1 page (cioe’ 512 bytes) input
+ 1 page di output sul disco
1 page faulted in +
0 page faulted out
1 Kb di physical memory
+ 2 Kb di memory stack
user time
consumato
system time
consumato
tempo solare
trascorso
% delle risorse
di CPU usato
222*
Comando source
Questo comando serve quando si vogliono eseguire i comandi da una sorgente (source,
appunto) che tipicamente e’ un file ASCII. Questo risultato si potrebbe ottenere
ugualmente dando direttamente il comando
sorgente
da STDIN (a patto
che il file abbia la protezione x on).
La differenza e’ che con source eventuali definizione di shell variables ed eventuali
definizioni con alias NON vengono perse dopo l’esecuzione di tutti i comandi contenuti
in sorgente ma continuano a valere per la current shell.
Sintassi :
source [-h] sorgente
Opzione :
-h
serve solo per mettere i comandi contenuti in sorgente nella
history list (per default NON ci vengono messi) ; i comandi NON
vengono effettivamente eseguiti.
223*
Comando source
#!/bin/tcsh
# definizioni di variabili ed esecuzione \
di ls
set var1 = test
#
ls
exit
pwd
/home/boca
ls
program.f program.x prova.com test_script zoom
test_script
esegue direttamente lo script
program.f program.x prova.com test_script zoom
echo $var1
la variabile di shell var1 viene persa
var1: Undefined variable
dopo l’esecuzione di test_script
source test_script
program.f program.x prova.com test_script zoom
echo $var1
test
con source la variabile di shell var1 mantiene
la sua definizione anche nella current shell
224*
8.10 Debugging
Si puo’ fare il debugging (eliminazione degli errori di programmazione) di uno shell
script eseguendo lo script mediante il comando csh con determinate opzioni; tra tutte
esaminiamo qui solo -x e -v
Sintassi :
csh [-options] script
Opzione :
-x
ripete le linee di comando dopo aver eseguito eventuali
variable substitutions. Utile per localizzare problemi legati
a variable substitutions.
-v
ripete le linee di comando PRIMA di aver eseguito eventuali
variable substitutions. Utile per localizzare quale comando
fa fallire lo script.
225*
8.10 Debugging
esegue lo script ripetendo i
comandi DOPO aver fatto ...
… la variable sustitution
esegue lo script ripetendo i comandi
letteralmente, come sarebbero SENZA
la variable substitution
226*
Si definisco programmi di text processing quelli che leggono un file di input ASCII, lo
manipolano in vari modi e generalmente producono un testo di output.
In questa categoria possiamo mettere i comandi di screen editor vi e nedit gia’ visti in
precedenza.
Vedremo ora il comando awk che e’ un potente programma di text processing la cui
versatilita’ lo avvicina ad un linguaggio ad alto livello. E’ un comando di text processing
line oriented poiche’ il testo viene analizzato una linea alla volta. Le possibilita’ offerte da
awk sono tra l’altro :
1) field oriented processing
5) arithmetic expressions
2) predefined variables
6) scalar variables and arrays
3) variable assignment
7) output redirection and piping
4) logical operations
227*
Sintassi :
awk [-options] ’program text’ file [file2 … ]
dove program text ha la forma :
pattern {action} ... pattern {action}
Opzione : -Fdelimiter
questa opzione specifica che l’ input field separator
e’ delimiter invece che il blank (che e’ il default)
-f awk_script
specifica che i comandi da eseguire non vengono
dati da terminali ma sono contenuti nel file ASCII awk_script
-v var=val viene definita una variabile var che puo’ essere ‘vista’
durante l’esecuzione dei comandi di awk. A tale variabile viene anche assegnato
assegnato il valore val prima di cominciare ad eseguire le altre operazioni.
Azione :
il comando esamina ogni riga di file (se ci sono piu’ files in input
vengono concatenati e visti come un unico grande file), una riga alla volta,
la scompone in campi (fields), indidua eventuali patterns, esegue
eventuali azioni (actions).
228*
Le single quotes ( ’ ) delimitano le combinazioni pattern - action statements ; le parentesi
graffe { } isolano le actions dai patterns. Il pattern viene per primo, poi si mette l’action.
Sia il
pattern che l’action possono non esserci ma, non entrambi.
Se il pattern manca, l’action sara’ eseguita per ogni record (cioe’ per ogni riga) di input.
Se manca l’action allora viene assunta quella di default che e’ print vale a dire la
stampa dell’intera riga di input.
Infine in mancanza dell’opzione -F il field delimiter e’ lo spazio (blank).
pattern :
il primo campo sia uguale a pippo
action :
stampa a stdout il primo e terzo campo
229*
9.1 Definizione dei campi con i field separators
Per default il delimitatore di campi (field separator) e’ qualunque un numero di blanks
tra caratteri non blank. Eventuali blanks all’inizio della riga vengono trascurati.
secondo campo
primo campo
cat dimostrazione_campi.txt
primocampo secondo terzo
field delimiter
terzo campo
230*
Si puo’ ridefinire il field separator con una qualunque stringa di caratteri, con l’opzione
-F come negli esempi che seguono. A differenza del blank, piu’ field separators di seguito
definiscono campi vuoti ed eventuali field separators all’inizio di una riga NON vengono
trascurati da awk.
quarto campo
primo campo
(vuoto)
cat esempio.txt
::nome:cognome::via:paese
awk -F: ‘{print $4}’ esempio.txt
cognome
il : e’ il field delimiter
l’action e’ un print
su stdout
231*
il field
delimiter
e’ :
pattern : uno
qualunque dei campi
sia uguale a boca
l’action e’ un print
di $0 (tutta la riga)
delimitatore dei
campi pattern-action
file esaminato
da awk 232*
risultato del comando
9.2 Patterns
Diamo la tavola dei tipi di patterns di awk e, nelle pagine seguenti, numerosi esempi.
Tavola dei patterns di awk
BEGIN
esegue dei comandi prima di esaminare alcuna
linea di input
END
esegue dei comandi dopo aver saminato tutte le linee
di input
/regular expression/
pattern di match (con una regular expression)
relational expression
pattern che contiene relational operator(s)
pattern && pattern
AND logico di due patterns
pattern || pattern
OR logico di due patterns
!pattern
NOT logico di un pattern
pattern1?pattern2:pattern3 questo operatore ternario e’ uguale all’analogo del C.
Se pattern1 e’ vero allora il pattern usato nel test logico
e’ pattern2, altrimenti e’ pattern3
pattern1, pattern2
questa forma e’ chiamata pattern range. Corrisponde
a tutti i recors in input che cominciano con un record
che corrisponde a pattern1 fino al record che soddisfa
233*
pattern2, inclusi.
Patterns contenenti BEGIN od END
prima dell’esame delle righe
di input viene eseguita
la stampa tra parentesi graffe
backslash prima di return per la
continuazione del comando
nella prossima riga
operatore aritmetico di
autoincremento come
quello del C
dopo aver esaminato il
file di input viene eseguito
lo statement tra parentesi graffe
234*
Pattern di match (con una regular expression)
Il pattern di match e’ indicato dalla presenza delle barre in avanti (slash). Il match si
verifica quando uno o piu’ campi contengono la stringa di caratteri con cui si fa il match.
Quest’ultima e’ appunto quella racchiusa tra barre. Si noti che quest’ultima puo’ essere
sia una stringa normale, sia una con i simboli speciali (ad es. il $ ed il ^) che si possono
usare con il comando grep, con significato analogo. In UNIX sia le stringhe normali che
quelle con simboli speciali vengono chiamate regular expressions.
pattern :
un campo qualunque sia uguale a boca
action statement :
print da solo, cioe’ print di tutta la riga
l’output del comando
awk e’ il printout di
tutte le righe del file
/etc/passwd che abbiano
un qualunque campo
uguale a boca
235*
Pattern di match (con una regular expression)
Il pattern di match e’ indicato dalla presenza delle barre in avanti (slash). Il match si
verifica quando uno o piu’ campi contengono la stringa di caratteri con cui si fa il match.
Quest’ultima e’ appunto quella racchiusa tra barre. Si noti che quest’ultima puo’ essere
sia una stringa normale, sia una con i simboli speciali (ad es. il $ ed il ^) che si possono
usare con il comando grep, con significato analogo. In UNIX sia le stringhe normali che
quelle con simboli speciali vengono chiamate regular expressions.
pattern :
un campo qualunque sia uguale alla regular expression ^b
(che vuol dire una stringa di caratteri che inizi con b )
l’output del comando
awk e’ il printout di
tutte le righe che hanno
qualche campo che
comincia per b
236*
Pattern di match (con una regular expression)
Il pattern di match e’ indicato dalla presenza delle barre in avanti (slash). Il match si
verifica quando uno o piu’ campi contengono la stringa di caratteri con cui si fa il match.
Quest’ultima e’ appunto quella racchiusa tra barre. Si noti che quest’ultima puo’ essere
sia una stringa normale, sia una con i simboli speciali (ad es. il $ ed il ^) che si possono
usare con il comando grep, con significato analogo. In UNIX sia le stringhe normali che
quelle con simboli speciali vengono chiamate regular expressions.
pattern :
il primo campo sia uguale alla regular expression ^g
( stringa di caratteri che inizi con g )
action mancante, significa print ;
l’output del comando
awk e’ il printout di
tutte le righe che hanno
il primo campo che
comincia per g
237*
Pattern di match (con una regular expression)
Il pattern di match e’ indicato dalla presenza delle barre in avanti (slash). Il match si
verifica quando uno o piu’ campi contengono la stringa di caratteri con cui si fa il match.
Quest’ultima e’ appunto quella racchiusa tra barre. Si noti che quest’ultima puo’ essere
sia una stringa normale, sia una con i simboli speciali (ad es. il $ ed il ^) che si possono
usare con il comando grep, con significato analogo. In UNIX sia le stringhe normali che
quelle con simboli speciali vengono chiamate regular expressions.
pattern :
qualunque campo sia uguale alla regular expression tcsh$
che vuol dire stringa di caratteri che finisca con tcsh
l’output del comando
awk e’ il printout di
tutte le righe che hanno
qualunque campo238*
che
termina per tcsh
Altri esempi di patterns
action
operatore relazionale <
operatore matematico
AND logico dei due patterns
239*
Altri esempi di patterns
se il 30 campo e’ < 10000
allora il 30 campo sia < 120
altrimenti il 40 campo sia < 120
corrisponde ai records (linee)
cominciando da quello che contiene
il pattern halt a quello che contiene
il pattern ope all’inizio della riga.
L’action non e’ indicata, quindi e’
quella di default : print $0
240*
Altri esempi di patterns
NOT logico (negazione)
241*
9.3 Actions
Come gia’ detto, le actions sono racchiuse tra parentesi graffe. Gli statements che formano
una action sono uguali a quelle disponibile nel linguaggio C. Il numero ed il tipo di actions
possedute da awk lo avvicinano molto ad un vero e proprio linguaggio ad alto livello.
Nel seguito, ciascuna categoria di action verra’ spiegata mediante un esempio.
Tipi di action statements
1) Variable assignment
2) Formatted printing, I/O statements, output redirecting
3) Mathematical and logiacal operators, string and mathematical
functions
4) Conditional, flow control and looping statements
242*
Variable assignment
In awk si possono definire delle variabili che possono essere scalari oppure anche vettori
ad una dimensione. Esistono anche delle variabili predefinite. Le variabili sono dinamiche,
cioe’ vengono create quando vengono usate per la prima volta. Inoltre, a differenza di
quanto succede in molti linguaggi di alto livello, NON occorre dichiarare prima il tipo di
variabile. I valori che possono assumere le variabili possono essere floating point, interi,
stringhe di caratteri in dipendenza da come vengono usate. L’utente assegna valori alle
variabili mediante l’uguale ( = ).
Non c’e’ bisogno che
la variabile x sia
stata definita prima
La variabile x puo’ assumere
valori sia interi che
alfanumerici (stringa di caratteri)
; separatore
di comandi
(come in C
e nella C shell)
243*
Variabili predefinite
Come detto prima, awk ha un set di varibili predefinite (built-in variables)che l’utente
puo’ usare in qualunque punto del suo script ; sono riassunte nella tavola che segue.
Tavola delle variabili predefinite
ARGC
ARGIND
ARGV
CONVFMT
ENVIRON
il numero di argomenti dati nella linea di comando di awk, ad
esclusione delle opzioni e dell’input file.
l’indice in ARGV del file correntemente esaminato.
array degli argomenti dati nella linea di comando di awk. L’array e’
numerato da 0 ad ARGC-1. Modificando dinamicamente ARGV
si possono controllare i files di dati in input.
il formato di conversione per i numeri che per default e’ “%.6g”
e’ l’array contenente i valori correnti delle environment variables.
Questo array e’ indicizzato dal nome della variabile d’ambiente e
ciascun elemento e’ il valore di tale variabile. Ad esempio,
ENVIRON[“HOME”] potrebbe essere /home/studente (vedi anche
seguito la sintassi degli arrays). Da notare che se si cambia questo
array all’interno di awk NON cambia il set di variabili d’ambiente
visto da programmi fatti partire da awk mediante redirection o
dall’uso della funzione system.
244*
Variabili predefinite
Come detto prima, awk ha un set di varibili predefinite (built-in variables)che l’utente
puo’ usare in qualunque punto del suo script ; sono riassunte nella tavola che segue.
Tavola delle variabili predefinite
se c’e’ un errore di sistema durante la ridirezionamento con la
la funzione getline o durante un read con getline e durante una close
allora ERRNO conterra’ una stringa che descrive l’errore.
FILENAME
il nome del file di input corrente.
FNR
l’input record number nel file di input corrente.
FS
l’input field separator (uno spazio per default).
IGNORECASE controlla la case-sensitivity di tutte le regular expressions e le
operazioni con stringhe. Se esso ha un valore diverso da 0, allora
tutte le operazioni che coinvolgono pattern matching, regular
expressions etc. non fanno differenza tra maiuscole e minuscole. Ad
es. /aB/ corrisponde alle stringhe “ab”, “aB”, “Ab” e “AB”.
NF
il numero di campi della riga corrente
NR
numero totale di input records (cioe’ righe di input) viste finora.
ERRNO
245*
Variabili predefinite
Come detto prima, awk ha un set di varibili predefinite (built-in variables)che l’utente
puo’ usare in qualunque punto del suo script ; sono riassunte nella tavola che segue.
Tavola delle variabili predefinite
OFMT
OFS
ORS
RS
RSTART
RLENGTH
SUBSEP
il formato di output per i numeri, per default “%.6g”. Modificando
questa variabile si puo’ modificare l’output del comando print NON
formattato; vedi in seguito nella sezione sull’ I/O.
l’ output field separator, uno spazio per default.
l’ output record separator; per default e’ un newline.
l’ nput record separator; per default e’ un newline.
l’indice del primo carattere corrispondente ai criteri della funzione
match( ) ; 0 se non ce n’e’ nessuno.
la lunghezza della stringa individuata da match( ) ; -1 se non ce n’e’
alcuna.
il carattere usato per separare gli indici ‘multipli’ negli arrays, per
default e’ “\034” (cioe’ il carattere ASCII corrispondente al numero
ottale 34 ( 1C in esadecimale) ; vedi seguito nella sezione dedicata
agli arrays).
246*
Variabili predefinite
Come detto prima, awk ha un set di varibili predefinite (built-in variables)che l’utente
puo’ usare in qualunque punto del suo script ; sono riassunte nella tavola che segue.
Tavola delle variabili predefinite
$0
$n
length(var)
tutto il record ( tutta la riga ) corrente
il field nesimo del record corrente
lunghezza (in caratteri) del contenuto di var
247*
Vettori
Come gia’ detto, in awk si possono definire delle variabili anche vettori. Tali arrays
vengono indicati, come in C, con un nome seguito da parentesi quadre ( [ ] ). Non e’
necessario dichiararne il tipo prima poiche’ vengono creati al momento dell’uso. La loro
dimensione e’ solo 1 . Tuttavia se ne puo’ sfruttare una notevole particolarita’, vale a dire
che l’indice dei vettori e’ una stringa di caratteri (proprieta’ associativa dell’indice del
vettore ) per simulare arrays a piu’ dimensioni.
Il vettore v ha indici
alfanumerici ( hash table )
248*
Vettori
Come gia’ detto, in awk si possono definire delle variabili anche vettori. Tali arrays
vengono indicati, come in C, con un nome seguito da parentesi quadre ( [ ] ). Non e’
necessario dichiararne il tipo prima poiche’ vengono creati al momento dell’uso. La loro
dimensione e’ solo 1 . Tuttavia se ne puo’ sfruttare una notevole particolarita’, vale a dire
che l’indice dei vettori e’ una stringa di caratteri (proprieta’ associativa dell’indice del
vettore ) per simulare arrays a piu’ dimensioni.
Infatti, se il vettore viene indicizzato con una lista di espressioni :
expr1, expr2,expr3 …
allora l’indice del vettore diventa la stringa risultato della concatenazione dei valori (come
stringhe) di ciascuna espressione, separate dal valore della variabile SUBSEP (vedi tavola
precedente delle variabili predefinite). In tal modo e’ possibile simulare la presenza di piu’
indici per il vettore.
Il vettore v ha un UNICO indice dato dalla
concatenazione dei valori A B C separati tra loro
dal separatore \034 (cioe’ dal valore contenuto in
SUBSEP)
Il vettore vec ha un UNICO indice dato dalla
concatenazione dei valori 3 1 5 separati tra loro
dal separatore \034 (cioe’ dal valore di SUBSEP).
Cosi’ il riferimento al vettore vec nello statement
print e’ formalmente identico a quello di un vero
249*
vettore multidimensionale
Vettori
Esiste in awk l’operatore in che serve per determinare se un valore e’ un possibile indice
di un vettore.
Valori possibili dell’indice di vec
sono 1 e 3
operatore in che restituisce un valore
(true o false ) che e’ possibile usare in uno
statement logico (if in questo esempio)
250*
Formatted printing, I/O statements,
output redirecting
Il printout a stdout si ottiene con lo statement print come abbiamo gia’ visto in numerosi
esempi precedenti. Si noti che print e’ anche l’action di default nel caso l’utente non ne
indichi esplicitamente di proprie. Nel caso invece si voglia formattare l’output si puo’ usare,
in modo del tutto analogo al C, lo statement printf.
Sintassi :
{ printf “format statement” expression }
dove program text ha la forma :
pattern {action} ... pattern {action}
printout di variabile floating point, in un campo
da 8 cifre con 2 cifre decimali
{ printf “%8.2f”,i }
{ printf “variabile intera %10d\n”,i }
{ printf “formato variabile %10.6g\n”,i}
printout di variabile intera in campo di 10 cifre
printout di variabile con formato variabile
in campo di 10 cifre con 2 cifre significative
251*
action :
printout delle variabili
i e $1 con un campo di
5 interi e come stringa
rispettivamente
252*
In awk e’ possibile ridirigere l’output, normalmente diretto a stdout, ad un file
oppure ad un altro comando con un piping.
> : ridirezione dell’output da stdout a users_file.lis
>> : ridirezione dell’output da stdout
a users_file.lis
piping dell’output di awk al comando
head -3
253*
Esistono anche altri statements che riguardano l’ I/O; sono riassunti nella tavola seguente
Tavola degli statements di Input/Output
close(file)
getline
getline < file
getline var
getline var < file
next
nextfile
close file or pipe
set $0 equal to the next input line; set NF, NR, FNR
set $0 equal to the next input line of file ; set NF
set var equal to the next input line; set NR, FNR
set var equal to the next input line of file
stop processing the current input record. The next input record
is read and processing starts over with the first pattern in the
awk program. If the end of the input is reached, the END
block(s), if any, are executed.
stop processing the current input record. The next input record
read comes from the next input file. FILENAME and ARGIND
are updated, FNR is reset to 1 and processing starts over with the
first pattern in the awk program. If the end of the input data is
reached, the END block(s), if any, are executed.
254*
Esistono anche altri statements che riguardano l’ I/O; sono riassunti nella tavola seguente
Tavola degli statements di Input/Output
fflush([file])
flush any buffers associated with the open output file or pipe
file . If file is missing, then stdout is flushed. If file is the NULL
string, then all open output files and pipes have their buffers
flushed.
system(command line) executes command line and returns the status. The
command is executed in the Bash shell (sh).
255*
action :
quando NR
(numero di records)
e’ uguale a 3
salta un record e
poni il prossimo
input record in $0
non ha stampato la
terza riga perche’
l’ha saltata con next
256*
pattern :
NR sia <= 3
esegue il comando di (Bash) shell date
257*
Operatori matematici e logici
Vengono di seguito elencati nella tavola gli operatori matematici e logici disponibili in
awk in ordine di priorita’ decrescente (gli operatori in cima all’elenco vengono eseguiti
per primi, quelli sulla stessa riga hanno la stessa priorita’ e vengono eseguiti da sinistra a
destra). Si nota una volta di piu’, che sono uguali agli operatori del C ; hanno anche
la stessa sintassi.
Tavola degli operatori matematici e logici
( )
$
++ -^
+ - !
* / %
+ space
<>
parenthesis
field reference
increment and decremet, both prefix and postfix
exponentiation (also ** )
unary plus, unary minus, negate value of expression
multiply, divide and remainder (modulo)
addition and subtraction
string concatenation
less than, greater than
258*
Operatori matematici e logici
Vengono di seguito elencati nella tavola gli operatori matematici e logici disponibili in
awk in ordine di priorita’ decrescente (gli operatori in cima all’elenco vengono eseguiti
per primi, quelli sulla stessa riga hanno la stessa priorita’ e vengono eseguiti da sinistra a
destra). Si nota una volta di piu’, che sono uguali agli operatori del C ; hanno anche
la stessa sintassi.
Tavola degli operatori matematici e logici
<= >=
!= ==
~ !~
less than or equal to, greater than or equal to
not similar to, similar to
match ( for example, $2~/A||B||C/ ),
no match ( for example, $2!~/A||B||C/ )
in
array membership
&&
Boolean AND
||
Boolean OR
?:
the C conditional expression
= += -= *= /= %= ^=
assignments
259*
pattern :
quando NR e’ uguale a 5
autoincremento di 1
il resto di $4 / 3
elevamento alla 4a potenza
260*
String functions
Il comando awk possiede anche una notevole varieta’ di funzioni che manipolano le
stringhe di caratteri.
Tavola degli string operators
gensub(r , s , h , [, t ] )
gsub(r , s , [, t ] )
index(string, substring)
length(string)
match (s , r )
search the string t for matches of the regular expression
r . If h is a string beginning with g or G, then replace
all matches of r with s. Otherwise, h is a number
indicating which match of r to replace.If no t is supplied
$0 is used insted.
for each substring matching the regular expression r in
the string t , substitute the string s , and return the
number of substitutions. If t is not supplied, use $0 .
starting position of string in substring;
if not found returns 0
length of string
returns the position in s where the regular expression r
occurs, or 0 if r is not present, and sets the values of
RSTART and RLENGTH
261*
String functions
Il comando awk possiede anche una notevole varieta’ di funzioni che manipolano le
stringhe di caratteri.
Tavola degli string operators
sprintf(fmt , expr-list)
prints expr-list according to fmt and returns the resulting
string
split(string, array, “separator”) separates string into elements of array according to the
field separator
sub(r , s , [, t ] )
just like gsub( ) but only the first matching substring is replaced
substr(string, position, length)
substring of string , starting at position , and length
characters long
tolower( string )
returns a copy of the string string with all the upper-case
characters in string translated to their corresponding
lower-case counterparts. Non-alphabetic characters are
left unchanged.
toupper ( string )
returns a copy of the string string with all the lower-case
characters in string translated to their corresponding
upper-case counterparts. Non-alphabetic characters are
left unchanged.
262*
inizializza la
variabile nc a 0
action :
incrementa la variabile nc della lunghezza
(numero di caratteri) di ciascuna linea di input
action :
splitting del 40 campo del record
di input, secondo il field separator :
e creazione del vettore time con
dentro il risultato dello splitting
action :
printout degli
elementi del vettore
time
263*
solo un BEGIN ed un END
in questo awk script; in pratica
il file di input e’ irrilevante
264*
Mathematical functions
La tabella che segue mostra le funzioni matematiche disponibili con awk.
Tavola delle funzioni matematiche
atan2(y , x)
cos(expr)
exp(expr)
int(expr)
log(expr)
rand ( )
sin(expr)
sqrt(expr)
srand(expr)
preturns the arctang of y /x in radians
returns cosine of expr (which is in radians)
exponential function
truncates to integer
natural logarithm
returns a andom number between 0 and 1
returns sine of expr (which is in radians)
returns the square root function
uses expr as a new seed for the random number generator
265*
pattern :
NR
minore di
action :
calcolo di sqrt(NR) e log(NR)
266*
Conditional, flow control and looping statements
Sono uguali a quelli del linguaggio C.
Tavola dei conditional, flow
control e looping statements
if(condition) statement [ else statement ]
while (condition) statement
do statement while condition
for(expr1 ; expr2 ; expr3 ) statement
for( var in array )
break
continue
exit [ expression ] { statements }
267*
268*
action :
loop while
action :
test del loop while
269*
loop for con la stessa sintassi del C
# esempio 1
print del contenuto della variabile
for (x = 1; x<=NF; x++) { print $x }
x (cioe’ $1, $2, $3 .. etc.)
…
# esempio 2
loop for con l’uso dell’operatore in
for (x in test;) {print x, test[x] }
…
# esempio 3
salta fuori dal loop
for (x = 1; x<=NF; x++) { if( $x == “halt”) break }
e continua con gli
...
statements seguenti
# esempio 4
for (x = 1; x<=NF; x++) { if( $x == “end”) continue }
forza l’esecuzione del prossimo ciclo del loop (a
partire dall’inizio del loop)
abbandonando l’esecuzione di quello corrente
270*
# esempio 1
for (x = 1; x<=NF; x++) { print $x }
…
# esempio 2
for (x in test;) {print x, test[x] }
…
# esempio 3
forscarta
(x = 1;il x<=NF;
x++) { if(
record corrente
e $x == “halt”) break }
salta fuori dal loop e va direttamente
... legge il prossimo record,
ad END oppure, in mancanza di
# esempio 4 il flusso di comandi
ricominciando
quest’ultimo,
esce }dai comandi di awk
for (x
= 1;PRIMO
x<=NF;comando
x++) { if( $x == “end”)
continue
DAL
…
# esempio 5
for (x = 1; x<=NF; x++) { incr += 1 ; if (incr > 100) exit }
...
scarta il record corrente e
# esempio 6
legge il prossimo record,
{ for (x = 1; x<=NF; x++) if( NF < 4) getline }
ricominciando il flusso di
...
comandi dal punto
# esempio 7
appena dopo getline
{ for (x = 1; x<=NF; x++) if( NF == 1) next }
271*
Sommario
Come esempio finale dell’uso di awk viene mostrato un awk script che controlla se uno
o piu’ files di testo hanno due parole adiacenti identiche (errore tipografico piuttosto
comune) e riporta tale evenienza in output.
numero totale
di linee di input
esaminate finora
FILENAME :nome del file
correntemente esaminato
NF
numero di fields
nel record
correntemente
esaminato
272*
273*
Fly UP