Difference between revisions of "SYS CALL viste a lezione."

From Sistemi Operativi
Jump to navigation Jump to search
Line 1: Line 1:
==FORK==
+
==Controllo processi==
 +
===FORK===
 
Crea un nuovo processo duplicando il processo chiamante. Il nuovo processo , chiamato figlio, é un duplicato esatto del processo chiamante , chiamato padre.  
 
Crea un nuovo processo duplicando il processo chiamante. Il nuovo processo , chiamato figlio, é un duplicato esatto del processo chiamante , chiamato padre.  
  
Line 56: Line 57:
  
  
==_EXIT==
+
===_EXIT===
 
Termina il proceso chiamante.
 
Termina il proceso chiamante.
  
Line 95: Line 96:
  
  
==WAIT==
+
===WAIT===
 
Aspetta che un processo cambi di stato.
 
Aspetta che un processo cambi di stato.
  
Line 156: Line 157:
  
  
==EXEC==
+
===EXEC===
 
Esegue un programma.
 
Esegue un programma.
 
La famiglia di funzioni exec() rimpiazza l'immagine del processo corrente con l'immagine di un nuovo processo.
 
La famiglia di funzioni exec() rimpiazza l'immagine del processo corrente con l'immagine di un nuovo processo.

Revision as of 16:46, 20 November 2013

Controllo processi

FORK

Crea un nuovo processo duplicando il processo chiamante. Il nuovo processo , chiamato figlio, é un duplicato esatto del processo chiamante , chiamato padre.

esempio1:

#include <stdio.h>
#include <unistd.h>

void main (void){     
	if(fork()){
	printf("uno  %d  %d \n", getpid(), getppid() ); // getpid() stampa il pid del processo corrente , getppid() stampa il pid del processo padre
        sleep(2);}   //se togliessimo lo sleep;il processo figlio stamperebbe come getppid() 1,perché essendo il padre terminato e lui rimasto orfano,il nuovo padre diventa init
	else
	printf("due %d %d  \n",getpid(), getppid() );
}

esempio2(una piccola osservazione sull'eredità del buffer):

#include <stdio.h>
#include <unistd.h>

void main (void){
	printf("cucù! : ");      //notare la differenza se nella sringa metto \n 
	if(fork())
	printf("uno  %d  %d \n", getpid(), getppid() );
	else
	printf("due %d %d  \n",getpid(), getppid() );
}

esempio3(fork e malloc):
(sottolineerei che lo spazio di indirizzamento è di fatto separato: i due processi hanno una analoga visione dell'indirizzamento logico, che però è specifico di ogni processo e i dati sono memorizzati fisicamente in aree di memoria diverse. am_20131110)

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>


void main (void){
	int *p;
	if( fork() ){
	p = malloc(sizeof(int));
	*p = 45;
	printf("%d %p  pid : %d  , ppid : %d \n",*p,p,getpid(),getppid());   
	sleep(2);
	}
	else {
	p = malloc(sizeof(int));
	printf("%d %p  pid : %d  , ppid : %d \n",*p,p,getpid(),getppid());  //i puntatori restituiranno lo stesso indirizzo di memoria sia per il padre che per il figlio         
	sleep(1);                                                           //perché condividono lo stesso spazio di indirizzamento
	}
}


_EXIT

Termina il proceso chiamante.

esempio1:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>

int main (int argc,char *argv[]){
	_exit(0);                     //Sys call che termina il processo chiamante
}

esempio2(atexit):

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>

void at1(void){
	printf("at1 \n");
	}

void at2(void){
	printf("at2 \n");
	}


int main (int argc,char *argv[]){
	printf("brutal kill \n");
	atexit(at1);	//funzione di libreria che termina il processo passato come argomento
	atexit(at2); 
}

//le funzioni passate ad atexit vengono eseguite in modo inverso rispetto all'invocazione


WAIT

Aspetta che un processo cambi di stato.

esempio1:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>

int main (int argc, char *argv[]){
	pid_t pid;
	if( pid = fork() ){
		int status;
		printf(" padre : %d  figlio : %d \n",getpid(),pid);
                sleep(10); 
		waitpid(pid,&status,0);
		printf(" exit status %d \n",WEXITSTATUS(status)); //Macro che restituisce l' exit status del figlio,cioè gli otto bit meno significativi dello status che il figlio
	}                                                         //specifica in una chiamata di _exit o exit o come argomento di ritorno del main.
	else {
		printf(" figlio : %d  padre : %d \n",getpid(),getppid());
		sleep(1);
		exit(1);
		}
}


esempio2:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>

int main (int argc, char *argv[]){
	pid_t pid;
	if( pid = fork() ){
		int status;
		printf(" padre : %d  figlio : %d \n",getpid(),pid);
		sleep(5);
		waitpid(pid,&status,0);
		if (WIFEXITED(status)) //Macro che restituisce true se il figlio termina normalmente, cioé chiamando _exit o exit oppure tramite il return del main
		printf(" exit status %d \n", WEXITSTATUS(status));
		else if(WIFSIGNALED(status) )  //Macro che restituisce true se il figlio é terminato da un segnale
			printf("signal : %d \n", WTERMSIG(status) );  //Macro che restituisce il numero del segnale che causa la terminazione del processo figlio
	}
	else {
		int *p;
		printf(" figlio : %d  padre : %d \n",getpid(),getppid());
		sleep(1);
		p = (int *)42;
		*p = 43;	
		exit(2);
		}
}


EXEC

Esegue un programma. La famiglia di funzioni exec() rimpiazza l'immagine del processo corrente con l'immagine di un nuovo processo.

esempio1:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>

int main (int argc, char *argv[]){
	pid_t pid;
	if( pid = fork() ){
		int status;
		printf(" padre : %d  figlio : %d \n",getpid(),pid);
		sleep(5);
		waitpid(pid,&status,0);
		if (WIFEXITED(status)) 
		printf(" exit status %d \n", WEXITSTATUS(status));
		else if( WIFSIGNALED(status) )  
			printf("signal : %d \n", WTERMSIG(status) ); 
	}
	else {
		char *args[] = {"ls","-l",(char *)0};
		execvp("ls",args); //funzione di libreria che prende in input il path(p) e un vettore(v).
	}
}

esempio2:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>

int main (int argc, char *argv[]){
	pid_t pid;
	if( pid = fork() ){
		int status;
		printf(" padre : %d  figlio : %d %s \n",getpid(),pid,argv[1]);
		sleep(5);
		waitpid(pid,&status,0);
		if (WIFEXITED(status)) 
		printf(" exit status %d \n", WEXITSTATUS(status));
		else if( WIFSIGNALED(status) )  
			printf("signal : %d \n", WTERMSIG(status) ); 
	}
	else {
		execvp(argv[2],argv+2);
	}
}


Correggetemi se ho scritto delle sciocchezze. -Pirata-

Gestione File

  • int open(const char *path, int oflag, ...);
  • int creat(const char *path, mode_t mode);
  • int close(int filedes);
  • off_t lseek(int filedes, off_t offset, int whence);
  • ssize_t read(int filedes, void *buf, size_t nbyte);
  • ssize_t write(int filedes, const void *buf, size_t nbyte);

Qualche esempio? Iniziamo con i file "con il buco" visti a lezione?