File:  [local] / rpl / src / gestion_threads.c
Revision 1.122: download - view: text, annotated - select for diffs - revision graph
Wed Jan 17 16:57:10 2024 UTC (3 months, 1 week ago) by bertrand
Branches: MAIN
CVS tags: HEAD
En route pour la 4.1.36.

    1: /*
    2: ================================================================================
    3:   RPL/2 (R) version 4.1.36
    4:   Copyright (C) 1989-2024 Dr. BERTRAND Joël
    5: 
    6:   This file is part of RPL/2.
    7: 
    8:   RPL/2 is free software; you can redistribute it and/or modify it
    9:   under the terms of the CeCILL V2 License as published by the french
   10:   CEA, CNRS and INRIA.
   11:  
   12:   RPL/2 is distributed in the hope that it will be useful, but WITHOUT
   13:   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   14:   FITNESS FOR A PARTICULAR PURPOSE.  See the CeCILL V2 License
   15:   for more details.
   16:  
   17:   You should have received a copy of the CeCILL License
   18:   along with RPL/2. If not, write to info@cecill.info.
   19: ================================================================================
   20: */
   21: 
   22: 
   23: #include "rpl-conv.h"
   24: 
   25: 
   26: /*
   27: ================================================================================
   28:   Fonction de lancement d'un thread
   29: ================================================================================
   30:   Entrées : pointeur sur une structure
   31: --------------------------------------------------------------------------------
   32:   Sorties :
   33: --------------------------------------------------------------------------------
   34:   Effets de bord : néant
   35: ================================================================================
   36: */
   37: 
   38: void *
   39: lancement_thread(void *argument)
   40: {
   41:     int                                 status;
   42: 
   43:     pid_t                               ppid;
   44: 
   45:     sig_atomic_t                        registre_stop;
   46: 
   47:     ssize_t                             longueur_ecriture;
   48: 
   49:     struct_descripteur_thread           *s_argument_thread;
   50: 
   51:     struct_liste_chainee                *l_element_courant;
   52:     struct_liste_chainee                *l_element_suivant;
   53: 
   54:     struct_liste_variables_statiques    *l_element_statique_courant;
   55:     struct_liste_variables_statiques    *l_element_statique_suivant;
   56: 
   57:     struct_objet                        *s_objet_temporaire;
   58: 
   59:     struct_processus                    *s_etat_processus;
   60: 
   61:     struct sigaction                    action;
   62:     struct sigaction                    registre;
   63: 
   64:     struct timespec                     attente;
   65: 
   66:     unsigned char                       caractere;
   67:     unsigned char                       *message;
   68: 
   69:     unsigned int                        erreur;
   70: 
   71:     integer8                            i;
   72: 
   73:     attente.tv_sec = 0;
   74:     attente.tv_nsec = GRANULARITE_us * 1000;
   75: 
   76:     s_argument_thread = (struct_descripteur_thread *) argument;
   77:     s_etat_processus = (*s_argument_thread).s_nouvel_etat_processus;
   78: 
   79: #   ifndef SEMAPHORES_NOMMES
   80:         if (sem_init(&((*s_etat_processus).semaphore_fork), 0, 0) != 0)
   81: #   else
   82:         if (((*s_etat_processus).semaphore_fork = sem_init3(0, getpid(),
   83:                 pthread_self(), SEM_FORK)) == SEM_FAILED)
   84: #   endif
   85:     {
   86:         (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
   87:         pthread_exit(NULL);
   88:     }
   89: 
   90:     (*s_argument_thread).tid = pthread_self();
   91:     insertion_thread(s_etat_processus, d_faux);
   92: 
   93:     if (pthread_mutex_lock(&((*s_argument_thread).mutex)) != 0)
   94:     {
   95:         (*s_etat_processus).erreur_systeme = d_es_processus;
   96:         pthread_exit(NULL);
   97:     }
   98: 
   99:     (*s_argument_thread).thread_actif = d_vrai;
  100: 
  101:     if (pthread_mutex_unlock(&((*s_argument_thread).mutex)) != 0)
  102:     {
  103:         (*s_etat_processus).erreur_systeme = d_es_processus;
  104:         pthread_exit(NULL);
  105:     }
  106: 
  107:     // Envoi d'une donnée pour signaler le démarrage du thread au thread
  108:     // de surveillance.
  109: 
  110:     caractere = 0;
  111: 
  112:     if (write_atomic(s_etat_processus,
  113:             (*s_argument_thread).pipe_nombre_elements_attente[1],
  114:             &caractere, sizeof(caractere)) != sizeof(caractere))
  115:     {
  116:         (*s_etat_processus).erreur_systeme = d_es_processus;
  117: 
  118:         pthread_mutex_lock(&((*s_argument_thread).mutex));
  119:         pthread_mutex_unlock(&((*s_argument_thread).mutex));
  120: 
  121:         (*s_argument_thread).thread_actif = d_faux;
  122: 
  123:         while((longueur_ecriture = write_atomic(s_etat_processus,
  124:                 (*s_argument_thread).pipe_nombre_elements_attente[1],
  125:                 &caractere, sizeof(caractere))) != sizeof(caractere))
  126:         {
  127:             if (longueur_ecriture == -1)
  128:             {
  129:                 break;
  130:             }
  131:         }
  132: 
  133:         pthread_exit(NULL);
  134:     }
  135: 
  136:     if ((*s_etat_processus).evaluation_expression_compilee == 'N')
  137:     {
  138:         free((*s_etat_processus).instruction_courante);
  139:         (*s_etat_processus).instruction_courante = NULL;
  140:     }
  141: 
  142:     // Attente de la réception du signal rpl_sigstart.
  143: 
  144:     for((*s_etat_processus).demarrage_fils = d_faux;;)
  145:     {
  146:         scrutation_interruptions(s_etat_processus);
  147: 
  148:         if ((*s_etat_processus).demarrage_fils == d_vrai)
  149:         {
  150:             break;
  151:         }
  152: 
  153:         if (sem_post(&((*s_etat_processus).semaphore_fork)) != 0)
  154:         {
  155:             (*s_etat_processus).erreur_systeme = d_es_processus;
  156:             pthread_exit(NULL);
  157:         }
  158: 
  159:         nanosleep(&attente, NULL);
  160: 
  161:         while(sem_wait(&((*s_etat_processus).semaphore_fork)) != 0)
  162:         {
  163:             if (errno != EINTR)
  164:             {
  165:                 (*s_etat_processus).erreur_systeme = d_es_processus;
  166:                 pthread_exit(NULL);
  167:             }
  168:         }
  169:     }
  170: 
  171:     if ((*s_etat_processus).debug == d_vrai)
  172:         if (((*s_etat_processus).type_debug & d_debug_processus) != 0)
  173:     {
  174:         if ((*s_etat_processus).langue == 'F')
  175:         {
  176:             printf("[%d] Lancement du thread %llu\n", (int) getpid(),
  177:                     (unsigned long long) pthread_self());
  178:         }
  179:         else
  180:         {
  181:             printf("[%d] Start thread %llu\n", (int) getpid(),
  182:                     (unsigned long long) pthread_self());
  183:         }
  184: 
  185:         fflush(stdout);
  186:     }
  187: 
  188:     (*s_etat_processus).pid_erreur_processus_fils = getpid();
  189: 
  190:     // Évaluation de l'objet
  191: 
  192:     if ((*s_etat_processus).erreur_systeme == d_es)
  193:     {
  194:         if (setjmp(contexte_thread) == 0)
  195:         {
  196:             if (evaluation(s_etat_processus, (*s_argument_thread).argument, 'E')
  197:                     == d_erreur)
  198:             {
  199:                 if (((*s_etat_processus).erreur_execution == d_ex) &&
  200:                         ((*s_etat_processus).erreur_systeme == d_es))
  201:                 {
  202:                     (*s_etat_processus).erreur_execution =
  203:                             d_ex_erreur_evaluation;
  204:                 }
  205:             }
  206:             else
  207:             {
  208:                 if (((*s_etat_processus).arret_depuis_abort == 0)
  209:                         && ((*s_etat_processus).at_exit != NULL))
  210:                 {
  211:                     (*s_etat_processus).var_volatile_requete_arret = 0;
  212:                     (*s_etat_processus).var_volatile_alarme = 0;
  213:                     (*s_etat_processus).var_volatile_traitement_sigint = 0;
  214: 
  215:                     if ((*s_etat_processus).profilage == d_vrai)
  216:                     {
  217:                         profilage(s_etat_processus, "ATEXIT");
  218:                     }
  219: 
  220:                     if (evaluation(s_etat_processus,
  221:                             (*s_etat_processus).at_exit, 'E') == d_erreur)
  222:                     {
  223:                         if (((*s_etat_processus).erreur_execution == d_ex) &&
  224:                                 ((*s_etat_processus).erreur_systeme == d_es))
  225:                         {
  226:                             (*s_etat_processus).erreur_execution =
  227:                                     d_ex_erreur_evaluation;
  228:                         }
  229:                     }
  230: 
  231:                     if ((*s_etat_processus).profilage == d_vrai)
  232:                     {
  233:                         profilage(s_etat_processus, NULL);
  234:                     }
  235:                 }
  236:             }
  237:         }
  238: 
  239:         if ((*s_argument_thread).destruction_objet == d_vrai)
  240:         {
  241:             liberation(s_etat_processus, (*s_argument_thread).argument);
  242:         }
  243:     }
  244: 
  245:     if ((*s_etat_processus).presence_fusible == d_vrai)
  246:     {
  247:         pthread_cancel((*s_etat_processus).thread_fusible);
  248:     }
  249: 
  250:     caractere = 0;
  251: 
  252:     while((longueur_ecriture = write_atomic(s_etat_processus,
  253:             (*s_argument_thread).pipe_nombre_elements_attente[1],
  254:             &caractere, sizeof(caractere))) != sizeof(caractere))
  255:     {
  256:         if (longueur_ecriture == -1)
  257:         {
  258:             break;
  259:         }
  260:     }
  261: 
  262:     if ((*s_etat_processus).var_volatile_processus_pere != 0)
  263:     {
  264:         // Racine des processus atteinte
  265: 
  266:         erreur = d_ex;
  267: 
  268:         while((longueur_ecriture = write_atomic(s_etat_processus,
  269:                 (*s_argument_thread).pipe_erreurs[1], &erreur,
  270:                 sizeof((*s_etat_processus).erreur_execution))) !=
  271:                 sizeof((*s_etat_processus).erreur_execution))
  272:         {
  273:             if (longueur_ecriture == -1)
  274:             {
  275:                 break;
  276:             }
  277:         }
  278:     }
  279:     else
  280:     {
  281:         while((longueur_ecriture = write_atomic(s_etat_processus,
  282:                 (*s_argument_thread).pipe_erreurs[1],
  283:                 (int *) &((*s_etat_processus).erreur_execution),
  284:                 sizeof((*s_etat_processus).erreur_execution))) !=
  285:                 sizeof((*s_etat_processus).erreur_execution))
  286:         {
  287:             if (longueur_ecriture == -1)
  288:             {
  289:                 break;
  290:             }
  291:         }
  292:     }
  293: 
  294:     if ((*s_etat_processus).var_volatile_processus_pere != 0)
  295:     {
  296:         // Racine des processus atteinte
  297: 
  298:         erreur = d_es;
  299: 
  300:         while((longueur_ecriture = write_atomic(s_etat_processus,
  301:                 (*s_argument_thread).pipe_erreurs[1], &erreur,
  302:                 sizeof((*s_etat_processus).erreur_systeme))) !=
  303:                 sizeof((*s_etat_processus).erreur_systeme))
  304:         {
  305:             if (longueur_ecriture == -1)
  306:             {
  307:                 break;
  308:             }
  309:         }
  310:     }
  311:     else
  312:     {
  313:         while((longueur_ecriture = write_atomic(s_etat_processus,
  314:                 (*s_argument_thread).pipe_erreurs[1],
  315:                 (int *) &((*s_etat_processus).erreur_systeme),
  316:                 sizeof((*s_etat_processus).erreur_systeme))) !=
  317:                 sizeof((*s_etat_processus).erreur_systeme))
  318:         {
  319:             if (longueur_ecriture == -1)
  320:             {
  321:                 break;
  322:             }
  323:         }
  324:     }
  325: 
  326:     if ((*s_etat_processus).pid_erreur_processus_fils == 0)
  327:     {
  328:         ppid = getpid();
  329: 
  330:         while((longueur_ecriture = write_atomic(s_etat_processus,
  331:                 (*s_argument_thread).pipe_erreurs[1],
  332:                 &ppid, sizeof(ppid))) != sizeof(ppid))
  333:         {
  334:             if (longueur_ecriture == -1)
  335:             {
  336:                 break;
  337:             }
  338:         }
  339:     }
  340:     else
  341:     {
  342:         while((longueur_ecriture = write_atomic(s_etat_processus,
  343:                 (*s_argument_thread).pipe_erreurs[1],
  344:                 &((*s_etat_processus).pid_erreur_processus_fils),
  345:                 sizeof((*s_etat_processus).pid_erreur_processus_fils))) !=
  346:                 sizeof((*s_etat_processus).pid_erreur_processus_fils))
  347:         {
  348:             if (longueur_ecriture == -1)
  349:             {
  350:                 break;
  351:             }
  352:         }
  353:     }
  354: 
  355:     l_element_courant = (*s_etat_processus).s_fichiers;
  356: 
  357:     while(l_element_courant != NULL)
  358:     {
  359:         l_element_suivant = (*l_element_courant).suivant;
  360: 
  361:         if (((*((struct_descripteur_fichier *) (*l_element_courant)
  362:                 .donnee)).pid == getpid()) &&
  363:                 ((*((struct_descripteur_fichier *) (*l_element_courant)
  364:                 .donnee)).tid == pthread_self()))
  365:         {
  366:             fclose((*((struct_descripteur_fichier *)
  367:                     (*l_element_courant).donnee)).descripteur_c);
  368: 
  369:             if ((*((struct_descripteur_fichier *)
  370:                     (*l_element_courant).donnee)).type != 'C')
  371:             {
  372:                 sqlite3_close((*((struct_descripteur_fichier *)
  373:                         (*l_element_courant).donnee)).descripteur_sqlite);
  374:             }
  375: 
  376:             if ((*((struct_descripteur_fichier *) (*l_element_courant)
  377:                     .donnee)).effacement == 'Y')
  378:             {
  379:                 unlink((*((struct_descripteur_fichier *)
  380:                         (*l_element_courant).donnee)).nom);
  381:             }
  382:         }
  383: 
  384:         free((*((struct_descripteur_fichier *) (*l_element_courant)
  385:                 .donnee)).nom);
  386:         free((struct_descripteur_fichier *) (*l_element_courant).donnee);
  387:         free(l_element_courant);
  388: 
  389:         l_element_courant = l_element_suivant;
  390:     }
  391: 
  392:     pthread_mutex_lock(&((*s_etat_processus).mutex_pile_processus));
  393: 
  394:     l_element_courant = (struct_liste_chainee *)
  395:             (*s_etat_processus).l_base_pile_processus;
  396: 
  397:     while(l_element_courant != NULL)
  398:     {
  399:         if ((*(*((struct_processus_fils *) (*(*l_element_courant).donnee)
  400:                 .objet)).thread).processus_detache == d_vrai)
  401:         {
  402:             if ((*s_etat_processus).debug == d_vrai)
  403:             {
  404:                 if (((*s_etat_processus).type_debug & d_debug_processus) != 0)
  405:                 {
  406:                     if ((*s_etat_processus).langue == 'F')
  407:                     {
  408:                         printf("[%d] Signalement pour arrêt du processus %d\n",
  409:                                 (int) getpid(),
  410:                                 (int) (*(*((struct_processus_fils *)
  411:                                 (*(*l_element_courant).donnee).objet)).thread)
  412:                                 .pid);
  413:                     }
  414:                     else
  415:                     {
  416:                         printf("[%d] Send stop signal to process %d\n",
  417:                                 (int) getpid(),
  418:                                 (int) (*(*((struct_processus_fils *)
  419:                                 (*(*l_element_courant).donnee).objet)).thread)
  420:                                 .pid);
  421:                     }
  422:                 }
  423:             }
  424: 
  425:             if ((*s_etat_processus).var_volatile_alarme != 0)
  426:             {
  427:                 envoi_signal_processus((*(*((struct_processus_fils *)
  428:                         (*(*l_element_courant)
  429:                         .donnee).objet)).thread).pid, rpl_sigurg, d_faux);
  430:             }
  431:             else
  432:             {
  433:                 if ((*s_etat_processus).arret_depuis_abort == -1)
  434:                 {
  435:                     envoi_signal_processus((*(*((struct_processus_fils *)
  436:                             (*(*l_element_courant)
  437:                             .donnee).objet)).thread).pid, rpl_sigabort, d_faux);
  438:                 }
  439:                 else
  440:                 {
  441:                     envoi_signal_processus((*(*((struct_processus_fils *)
  442:                             (*(*l_element_courant)
  443:                             .donnee).objet)).thread).pid, rpl_sigstop,d_faux);
  444:                 }
  445:             }
  446:         }
  447:         else
  448:         {
  449:             if ((*s_etat_processus).debug == d_vrai)
  450:             {
  451:                 if (((*s_etat_processus).type_debug & d_debug_processus) != 0)
  452:                 {
  453:                     if ((*s_etat_processus).langue == 'F')
  454:                     {
  455:                         printf("[%d] Signalement pour arrêt du thread %llu\n",
  456:                                 (int) getpid(), (unsigned long long)
  457:                                 (*(*((struct_processus_fils *)
  458:                                 (*(*l_element_courant).donnee).objet)).thread)
  459:                                 .tid);
  460:                     }
  461:                     else
  462:                     {
  463:                         printf("[%d] Send stop signal to thread %llu\n",
  464:                                 (int) getpid(), (unsigned long long)
  465:                                 (*(*((struct_processus_fils *)
  466:                                 (*(*l_element_courant).donnee).objet)).thread)
  467:                                 .tid);
  468:                     }
  469:                 }
  470:             }
  471: 
  472:             if ((*s_etat_processus).var_volatile_alarme != 0)
  473:             {
  474:                 if (pthread_mutex_lock(&((*(*((struct_processus_fils *)
  475:                         (*(*l_element_courant).donnee).objet)).thread).mutex))
  476:                         != 0)
  477:                 {
  478:                     pthread_mutex_unlock(&((*s_etat_processus)
  479:                             .mutex_pile_processus));
  480:                     (*s_etat_processus).erreur_systeme = d_es_processus;
  481: 
  482:                     pthread_mutex_lock(&((*s_argument_thread).mutex));
  483:                     pthread_mutex_unlock(&((*s_argument_thread).mutex));
  484: 
  485:                     (*s_argument_thread).thread_actif = d_faux;
  486: 
  487:                     pthread_exit(NULL);
  488:                 }
  489: 
  490:                 if ((*(*((struct_processus_fils *)
  491:                         (*(*l_element_courant).donnee).objet)).thread)
  492:                         .thread_actif == d_vrai)
  493:                 {
  494:                     envoi_signal_thread(NULL,
  495:                             (*(*((struct_processus_fils *)
  496:                             (*(*l_element_courant).donnee).objet)).thread).tid,
  497:                             rpl_sigurg);
  498:                 }
  499: 
  500:                 if (pthread_mutex_unlock(&((*(*((struct_processus_fils *)
  501:                         (*(*l_element_courant).donnee).objet)).thread)
  502:                         .mutex)) != 0)
  503:                 {
  504:                     pthread_mutex_unlock(&((*s_etat_processus)
  505:                             .mutex_pile_processus));
  506:                     (*s_etat_processus).erreur_systeme = d_es_processus;
  507: 
  508:                     pthread_mutex_lock(&((*s_argument_thread).mutex));
  509:                     pthread_mutex_unlock(&((*s_argument_thread).mutex));
  510: 
  511:                     (*s_argument_thread).thread_actif = d_faux;
  512: 
  513:                     pthread_exit(NULL);
  514:                 }
  515:             }
  516:             else
  517:             {
  518:                 if (pthread_mutex_lock(&((*(*((struct_processus_fils *)
  519:                         (*(*l_element_courant).donnee).objet)).thread).mutex))
  520:                         != 0)
  521:                 {
  522:                     pthread_mutex_unlock(&((*s_etat_processus)
  523:                             .mutex_pile_processus));
  524:                     (*s_etat_processus).erreur_systeme = d_es_processus;
  525: 
  526:                     pthread_mutex_lock(&((*s_argument_thread).mutex));
  527:                     pthread_mutex_unlock(&((*s_argument_thread).mutex));
  528: 
  529:                     (*s_argument_thread).thread_actif = d_faux;
  530: 
  531:                     pthread_exit(NULL);
  532:                 }
  533: 
  534:                 if ((*(*((struct_processus_fils *)
  535:                         (*(*l_element_courant).donnee).objet)).thread)
  536:                         .thread_actif == d_vrai)
  537:                 {
  538:                     if ((*s_etat_processus).arret_depuis_abort == -1)
  539:                     {
  540:                         envoi_signal_thread(NULL,
  541:                                 (*(*((struct_processus_fils *)
  542:                                 (*(*l_element_courant).donnee).objet)).thread)
  543:                                 .tid, rpl_sigabort);
  544:                     }
  545:                     else
  546:                     {
  547:                         envoi_signal_thread(NULL,
  548:                                 (*(*((struct_processus_fils *)
  549:                                 (*(*l_element_courant).donnee).objet)).thread)
  550:                                 .tid, rpl_sigstop);
  551:                     }
  552:                 }
  553: 
  554:                 if (pthread_mutex_unlock(&((*(*((struct_processus_fils *)
  555:                         (*(*l_element_courant).donnee).objet)).thread).mutex))
  556:                         != 0)
  557:                 {
  558:                     pthread_mutex_unlock(&((*s_etat_processus)
  559:                             .mutex_pile_processus));
  560:                     (*s_etat_processus).erreur_systeme = d_es_processus;
  561: 
  562:                     pthread_mutex_lock(&((*s_argument_thread).mutex));
  563:                     pthread_mutex_unlock(&((*s_argument_thread).mutex));
  564: 
  565:                     (*s_argument_thread).thread_actif = d_faux;
  566: 
  567:                     pthread_exit(NULL);
  568:                 }
  569:             }
  570:         }
  571: 
  572:         l_element_courant = (*l_element_courant).suivant;
  573:     }
  574: 
  575:     /*
  576:      * Attente de la fin de tous les processus fils
  577:      */
  578: 
  579:     for(i = 0; i < d_NOMBRE_INTERRUPTIONS;
  580:             (*s_etat_processus).masque_interruptions[i++] = 'I');
  581: 
  582:     attente.tv_sec = 0;
  583:     attente.tv_nsec = GRANULARITE_us * 1000;
  584: 
  585:     while((*s_etat_processus).l_base_pile_processus != NULL)
  586:     {
  587:         status = 0;
  588: 
  589:         l_element_courant = (struct_liste_chainee *)
  590:                 (*s_etat_processus).l_base_pile_processus;
  591: 
  592:         registre_stop = (*s_etat_processus)
  593:                 .var_volatile_traitement_retarde_stop;
  594:         (*s_etat_processus).var_volatile_traitement_retarde_stop = 1;
  595: 
  596:         for(i = 0; i < (*(*((struct_processus_fils *)
  597:                 (*(*l_element_courant).donnee).objet)).thread)
  598:                 .nombre_objets_dans_pipe; i++)
  599:         {
  600:             if ((s_objet_temporaire = lecture_pipe(s_etat_processus,
  601:                     (*(*((struct_processus_fils *) (*(*l_element_courant)
  602:                     .donnee).objet)).thread).pipe_objets[0])) != NULL)
  603:             {
  604:                 liberation(s_etat_processus, s_objet_temporaire);
  605: 
  606:                 (*(*((struct_processus_fils *) (*(*l_element_courant)
  607:                         .donnee).objet)).thread).nombre_objets_dans_pipe--;
  608: 
  609:                 if (pthread_mutex_lock(&mutex_sigaction) != 0)
  610:                 {
  611:                     (*s_etat_processus).erreur_systeme = d_es_processus;
  612:                     pthread_exit(NULL);
  613:                 }
  614: 
  615:                 action.sa_handler = SIG_IGN;
  616:                 action.sa_flags = 0;
  617: 
  618:                 if (sigaction(SIGPIPE, &action, &registre) != 0)
  619:                 {
  620:                     pthread_mutex_unlock(&mutex_sigaction);
  621:                     pthread_mutex_unlock(&((*s_etat_processus)
  622:                             .mutex_pile_processus));
  623: 
  624:                     if (registre_stop == 0)
  625:                     {
  626:                         if ((*s_etat_processus)
  627:                                 .var_volatile_traitement_retarde_stop
  628:                                 == -1)
  629:                         {
  630:                             (*s_etat_processus)
  631:                                     .var_volatile_requete_arret = -1;
  632:                         }
  633: 
  634:                         (*s_etat_processus)
  635:                                 .var_volatile_traitement_retarde_stop =
  636:                                 registre_stop;
  637:                     }
  638: 
  639:                     (*s_etat_processus).erreur_systeme = d_es_signal;
  640:                     pthread_exit(NULL);
  641:                 }
  642: 
  643:                 while((longueur_ecriture = write_atomic(
  644:                         s_etat_processus, (*(*((struct_processus_fils *)
  645:                         (*(*l_element_courant).donnee).objet)).thread)
  646:                         .pipe_nombre_injections[1], "+",
  647:                         sizeof(unsigned char))) !=
  648:                         sizeof(unsigned char))
  649:                 {
  650:                     if (longueur_ecriture == -1)
  651:                     {
  652:                         // Le processus n'existe plus.
  653:                         break;
  654:                     }
  655:                 }
  656: 
  657:                 if (registre_stop == 0)
  658:                 {
  659:                     if ((*s_etat_processus)
  660:                             .var_volatile_traitement_retarde_stop == -1)
  661:                     {
  662:                         (*s_etat_processus).var_volatile_requete_arret
  663:                                 = -1;
  664:                     }
  665: 
  666:                     (*s_etat_processus)
  667:                             .var_volatile_traitement_retarde_stop =
  668:                             registre_stop;
  669:                 }
  670: 
  671:                 if (sigaction(SIGPIPE, &registre, NULL) != 0)
  672:                 {
  673:                     pthread_mutex_unlock(&mutex_sigaction);
  674:                     pthread_mutex_unlock(&((*s_etat_processus)
  675:                             .mutex_pile_processus));
  676: 
  677:                     (*s_etat_processus).erreur_systeme = d_es_signal;
  678:                     pthread_exit(NULL);
  679:                 }
  680: 
  681:                 if (pthread_mutex_unlock(&mutex_sigaction) != 0)
  682:                 {
  683:                     pthread_mutex_unlock(&((*s_etat_processus)
  684:                             .mutex_pile_processus));
  685: 
  686:                     (*s_etat_processus).erreur_systeme = d_es_signal;
  687:                     pthread_exit(NULL);
  688:                 }
  689:             }
  690:         }
  691: 
  692:         if ((*(*((struct_processus_fils *) (*(*l_element_courant)
  693:                 .donnee).objet)).thread).processus_detache == d_vrai)
  694:         {
  695:             if (waitpid((*(*((struct_processus_fils *)
  696:                     (*(*l_element_courant).donnee).objet)).thread).pid,
  697:                     &status, WNOHANG) < 0)
  698:             {
  699:             }
  700:         }
  701: 
  702:         if (pthread_mutex_lock(&((*s_etat_processus).mutex_interruptions)) != 0)
  703:         {
  704:             pthread_mutex_unlock(&((*s_etat_processus).mutex_pile_processus));
  705: 
  706:             (*s_etat_processus).erreur_systeme = d_es_processus;
  707:             pthread_exit(NULL);
  708:         }
  709: 
  710:         if ((*s_etat_processus).nombre_interruptions_non_affectees != 0)
  711:         {
  712:             affectation_interruptions_logicielles(s_etat_processus);
  713:         }
  714: 
  715:         if (pthread_mutex_unlock(&((*s_etat_processus).mutex_interruptions))
  716:                 != 0)
  717:         {
  718:             pthread_mutex_unlock(&((*s_etat_processus).mutex_pile_processus));
  719: 
  720:             (*s_etat_processus).erreur_systeme = d_es_processus;
  721:             pthread_exit(NULL);
  722:         }
  723: 
  724:         pthread_mutex_unlock(&((*s_etat_processus).mutex_pile_processus));
  725:         nanosleep(&attente, NULL);
  726:         pthread_mutex_lock(&((*s_etat_processus).mutex_pile_processus));
  727:     }
  728: 
  729:     pthread_mutex_unlock(&((*s_etat_processus).mutex_pile_processus));
  730: 
  731:     l_element_courant = (*s_etat_processus).s_sockets;
  732: 
  733:     while(l_element_courant != NULL)
  734:     {
  735:         l_element_suivant = (*l_element_courant).suivant;
  736: 
  737:         /*
  738:          * Fermeture des sockets créées dans le processus courant.
  739:          */
  740: 
  741:         if (((*((struct_socket *) (*(*l_element_courant).donnee).objet))
  742:                 .pid == getpid()) && (pthread_equal((*((struct_socket *)
  743:                 (*(*l_element_courant).donnee).objet)).tid, pthread_self())
  744:                 != 0))
  745:         {
  746:             if ((*((struct_socket *) (*(*l_element_courant).donnee).objet))
  747:                     .socket_connectee == d_vrai)
  748:             {
  749:                 shutdown((*((struct_socket *) (*(*l_element_courant).donnee)
  750:                         .objet)).socket, SHUT_RDWR);
  751:             }
  752: 
  753:             close((*((struct_socket *) (*(*l_element_courant).donnee).objet))
  754:                     .socket);
  755: 
  756:             if ((*((struct_socket *) (*(*l_element_courant).donnee).objet))
  757:                     .effacement == 'Y')
  758:             {
  759:                 unlink((*((struct_socket *) (*(*l_element_courant).donnee)
  760:                         .objet)).adresse);
  761:             }
  762:         }
  763: 
  764:         liberation(s_etat_processus, (*((struct_liste_chainee *)
  765:                 l_element_courant)).donnee);
  766:         free(l_element_courant);
  767: 
  768:         l_element_courant = l_element_suivant;
  769:     }
  770: 
  771:     l_element_courant = (*s_etat_processus).s_connecteurs_sql;
  772: 
  773:     while(l_element_courant != NULL)
  774:     {
  775:         l_element_suivant = (*l_element_courant).suivant;
  776: 
  777:         /*
  778:          * Fermeture des connecteurs créés dans le processus courant.
  779:          */
  780: 
  781:         if (((*((struct_socket *) (*(*l_element_courant).donnee).objet))
  782:                 .pid == getpid()) && (pthread_equal((*((struct_socket *)
  783:                 (*(*l_element_courant).donnee).objet)).tid, pthread_self())
  784:                 != 0))
  785:         {
  786:             sqlclose((*l_element_courant).donnee);
  787:         }
  788: 
  789:         liberation(s_etat_processus, (*((struct_liste_chainee *)
  790:                 l_element_courant)).donnee);
  791:         free(l_element_courant);
  792: 
  793:         l_element_courant = l_element_suivant;
  794:     }
  795: 
  796:     if ((((*s_etat_processus).erreur_execution != d_ex) ||
  797:             ((*s_etat_processus).exception != d_ep) ||
  798:             ((*s_etat_processus).erreur_systeme != d_es)) &&
  799:             ((*s_etat_processus).var_volatile_traitement_sigint == 0))
  800:     {
  801:         printf("%s [%d]\n", message =
  802:                 messages(s_etat_processus), (int) getpid());
  803:         free(message);
  804: 
  805:         if ((*s_etat_processus).core == d_vrai)
  806:         {
  807:             printf("\n");
  808: 
  809:             if ((*s_etat_processus).langue == 'F')
  810:             {
  811:                  printf("+++Information : Génération du fichier rpl-core "
  812:                         "[%d]\n", (int) getpid());
  813:             }
  814:             else
  815:             {
  816:                 printf("+++Information : Writing rpl-core file [%d]\n",
  817:                         (int) getpid());
  818:             }
  819: 
  820:             rplcore(s_etat_processus);
  821: 
  822:             if ((*s_etat_processus).langue == 'F')
  823:             {
  824:                 printf("+++Information : Processus tracé [%d]\n",
  825:                         (int) getpid());
  826:             }
  827:             else
  828:             {
  829:                 printf("+++Information : Done [%d]\n", (int) getpid());
  830:             }
  831: 
  832:             printf("\n");
  833:             fflush(stdout);
  834:         }
  835:     }
  836: 
  837:     if ((*s_etat_processus).entree_standard != NULL)
  838:     {
  839:         pclose((*s_etat_processus).entree_standard);
  840:         (*s_etat_processus).entree_standard = NULL;
  841:     }
  842: 
  843:     if ((*s_etat_processus).fichiers_graphiques != NULL)
  844:     {
  845:         instruction_cllcd(s_etat_processus);
  846:     }
  847: 
  848:     liberation(s_etat_processus, (*s_etat_processus).indep);
  849:     liberation(s_etat_processus, (*s_etat_processus).depend);
  850: 
  851:     free((*s_etat_processus).label_x);
  852:     free((*s_etat_processus).label_y);
  853:     free((*s_etat_processus).label_z);
  854:     free((*s_etat_processus).titre);
  855:     free((*s_etat_processus).legende);
  856: 
  857:     liberation(s_etat_processus,
  858:             (*s_etat_processus).parametres_courbes_de_niveau);
  859: 
  860:     if ((*s_etat_processus).instruction_derniere_erreur != NULL)
  861:     {
  862:         free((*s_etat_processus).instruction_derniere_erreur);
  863:         (*s_etat_processus).instruction_derniere_erreur = NULL;
  864:     }
  865: 
  866:     liberation_arbre_variables(s_etat_processus,
  867:             (*s_etat_processus).s_arbre_variables, d_faux);
  868: 
  869:     l_element_statique_courant = (*s_etat_processus)
  870:             .l_liste_variables_statiques;
  871: 
  872:     while(l_element_statique_courant != NULL)
  873:     {
  874:         l_element_statique_suivant = (*l_element_statique_courant).suivant;
  875:         free(l_element_statique_courant);
  876:         l_element_statique_courant = l_element_statique_suivant;
  877:     }
  878: 
  879:     l_element_courant = (*s_etat_processus).l_base_pile;
  880:     while(l_element_courant != NULL)
  881:     {
  882:         l_element_suivant = (*l_element_courant).suivant;
  883: 
  884:         liberation(s_etat_processus, (*l_element_courant).donnee);
  885:         free(l_element_courant);
  886: 
  887:         l_element_courant = l_element_suivant;
  888:     }
  889: 
  890:     l_element_courant = (*s_etat_processus).l_base_pile_last;
  891:     while(l_element_courant != NULL)
  892:     {
  893:         l_element_suivant = (*l_element_courant).suivant;
  894: 
  895:         liberation(s_etat_processus, (*l_element_courant).donnee);
  896:         free(l_element_courant);
  897: 
  898:         l_element_courant = l_element_suivant;
  899:     }
  900: 
  901:     l_element_courant = (*s_etat_processus).l_base_pile_contextes;
  902:     while(l_element_courant != NULL)
  903:     {
  904:         l_element_suivant = (*l_element_courant).suivant;
  905: 
  906:         liberation(s_etat_processus, (*l_element_courant).donnee);
  907:         free(l_element_courant);
  908: 
  909:         l_element_courant = l_element_suivant;
  910:     }
  911: 
  912:     l_element_courant = (*s_etat_processus).l_base_pile_taille_contextes;
  913:     while(l_element_courant != NULL)
  914:     {
  915:         l_element_suivant = (*l_element_courant).suivant;
  916: 
  917:         liberation(s_etat_processus, (*l_element_courant).donnee);
  918:         free(l_element_courant);
  919: 
  920:         l_element_courant = l_element_suivant;
  921:     }
  922: 
  923:     l_element_courant = (struct_liste_chainee *)
  924:             (*s_etat_processus).l_base_pile_systeme;
  925:     while(l_element_courant != NULL)
  926:     {
  927:         l_element_suivant = (struct_liste_chainee *)
  928:                 (*((struct_liste_pile_systeme *)
  929:                 l_element_courant)).suivant;
  930: 
  931:         liberation(s_etat_processus, (*((struct_liste_pile_systeme *)
  932:                 l_element_courant)).indice_boucle);
  933:         liberation(s_etat_processus, (*((struct_liste_pile_systeme *)
  934:                 l_element_courant)).limite_indice_boucle);
  935:         liberation(s_etat_processus, (*((struct_liste_pile_systeme *)
  936:                 l_element_courant)).objet_de_test);
  937: 
  938:         if ((*((struct_liste_pile_systeme *)
  939:                 l_element_courant)).nom_variable != NULL)
  940:         {
  941:             free((*((struct_liste_pile_systeme *)
  942:                     l_element_courant)).nom_variable);
  943:         }
  944: 
  945:         free((struct_liste_pile_systeme *) l_element_courant);
  946: 
  947:         l_element_courant = l_element_suivant;
  948:     }
  949: 
  950:     l_element_courant = (*s_etat_processus).s_bibliotheques;
  951: 
  952:     while(l_element_courant != NULL)
  953:     {
  954:         l_element_suivant = (*l_element_courant).suivant;
  955: 
  956:         free((*((struct_bibliotheque *) (*l_element_courant).donnee)).nom);
  957: 
  958:         if (((*((struct_bibliotheque *) (*l_element_courant).donnee)).pid
  959:                 == getpid()) && (pthread_equal((*((struct_bibliotheque *)
  960:                 (*l_element_courant).donnee)).tid, pthread_self()) != 0))
  961:         {
  962:             dlclose((*((struct_bibliotheque *) (*l_element_courant).donnee))
  963:                     .descripteur);
  964:         }
  965: 
  966:         free((*l_element_courant).donnee);
  967:         free(l_element_courant);
  968: 
  969:         l_element_courant = l_element_suivant;
  970:     }
  971: 
  972:     for(i = 0; i < (*s_etat_processus).nombre_instructions_externes; i++)
  973:     {
  974:         free((*s_etat_processus).s_instructions_externes[i].nom);
  975:         free((*s_etat_processus).s_instructions_externes[i]
  976:                 .nom_bibliotheque);
  977:     }
  978: 
  979:     if ((*s_etat_processus).nombre_instructions_externes != 0)
  980:     {
  981:         free((*s_etat_processus).s_instructions_externes);
  982:     }
  983: 
  984:     if ((*s_etat_processus).debug == d_vrai)
  985:         if (((*s_etat_processus).type_debug & d_debug_processus) != 0)
  986:     {
  987:         if ((*s_etat_processus).langue == 'F')
  988:         {
  989:             printf("[%d] Fin du thread %llu\n", (int) getpid(),
  990:                     (unsigned long long) pthread_self());
  991:         }
  992:         else
  993:         {
  994:             printf("[%d] End of thread %llu\n", (int) getpid(),
  995:                     (unsigned long long) pthread_self());
  996:         }
  997: 
  998:         fflush(stdout);
  999:     }
 1000: 
 1001:     liberation(s_etat_processus, (*s_argument_thread).argument);
 1002:     liberation(s_etat_processus, (*s_etat_processus).at_exit);
 1003:     liberation(s_etat_processus, (*s_etat_processus).at_poke);
 1004: 
 1005:     for(i = 0; i < d_NOMBRE_INTERRUPTIONS; i++)
 1006:     {
 1007:         liberation(s_etat_processus,
 1008:                 (*s_etat_processus).corps_interruptions[i]);
 1009: 
 1010:         l_element_courant = (*s_etat_processus)
 1011:                 .pile_origine_interruptions[i];
 1012: 
 1013:         while(l_element_courant != NULL)
 1014:         {
 1015:             l_element_suivant = (*l_element_courant).suivant;
 1016: 
 1017:             liberation(s_etat_processus, (*l_element_courant).donnee);
 1018:             free(l_element_courant);
 1019: 
 1020:             l_element_courant = l_element_suivant;
 1021:         }
 1022:     }
 1023: 
 1024:     l_element_courant = (struct_liste_chainee *) (*s_etat_processus).s_marques;
 1025: 
 1026:     while(l_element_courant != NULL)
 1027:     {
 1028:         free((*((struct_marque *) l_element_courant)).label);
 1029:         free((*((struct_marque *) l_element_courant)).position);
 1030:         l_element_suivant = (struct_liste_chainee *)
 1031:                 (*((struct_marque *) l_element_courant)).suivant;
 1032:         free((struct_marque *) l_element_courant);
 1033:         l_element_courant = l_element_suivant;
 1034:     }
 1035: 
 1036:     if ((*s_etat_processus).generateur_aleatoire != NULL)
 1037:     {
 1038:         liberation_generateur_aleatoire(s_etat_processus);
 1039:     }
 1040: 
 1041:     if ((*s_etat_processus).profilage == d_vrai)
 1042:     {
 1043:         ecriture_profil(s_etat_processus);
 1044:         liberation_profil(s_etat_processus);
 1045:     }
 1046: 
 1047:     retrait_thread(s_etat_processus);
 1048:     pthread_mutex_destroy(&((*s_etat_processus).mutex_pile_processus));
 1049:     pthread_mutex_destroy(&((*s_etat_processus).mutex_allocation));
 1050:     pthread_mutex_destroy(&((*s_etat_processus).mutex_interruptions));
 1051:     pthread_mutex_destroy(&((*s_etat_processus).mutex_signaux));
 1052: 
 1053: #   ifndef SEMAPHORES_NOMMES
 1054:         sem_post(&((*s_etat_processus).semaphore_fork));
 1055:         sem_destroy(&((*s_etat_processus).semaphore_fork));
 1056: #   else
 1057:         sem_post((*s_etat_processus).semaphore_fork);
 1058:         sem_destroy3((*s_etat_processus).semaphore_fork, getpid(),
 1059:                 pthread_self(), SEM_FORK);
 1060: #   endif
 1061: 
 1062:     close((*s_argument_thread).pipe_erreurs[1]);
 1063:     close((*s_argument_thread).pipe_interruptions[1]);
 1064:     close((*s_argument_thread).pipe_nombre_elements_attente[1]);
 1065:     close((*s_argument_thread).pipe_objets[1]);
 1066:     close((*s_argument_thread).pipe_injections[0]);
 1067:     close((*s_argument_thread).pipe_nombre_injections[0]);
 1068:     close((*s_argument_thread).pipe_acquittement[0]);
 1069: 
 1070:     liberation_contexte_cas(s_etat_processus);
 1071:     free((*s_etat_processus).localisation);
 1072:     liberation_allocateur(s_etat_processus);
 1073:     liberation_allocateur_buffer(s_etat_processus);
 1074:     pthread_mutex_destroy(&((*s_etat_processus).mutex_allocation_buffer));
 1075:     sys_free(s_etat_processus);
 1076: 
 1077:     pthread_mutex_lock(&((*s_argument_thread).mutex));
 1078:     (*s_argument_thread).thread_actif = d_faux;
 1079:     pthread_mutex_unlock(&((*s_argument_thread).mutex));
 1080: 
 1081:     pthread_exit(NULL);
 1082: }
 1083: 
 1084: // vim: ts=4

CVSweb interface <joel.bertrand@systella.fr>