SYS CALL viste a lezione.
- 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);
}
}
- EXECVE
Esegue un programma. La famiglia di funzioni exe() 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).
}
}
Correggetemi se ho scritto delle sciocchezze. (Pirata)