cerca
Sistemi Operativi - Lezione del 4 marzo 2008
modifica cronologia stampa login logout

Wiki

UniCrema


Materie per semestre

Materie per anno

Materie per laurea


Help

Sistemi Operativi - Lezione del 4 marzo 2008

 :: Sistemi operativi - Lezione del 4 marzo 2008 ::

Torna alla pagina di SO

Lezione 4: interfacce dei SO

Le interfacce per l'utente possono essere grafiche o testuali, e in questo ultimo caso c'è spesso una shell, ovvero un interprete dei comandi. Sono basate sullo stesso sistema fetch, decode, execute che caratterizza il flusso operativo del processore: infatti le interfacce fetchano l'input dell'utente, lo decodificano e eseguono ciò che viene loro ordinato (di solito).

Interfacce programmative

Sono le interfacce al SO, ma accessibili tramite la programmazione.

Hanno diversi nomi, che sono sì sinonimi, ma che mettono in rilievo un aspetto diverso della faccenda:

  • system call = chiamate di sistema
  • supervisor call = chiamate a supervisore
  • monitor call = chiamate a monitor

Il SO può essere visto come colui che supervisiona tutti i suoi bravi figliuoli, ovvero i processi che tanta parte avranno tra poco tempo:)

Queste system call devono proteggere il nostro SO, garantire l'integrità dei dati, l'esecuzione delle procedure e l'esecuzione dei controlli. Le risorse vanno gestite bene, e a questo scopo è importante cercare di proibire ad un programmatore di bypassare il SO per accedere direttamente all'hardware.

I vantaggi di chiamare il SO invece di accedere direttamente all'hardware sono molteplici:

  • il programmatore non deve occuparsi dei dettagli di 1000 tipi di hardware diverso;
  • non si devono reimplementare ogni volta le stesse funzioni;
  • se le funzioni sono complesse, si può sbagliare a scriverle, se non si è esperti in quel ramo.

Le chiamate di sistema non sono normali chiamate di procedura, anche se concettualmente lo sono. Ogni volta che ne viene fatta una, si controllano ben bene i permessi di chi le sta chiamando. Per evitare che il programmatore possa mettersi a fare CALL a indirizzi arbitrari della memoria riservata al sistema operativo (e quindi esporre lo stesso a grandi rischi), bisogna che non si usi una semplice call.

A questo scopo, si usa il meccanismo delle TRAP. È un meccanismo che genera interruzioni via software, del tutto simili alle interruzioni che arrivano al processore dalle periferiche hardware. Per scoprire chi ha chiamato la TRAP, si controlla lo stack delle chiamate. Il sistema operativo espone i nomi di funzioni e li associa agli indirizzi delle trap, ma non espone direttamente l'indirizzo del codice delle funzioni che espone. Trattandosi di interruzioni software sono sincrone con l'evoluzione della computazione, al contrario delle interruzioni hardware che sono asincrone per natura.

Modulo 3 - Lezione 1: i processi

Multitasking = è un passo oltre alla multiprogrammazione (avere più programmi contemporaneamente in memoria). Il multitasking vuol dire che quando un programma attende l'I/O da qualcosa, viene messo in pausa e viene chiamato un altro dei programmi che sono in ballo in quel momento, altrimenti detti processi.

Un processo è composto da codice, dati e stato di evoluzione della computazione. Lo stato di evoluzione della computazione è il valore del program counter e delle variabili in un dato istante. Esso mi dice a che punto dell'esecuzione del codice di quel processo siamo arrivati.

OCIO: programma != processo. Un programma è un'entità passiva, una lista di istruzioni. Un processo è un'entità attiva, con delle risorse in uso e delle variabili con certi valori. Il programma non è legato ad una particolare istanza dei suoi dati in input; il processo sì.

OCIO BIS: lo stato di evoluzione della computazione NON È lo stato del processo! Lo stato del processo è un'altra cosa che vedremo più in là!

Si può anche vedere il processo come una funzione: in input ci sono dei dati, e lui produce dell'output. È anche immaginabile come un automa a stati finiti, in cui le transizioni tra gli stati (le frecce del pallograma di scarabottoliana memoria) sono dovute alle istruzioni che modificano le info.

Ricapitolando, lo stato di evo della computazione' è l'insieme dei valori di tutte le informazioni da cui dipende l'esito della computazione del processo. Se modifico sti valori, l'esito finale cambia (a meno che, ovviamente, il mio programma non usi i dati in input, ma allora la sua utilità sarebbe quantomeno dubbia:).

Se il mio obiettivo è realizzare il multitasking, serve che, quando salto da un processo all'altro, lo stato di evo della comp. di ciascun processo venga salvato e ripristinato successivamente quando ritorno allo stesso processo. Come si fa? Beh, la memoria di ciascun processo abbiamo detto che è stata assegnata a lui e il SO non permette a nessun altro di toccarla, quindi di quella possiamo anche non preoccuparci. I registri invece vengono usati da tutti, quindi occorre salvarli da qualche parte per poi recuperarli. In genere i processori hanno delle istruzioni di PUSH ALL che salvano in un botto solo tutti i registri (anche quelli che il mio processo non usa, perché tanto ci metto meno a salvarli tutti che a star lì a decidere quali sì e quali no, e lo faccio con 1 solo fetch).

Lo stack pointer non può essere salvato nello stack, perché punterebbe a se stesso. Va salvato quindi in una particolare tabella mantenuta dal SO.

Se voglio riattivare quel dato processo, cerco lo stack pointer nella mia tabella, e da lì recupero i valori dei registri e del program counter, e riparto da dove mi ero fermato prima.

Uso del processore da parte del processo

Il processo, rispetto al processore, può trovarsi in uno di questi stati:

  1. può usarlo;
  2. può attendere perché il processore è impegnato;
  3. è costretto a rimandare perché non ha tutte le risorse che gli servono.

Ecco che vediamo che lo stato del processo è lo stato di uso del processore da parte del processo, e formalmente è uno di questi:

  • new: è stato creato e inizializzato;
  • running: sta andando regolarmente;
  • waiting: è in attesa delle risorse che vorrebbe
  • ready to run: ha tutte le risorse, e aspetta di essere chiamato;
  • terminated: lui ha finito, spetta al SO liberare le risorse che utilizzava e rimuoverlo dalla memoria (non sempre immediatamente).

Per distinguere un processo dagli altri, si usa una roba chiamata Process Control Block, che tiene traccia di diverse cose relative al processo:

  • il suo id;
  • lo stato;
  • il program counter;
  • i registro;
  • le info per lo scheduling (che è? vedremo...);
  • i confini della memoria riservata al processo;
  • lo stato di I/O;
  • l'accounting (i vari permessi).

Cmq non tutti i SO tengono traccia di tutte ste cose per ogni processo.

Quando un processo è pronto, è nella coda dei processi pronti, che in base allo scheduling (che vedremo poi) viene svuotata. Ma in generale se un processo ha bisogno di un certo I/O, può far parte anche della coda dell'I/O. Il SO deve quindi gestire queste code in modo efficiente.

Torna alla pagina di SO