:: Sistemi Inoperativi - Lezione del 3 marzo 2008 ::
Torna alla pagina di Sistemi Inoperativi
Modulo 2 - Lezione 1 - Funzioni del sistema operativo
Astraiamo un po' dalla macchina di Fonnoiman. A parte i sistemi embedded, in genere non si sa che tipo di applicativi gireranno su una data macchina, a meno che non sia quella di Rasputin, per cui ci saranno istruzioni ottimizzate MMX (Multi-hand Masturbation eXtension).
Occorre fare però in modo che ogni appli pensi che tutto il sistema sia lì per lei. Ciò si chiama virtualizzazione, e consiste nel dare l'illusione ad ogni programma che il sistema gli sia dedicato. Questo fa sì che le applicazioni possano essere scritte e possano funzionare senza curarsi delle altri: ci pensa il SO a illudere ciascuna. Senza la virtualizzazione, occorrerebbe scrivere e compilare applicazioni apposta non solo per ogni macchina, ma per ogni tipo di utilizzo della macchina stessa.
Da notare che, comunque, se un'applicazione chiede risorse che il sistema non può dare, non c'è virtualizzazione che tenga.
Al fine di offire la virtualizzazione alle applicazioni, il SO va organizzato in un certo modo a livello logico. Bisogna gestire in modo opportuno processore, memoria centrale e I/O, così che ogni processo veda sotto di sé l'intera Fonnoiman.
Nella fattispecie:
- processore: ogni applicazione vede il processore tutto per sé
- memoria centrale: ogni appli vede tutta la memoria per sé
- I/O: ogni appli vede le periferiche tutte per sé.
Il SO genera immagini astratte e semplificate di questi tre componenti. Sopra alla virtualizzazione però c'è ancora qualcosa: c'è il file system, che se ci pensate a noi fa vedere nomi di files e cartelle, mentre lavora con cilindri e testine e settori.
Gestione del processore
Vuol dire saper gestire i processi, ovvero crearli, farli finire, sospenderli e riattivarli, schedularli (scegliere il giusto ordine di esecuzione dei processi per ottimizzare le risorse, ma anche la percezione di un sistema fluido da parte dell'utente), sincronizzarli, evitare i deadlock e farli comunicare.
Non è poca roba.
Nota: un deadlock si ha quando un processo attende una risorsa, che è impegnata da un altro processo, il quale a sua volta attende una risorsa che è impegnata dal primo. L'uno aspetta l'altro, e nessuno fa un passo avanti.
Gestione della memoria centrale
I processi sono mantenuti in memoria centrale, come sostiene la multiprogrammazione. Ogni processo ha quindi la sua parte di memoria allocata e protetta da interferenze altrui.
Gestione delle periferiche
Le periferiche, oltre ad essere configurate ed inizializzate, vanno anche gestite. Le appli devono poter accedere in modo omogeneo a tutte le periferiche. Inoltre, occorre fare lo scheduling degli accessio I/O, e ottimizzare un po' le cose con buffering e caching.
File System
I file e le directory (a me direttorio non piace proprio, fa un po' Rivoluzione Francese e un po' fascista) devono poter essere creati, cancellati etc. Poi ci sono tutte le operazioni di copia, di ricerca, di protezione, di sicurezza, accounting e così via.
Gestione dell'interfaccia utente
In cima a tutto, si deve comunicare con l'utente. L'utente deve poter interagire coi processi. Questo aspetto ha due facce: da un lato l'utente deve poter colloquiare con i processi, dall'altro i processi devono poter colloquiare col sistema operativo.
Per quanto riguarda il colloqui tra utente e processo, ci sono interpreti di linea di comando e GUI. Per l'altro aspetto, c'è tutta la faccenda delle funzioni del sistema operativo, rese disponibili in qualche modo ai processi.
Lezione 2 - Architetture dei SO
Sistema monolitico
Vecchio modo di affrontare le questioni. Oltre alle scimmie che intorno ad esso scoprivano la civiltà, siamo alla faccenda dei job eseguiti uno dopo l'altro, con le funzioni interne senza nessun ordine che tanto le periferiche sono poche e i programmi sono scritti appositamente per la macchina. Da mantenere è difficile soprattutto quando si cresce in dimensioni.
Sistema con struttura gerarchica
Per aumentare la mantenibilità della base di codice del SO, si è pensato di organizzare le funzioni del SO in modo gerarchico. Quelle di un certo livello possono vedere solo quelle di livello inferiore. Le eventuali modifiche richiedono la palpugnazione di relativamente poche funzioni, perché bene o male si sa chi chiama cosa. Ma non c'è distinzione tra gli ambiti delle funzioni.
Sistema stratificato
Le procedure che riguardano un certo strato sono confinate all'interno di quello strato. Bello: però poco efficiente, perché per accedere a strati lontani dal mio devo passare attraverso innumerevoli chiamate.
Sistema a microkernel
Il SO viene diviso in 2 aspetti. Da una parte c'è l'hardware e le operazioni elementari che posso compiere su di esso, come spegnerlo e versarci il caffé sopra. Dall'altra ci sono le politiche, ovvero le regole, per utilizzare l'hardware: meccanismi VS politiche, uno scontro virulento.
Il microkernel realizza i meccanismi, e le politiche sono realizzate altrove. Quindi, la manutenzione è facile. L'efficienza però può risentirne.
Sistema a moduli funzionali
C'è un nucleo centrale che realizza le funzioni di base, e poi altri moduli che si connettono ad esso.
Sistema a macchine virtuali
Nacque dall'esigenza di installare più sistemi operativi di tipo batch su una macchina, così che venisse sfruttata di più. L'idea era di offrire ad ogni SO una replica della macchina sottostante. Poi si è pensato di poter offrire ste macchine virtuali anche a SO diversi.
Programmi di sistema
Oltre a come realizzo il mio SO internamente, occorre cmq tutta una serie di programmi per mantenerlo, per gestire i processi, e così via.
Lezione 3 - Generazione e avvio di un SO
Per scrivere un SO, dobbiamo sapere innanzitutto a che cosa servirà, e su che macchina dovrà girare, perché questo influenzerà le scelte di design. Più il SO è generico, e meno sarà efficiente (grosso modo).
I fattori da tenere in conto sono:
- applicazioni che vi gireranno
- utenti
- carico di lavoro
In genere è l'esperienza che dice come configurare i parametri del sistema operativo in funzione del carico di lavoro.
Avvio di un SO
Il bootstrap è la procedura di avvio del sistema operativo. Può essere eseguito in 1 passo, 2 passi, 3 passi.
Bootstrap ad 1 passo
Avviene quando il SO risiede in una ROM. Viene copiato in una RAM ed entra nel sonno REM, dopo aver bevuto del RUM. Alla fine rimane RIMbambito.
Il processore piglia semplicemente la pima istruzione del SO, e la esegue. Per pigliarla, viene hard-coded da qualche parte l'indirizzo della prima istruzione. Chiaramente stiamo parlando di sistemi embedded o simili.
Bootstrap in 2 passi
Il primo passo viene eseguito da un programma risiedente in una ROM. Questo programma è il caricatore del sistema operativo, ovvero si occupa di pescare da una posizione nota (in genere il primo settore del primo disco fisso) la prima istruzione del nostro SO.
Il secondo passo consiste nel cedere il controllo, da parte del nostro caricatore, al SO che è appena stato caricato in memoria dalla posizione nota di cui sopra, in un'altra posizione nota in memoria centrale.
Bootstrap in 3 passi
- Passo 1: il caricatore elementare viene caricato in memoria ed eseguito. Si trova da qualche parte in ROM.
- Passo 2: il caricatore elementare carica in memoria il caricatore complesso, NON il SO. Questo è il cosiddetto loader di 2° livello. Questo loader può cercare SO ovunque nei dischi, non è limitato al primo settore del primo disco o cose simili
- Passo 3: infine il caricatore del SO si preoccupa di avviare il SO stesso, ed è possibile passargli parametri per caricare moduli opzionali o simili.
Si usa questo sistema per dare l'opportunità di caricare più sistemi operativi, magari da un menu, o anche quando un SO è abbastanza grande da non starci nel settore iniziale di un disco. Ecco perché serve un caricatore secondario.
Il caricatore secondario può anche offrire un'interfaccia all'utente, come LILO o GRUB.
Da notare che non è necessario, per avere l'opzione di bootare più sistemi operativi sulla stessa macchina, avere un bootloader in 3 passi. Un bootloader caricato in ROM ed opportunamente programmato può offrire la stessa funzionalità.
Passi multipli
Questa dicitura si riferisce al procedimento di caricare rapidamente in memoria la parte essenziale del SO, e caricare il resto a tornate successive, possibilmente con un alto grado di configurabilità.
Torna alla pagina di Sistemi Inoperativi