--- rpl/src/instructions_d5.c 2011/09/14 17:55:59 1.68 +++ rpl/src/instructions_d5.c 2011/11/18 20:24:40 1.78 @@ -1,6 +1,6 @@ /* ================================================================================ - RPL/2 (R) version 4.1.3 + RPL/2 (R) version 4.1.4 Copyright (C) 1989-2011 Dr. BERTRAND Joël This file is part of RPL/2. @@ -814,8 +814,9 @@ instruction_der(struct_processus *s_etat void instruction_detach(struct_processus *s_etat_processus) { + int pipe_initialisation_segment_signaux[2]; + logical1 drapeau; - logical1 variable_partagee; pid_t ppid; pid_t pid_final; @@ -828,9 +829,6 @@ instruction_detach(struct_processus *s_e sig_atomic_t registre_stop; - sigset_t oldset; - sigset_t set; - ssize_t longueur_ecriture; struct_descripteur_thread *s_argument_thread; @@ -850,12 +848,15 @@ instruction_detach(struct_processus *s_e struct timespec attente; + unsigned char caractere; unsigned char *message; unsigned int erreur; unsigned long i; + volatile logical1 variable_partagee; + (*s_etat_processus).erreur_execution = d_ex; attente.tv_sec = 0; @@ -1085,6 +1086,12 @@ instruction_detach(struct_processus *s_e return; } + if (pipe(pipe_initialisation_segment_signaux) != 0) + { + (*s_etat_processus).erreur_systeme = d_es_processus; + return; + } + ppid = getpid(); /* @@ -1104,13 +1111,9 @@ instruction_detach(struct_processus *s_e * de mémoire, ni libération, ni copie d'objet concurrent au fork(). */ - sigfillset(&set); - pthread_sigmask(SIG_BLOCK, &set, &oldset); verrouillage_threads_concurrents(s_etat_processus); (*s_argument_thread).pid = fork(); deverrouillage_threads_concurrents(s_etat_processus); - pthread_sigmask(SIG_SETMASK, &oldset, NULL); - sigpending(&set); (*s_argument_thread).thread_pere = pthread_self(); (*s_argument_thread).processus_detache = d_vrai; @@ -1229,28 +1232,30 @@ instruction_detach(struct_processus *s_e return; } -# ifndef OS2 -# ifndef Cygwin +# ifdef SCHED_OTHER if (pthread_attr_setschedpolicy(&attributs, SCHED_OTHER) != 0) { (*s_etat_processus).erreur_systeme = d_es_processus; return; } +# endif +# ifdef PTHREAD_EXPLICIT_SCHED if (pthread_attr_setinheritsched(&attributs, PTHREAD_EXPLICIT_SCHED) != 0) { (*s_etat_processus).erreur_systeme = d_es_processus; return; } +# endif +# ifdef PTHREAD_SCOPE_SYSTEM if (pthread_attr_setscope(&attributs, PTHREAD_SCOPE_SYSTEM) != 0) { (*s_etat_processus).erreur_systeme = d_es_processus; return; } # endif -# endif (*s_argument_thread).s_etat_processus = s_etat_processus; @@ -1275,10 +1280,21 @@ instruction_detach(struct_processus *s_e liberation_queue_signaux(s_etat_processus); creation_queue_signaux(s_etat_processus); + routine_recursive = 0; (*s_etat_processus).pointeur_signal_lecture = 0; (*s_etat_processus).pointeur_signal_ecriture = 0; + if (write_atomic(s_etat_processus, + pipe_initialisation_segment_signaux[1], + "-", sizeof(unsigned char)) != sizeof(unsigned char)) + { + (*s_etat_processus).erreur_systeme = d_es_processus; + } + + close(pipe_initialisation_segment_signaux[0]); + close(pipe_initialisation_segment_signaux[1]); + if ((*s_etat_processus).debug == d_vrai) if (((*s_etat_processus).type_debug & d_debug_processus) != 0) @@ -2418,6 +2434,8 @@ instruction_detach(struct_processus *s_e nanosleep(&attente, NULL); pthread_mutex_lock(&((*s_etat_processus).mutex)); + + scrutation_interruptions(s_etat_processus); } pthread_mutex_unlock(&((*s_etat_processus).mutex)); @@ -2754,8 +2772,14 @@ instruction_detach(struct_processus *s_e pthread_mutex_destroy(&((*s_etat_processus).mutex_allocation)); pthread_mutex_destroy(&((*s_etat_processus).protection_liste_mutexes)); - pthread_mutex_unlock(&((*s_etat_processus).mutex_fork)); - pthread_mutex_destroy(&((*s_etat_processus).mutex_fork)); +# ifndef SEMAPHORES_NOMMES + sem_post(&((*s_etat_processus).semaphore_fork)); + sem_destroy(&((*s_etat_processus).semaphore_fork)); +# else + sem_post((*s_etat_processus).semaphore_fork); + sem_destroy3((*s_etat_processus).semaphore_fork, getpid(), + pthread_self(), SEM_FORK); +# endif free((*s_etat_processus).localisation); free(s_argument_thread); @@ -2822,6 +2846,7 @@ instruction_detach(struct_processus *s_e } } + scrutation_interruptions(s_etat_processus); l_element_courant = (*l_element_courant).suivant; } } while(drapeau == d_vrai); @@ -2841,25 +2866,24 @@ instruction_detach(struct_processus *s_e return; } - // Être sûr que le processus fils soit déjà présent... + // On attend une donnée fictive pour être sûr que le segment de mémoire + // partagée destiné à la gestion des signaux est bien initialisé. attente.tv_sec = 0; attente.tv_nsec = GRANULARITE_us * 1000; - while(kill((*s_argument_thread).pid, 0) != 0) + while(read_atomic(s_etat_processus, + pipe_initialisation_segment_signaux[0], + &caractere, sizeof(caractere)) == 0) { - //if ((errno != ESRCH) && (errno != EAGAIN)) - if (errno != ESRCH) - { - (*s_etat_processus).erreur_systeme = d_es_processus; - pthread_mutex_unlock(&((*s_etat_processus).mutex)); - return; - } - + scrutation_interruptions(s_etat_processus); nanosleep(&attente, NULL); INCR_GRANULARITE(attente.tv_nsec); } + close(pipe_initialisation_segment_signaux[0]); + close(pipe_initialisation_segment_signaux[1]); + // Le fils peut être présent sans être en attente du signal de départ. if (envoi_signal_processus((*s_argument_thread).pid, rpl_sigstart) != 0)