User Tools

Site Tools


progsys:index

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
Last revisionBoth sides next revision
progsys:index [2018/01/16 10:00] – [Envoyer & Recevoir Signaux] orelprogsys:index [2020/11/06 11:14] – [Ctrl-C] orel
Line 790: Line 790:
     int k = atoi(argv[1]);     int k = atoi(argv[1]);
  
-    for(int s = ; s < argc ; s++)+    for(int s = ; s < argc ; s++)
       for(int i = 0 ; i < k ; i++) {       for(int i = 0 ; i < k ; i++) {
  kill(ppid, atoi(argv[s])); // envoi signal  kill(ppid, atoi(argv[s])); // envoi signal
Line 809: Line 809:
     sigemptyset(&act.sa_mask);     sigemptyset(&act.sa_mask);
      
-    for(int sig = ; sig < NSIGNORT ; sig++) {+    for(int sig = ; sig < NSIGNORT ; sig++) {
       sigaction(sig, &act, NULL);       sigaction(sig, &act, NULL);
       tab[sig] = 0;       tab[sig] = 0;
Line 920: Line 920:
 </code> </code>
  
-==== Open Pipe Command ====+==== Open Pipe Command (exo 3, DS 2017-2018) ====
  
-//Le fils bombarde son père de signaux. Voici une version incomplète à modifier, car on perd des signaux !!! Il faut mettre en place un système d'acquitement des signaux du père vers le fils (signal SIGUSR1).//+On souhaite disposer d’une fonction //open_pipe_command// dont le profil est :
  
-<code C open_pipe_command.c>+  int open_pipe_command (int *fd, char *cmd, char **argv)
  
-/* correction exo 3.1DS 2017-2018 */+Cette fonction crée un processus chargé d’exécuter la commande //cmd// avec les arguments //argv//, et renvoie deux descripteurs (dans le tableau fd) permettant respectivement d’écrire vers l’entrée standard de la commande (descripteur fd[1]) et de lire depuis la sortie standard de la commande (descripteur fd[0]). On utilisera pour cela deux tubes permettant d’établir une connexion bidirectionnelle avec le processus exécutant la commande. La fonction retournera le //pid// du processus fils exécutant la commande. 
 + 
 +<code C open_pipe_command.c>
 /* gcc -Wall -std=c99 open_pipe_command.c && ./a.out */ /* gcc -Wall -std=c99 open_pipe_command.c && ./a.out */
  
Line 975: Line 977:
 </code> </code>
  
 +==== Ctrl-C ====
 +
 +Un processus fils est dans le même PGID (process group ID) que son père par defaut (pgid père = pgid fils = pid père). Un kill sur -pid du père envoie le signal à tous le groupe, donc au fils également...
 +
 +<code C sigint.c>
 +#include <stdlib.h>
 +#include <stdio.h>
 +#include <unistd.h>
 +#include <signal.h>
 +#include <sys/types.h>
 +
 +void handler(int sig)
 +{
 +    printf("paf\n");
 +}
 +
 +int main(void)
 +{
 +    signal(SIGINT, handler); // TODO: utiliser sigaction() plutôt que signal() !
 +
 +    if (fork() == 0)
 +    {
 +        printf("child: %d %d\n", getpid(), getpgid(0));
 +        pause();
 +        printf("child: bye bye!\n");
 +        exit(EXIT_SUCCESS);
 +    }
 +
 +    printf("father: %d %d\n", getpid(), getpgid(0));
 +    pause();
 +    printf("father: bye bye!\n");
 +    return EXIT_SUCCESS;
 +}
 +</code>
 +
 +
 +==== Timeout ====
 +
 +<code C executer-avant-delai.c>
 +
 +#define _GNU_SOURCE
 +#include <unistd.h>
 +#include <signal.h>
 +#include <stdio.h>
 +#include <setjmp.h>
 +
 +static struct sigaction sa, old;
 +static sigjmp_buf env;
 +
 +static void myalarm(int sig)
 +{
 +  printf("alarm!\n");
 +  siglongjmp(env,1);
 +}
 +
 +int executer_avant_delai( void (*fun)(void *), void *parametre, int delai_en_seconde)
 +{
 +  int ret = 1;
 +  sa.sa_handler = myalarm;
 +  sa.sa_flags = 0; // SA_RESETHAND;
 +  sigemptyset(&sa.sa_mask);
 +  sigaction(SIGALRM, &sa, &old);
 +
 +  alarm(delai_en_seconde);
 +  if(sigsetjmp(env,1) == 0)
 +    fun(parametre);
 +  else
 +    ret = 0; // alarm
 +  alarm(0);
 +  sigaction(SIGALRM, &old, NULL);
 +  return ret;
 +}
 +</code>
progsys/index.txt · Last modified: 2024/03/18 15:06 by 127.0.0.1