1: /*
2: ================================================================================
3: RPL/2 (R) version 4.1.13
4: Copyright (C) 1989-2013 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: Routines de gestion du nombre d'occurrences comme grandeur atomique
29: ================================================================================
30: entrées : structure sur l'état du processus et objet à afficher
31: --------------------------------------------------------------------------------
32: sorties : chaine de caractères
33: --------------------------------------------------------------------------------
34: effets de bord : néant
35: ================================================================================
36: */
37:
38: static inline void
39: incrementation_atomique(struct_objet *s_objet)
40: {
41: // Le mutex est sur l'objet.
42:
43: (*s_objet).nombre_occurrences++;
44:
45: BUG((*s_objet).nombre_occurrences <= 0,
46: uprintf("Capacity exceeded %ld\n", (*s_objet).nombre_occurrences));
47:
48: return;
49: }
50:
51: static inline long
52: decrementation_atomique(struct_objet *s_objet)
53: {
54: // Le mutex est sur l'objet.
55:
56: (*s_objet).nombre_occurrences--;
57: return((*s_objet).nombre_occurrences);
58: }
59:
60: void
61: initialisation_objet(struct_objet *s_objet)
62: {
63: pthread_mutexattr_t attributs_mutex;
64:
65: pthread_mutexattr_init(&attributs_mutex);
66: pthread_mutexattr_settype(&attributs_mutex, PTHREAD_MUTEX_NORMAL);
67: pthread_mutex_init(&((*s_objet).mutex), &attributs_mutex);
68: pthread_mutexattr_destroy(&attributs_mutex);
69:
70: (*s_objet).nombre_occurrences = 1;
71:
72: return;
73: }
74:
75:
76: /*
77: ================================================================================
78: Routines d'initialisation et de purge de l'allocateur
79: ================================================================================
80: Entrées : structure sur l'état du processus et objet à afficher
81: --------------------------------------------------------------------------------
82: Sorties : chaine de caractères
83: --------------------------------------------------------------------------------
84: Effets de bord : néant
85: ================================================================================
86: */
87:
88: void
89: initialisation_allocateur(struct_processus *s_etat_processus)
90: {
91: (*s_etat_processus).estimation_taille_pile_tampon = 0;
92: (*s_etat_processus).taille_pile_tampon = 0;
93: (*s_etat_processus).pile_tampon = NULL;
94:
95: (*s_etat_processus).estimation_taille_pile_systeme_tampon = 0;
96: (*s_etat_processus).taille_pile_systeme_tampon = 0;
97: (*s_etat_processus).pile_systeme_tampon = NULL;
98:
99: (*s_etat_processus).taille_pile_objets = 0;
100: (*s_etat_processus).pile_objets = NULL;
101:
102: (*s_etat_processus).pointeur_adr = 0;
103: (*s_etat_processus).pointeur_bin = 0;
104: (*s_etat_processus).pointeur_cpl = 0;
105: (*s_etat_processus).pointeur_fct = 0;
106: (*s_etat_processus).pointeur_int = 0;
107: (*s_etat_processus).pointeur_mat = 0;
108: (*s_etat_processus).pointeur_nom = 0;
109: (*s_etat_processus).pointeur_rel = 0;
110: (*s_etat_processus).pointeur_tab = 0;
111: (*s_etat_processus).pointeur_vec = 0;
112: (*s_etat_processus).pointeur_maillons = 0;
113:
114: (*s_etat_processus).pointeur_variables_noeud = 0;
115: (*s_etat_processus).pointeur_variables_partagees_noeud = 0;
116: (*s_etat_processus).pointeur_variables_feuille = 0;
117: (*s_etat_processus).pointeur_variables_variable = 0;
118: (*s_etat_processus).pointeur_variables_tableau_noeuds = 0;
119: (*s_etat_processus).pointeur_variables_tableau_noeuds_partages = 0;
120:
121: return;
122: }
123:
124:
125: void
126: liberation_allocateur(struct_processus *s_etat_processus)
127: {
128: int i;
129:
130: for(i = 0; i < (*s_etat_processus).pointeur_adr;
131: free((*s_etat_processus).objets_adr[i++]));
132: for(i = 0; i < (*s_etat_processus).pointeur_bin;
133: free((*s_etat_processus).objets_bin[i++]));
134: for(i = 0; i < (*s_etat_processus).pointeur_cpl;
135: free((*s_etat_processus).objets_cpl[i++]));
136: for(i = 0; i < (*s_etat_processus).pointeur_fct;
137: free((*s_etat_processus).objets_fct[i++]));
138: for(i = 0; i < (*s_etat_processus).pointeur_int;
139: free((*s_etat_processus).objets_int[i++]));
140: for(i = 0; i < (*s_etat_processus).pointeur_mat;
141: free((*s_etat_processus).objets_mat[i++]));
142: for(i = 0; i < (*s_etat_processus).pointeur_nom;
143: free((*s_etat_processus).objets_nom[i++]));
144: for(i = 0; i < (*s_etat_processus).pointeur_rel;
145: free((*s_etat_processus).objets_rel[i++]));
146: for(i = 0; i < (*s_etat_processus).pointeur_tab;
147: free((*s_etat_processus).objets_tab[i++]));
148: for(i = 0; i < (*s_etat_processus).pointeur_vec;
149: free((*s_etat_processus).objets_vec[i++]));
150: for(i = 0; i < (*s_etat_processus).pointeur_maillons;
151: free((*s_etat_processus).maillons[i++]));
152:
153: for(i = 0; i < (*s_etat_processus).pointeur_variables_noeud;
154: free((*s_etat_processus).variables_noeud[i++]));
155: for(i = 0; i < (*s_etat_processus).pointeur_variables_partagees_noeud;
156: free((*s_etat_processus).variables_partagees_noeud[i++]));
157: for(i = 0; i < (*s_etat_processus).pointeur_variables_feuille;
158: free((*s_etat_processus).variables_feuille[i++]));
159: for(i = 0; i < (*s_etat_processus).pointeur_variables_variable;
160: free((*s_etat_processus).variables_variable[i++]));
161: for(i = 0; i < (*s_etat_processus).pointeur_variables_tableau_noeuds;
162: free((*s_etat_processus).variables_tableau_noeuds[i++]));
163: for(i = 0; i < (*s_etat_processus)
164: .pointeur_variables_tableau_noeuds_partages;
165: free((*s_etat_processus).variables_tableau_noeuds_partages[i++]));
166:
167: {
168: struct_liste_chainee *l_element_courant;
169: struct_liste_chainee *l_element_suivant;
170:
171: l_element_courant = (*s_etat_processus).pile_tampon;
172:
173: while(l_element_courant != NULL)
174: {
175: l_element_suivant = (*l_element_courant).suivant;
176: liberation(s_etat_processus, (*l_element_courant).donnee);
177: free(l_element_courant);
178: l_element_courant = l_element_suivant;
179: }
180: }
181:
182: {
183: struct_liste_pile_systeme *l_element_courant;
184: struct_liste_pile_systeme *l_element_suivant;
185:
186: l_element_courant = (*s_etat_processus).pile_systeme_tampon;
187:
188: while(l_element_courant != NULL)
189: {
190: l_element_suivant = (*l_element_courant).suivant;
191: free(l_element_courant);
192: l_element_courant = l_element_suivant;
193: }
194: }
195:
196: {
197: struct_objet *l_element_courant;
198: struct_objet *l_element_suivant;
199:
200: l_element_courant = (*s_etat_processus).pile_objets;
201:
202: while(l_element_courant != NULL)
203: {
204: l_element_suivant = (*l_element_courant).objet;
205:
206: if (pthread_mutex_destroy(&((*l_element_courant).mutex)) != 0)
207: {
208: (*s_etat_processus).erreur_systeme = d_es_processus;
209: BUG(1, printf("Mutex error\n"));
210: return;
211: }
212:
213: free(l_element_courant);
214: l_element_courant = l_element_suivant;
215: }
216: }
217:
218: return;
219: }
220:
221:
222: /*
223: ================================================================================
224: Routine d'allocation d'un maillon d'un objet (liste, expression...)
225: ================================================================================
226: Entrées : structure sur l'état du processus et objet à afficher
227: --------------------------------------------------------------------------------
228: Sorties : chaine de caractères
229: --------------------------------------------------------------------------------
230: Effets de bord : néant
231: ================================================================================
232: */
233:
234: void *
235: allocation_maillon(struct_processus *s_etat_processus)
236: {
237: struct_liste_chainee *s_maillon;
238:
239: if ((*s_etat_processus).pointeur_maillons > 0)
240: {
241: s_maillon = (*s_etat_processus).maillons
242: [--(*s_etat_processus).pointeur_maillons];
243: }
244: else
245: {
246: if ((s_maillon = malloc(sizeof(struct_liste_chainee))) == NULL)
247: {
248: return(NULL);
249: }
250: }
251:
252: return(s_maillon);
253: }
254:
255:
256: /*
257: ================================================================================
258: Routine de libération d'un maillon d'un objet (liste, expression...)
259: ================================================================================
260: Entrées : structure sur l'état du processus et objet à afficher
261: --------------------------------------------------------------------------------
262: Sorties : chaine de caractères
263: --------------------------------------------------------------------------------
264: Effets de bord : néant
265: ================================================================================
266: */
267:
268: void
269: liberation_maillon(struct_processus *s_etat_processus,
270: struct_liste_chainee *maillon)
271: {
272: if ((*s_etat_processus).pointeur_maillons < TAILLE_CACHE)
273: {
274: (*s_etat_processus).maillons
275: [(*s_etat_processus).pointeur_maillons++] = maillon;
276: }
277: else
278: {
279: free(maillon);
280: }
281:
282: return;
283: }
284:
285:
286: /*
287: ================================================================================
288: Routine d'allocation d'une structure *s_objet
289: ================================================================================
290: Entrées : structure sur l'état du processus et objet à allouer
291: --------------------------------------------------------------------------------
292: Sorties : chaine de caractères
293: --------------------------------------------------------------------------------
294: Effets de bord : néant
295: ================================================================================
296: */
297:
298: struct_objet *
299: allocation(struct_processus *s_etat_processus, enum t_type type)
300: {
301: struct_objet *s_objet;
302:
303: if (pthread_mutex_lock(&((*s_etat_processus).mutex_allocation)) != 0)
304: {
305: (*s_etat_processus).erreur_systeme = d_es_processus;
306: return(NULL);
307: }
308:
309: if ((*s_etat_processus).pile_objets == NULL)
310: {
311: if (pthread_mutex_unlock(&((*s_etat_processus).mutex_allocation)) != 0)
312: {
313: (*s_etat_processus).erreur_systeme = d_es_processus;
314: return(NULL);
315: }
316:
317: // Il n'existe aucune structure struct_objet disponible dans le cache.
318:
319: if ((s_objet = malloc(sizeof(struct_objet))) == NULL)
320: {
321: return(NULL);
322: }
323:
324: initialisation_objet(s_objet);
325: }
326: else
327: {
328: // Récupération d'une structure dans le cache.
329:
330: s_objet = (*s_etat_processus).pile_objets;
331: (*s_etat_processus).pile_objets = (*s_objet).objet;
332: (*s_etat_processus).taille_pile_objets--;
333:
334: (*s_objet).nombre_occurrences = 1;
335:
336: if (pthread_mutex_unlock(&((*s_etat_processus).mutex_allocation)) != 0)
337: {
338: (*s_etat_processus).erreur_systeme = d_es_processus;
339: return(NULL);
340: }
341: }
342:
343: (*s_objet).type = type;
344:
345: switch(type)
346: {
347: case ADR :
348: {
349: if ((*s_etat_processus).pointeur_adr > 0)
350: {
351: (*s_objet).objet = (*s_etat_processus).objets_adr
352: [--(*s_etat_processus).pointeur_adr];
353: }
354: else
355: {
356: if (((*s_objet).objet = malloc(sizeof(unsigned long))) == NULL)
357: {
358: free(s_objet);
359: return(NULL);
360: }
361: }
362:
363: break;
364: }
365:
366: case ALG :
367: {
368: (*s_objet).objet = NULL;
369: break;
370: }
371:
372: case BIN :
373: {
374: if ((*s_etat_processus).pointeur_bin > 0)
375: {
376: (*s_objet).objet = (*s_etat_processus).objets_bin
377: [--(*s_etat_processus).pointeur_bin];
378: }
379: else
380: {
381: if (((*s_objet).objet = malloc(sizeof(logical8))) == NULL)
382: {
383: free(s_objet);
384: return(NULL);
385: }
386: }
387:
388: break;
389: }
390:
391: case CHN :
392: {
393: (*s_objet).objet = NULL;
394: break;
395: }
396:
397: case CPL :
398: {
399: if ((*s_etat_processus).pointeur_cpl > 0)
400: {
401: (*s_objet).objet = (*s_etat_processus).objets_cpl
402: [--(*s_etat_processus).pointeur_cpl];
403: }
404: else
405: {
406: if (((*s_objet).objet = malloc(sizeof(struct_complexe16)))
407: == NULL)
408: {
409: free(s_objet);
410: return(NULL);
411: }
412: }
413:
414: break;
415: }
416:
417: case FCH :
418: {
419: if (((*s_objet).objet = malloc(sizeof(struct_fichier))) == NULL)
420: {
421: free(s_objet);
422: return(NULL);
423: }
424:
425: break;
426: }
427:
428: case FCT :
429: {
430: if ((*s_etat_processus).pointeur_fct > 0)
431: {
432: (*s_objet).objet = (*s_etat_processus).objets_fct
433: [--(*s_etat_processus).pointeur_fct];
434: }
435: else
436: {
437: if (((*s_objet).objet = malloc(sizeof(struct_fonction)))
438: == NULL)
439: {
440: free(s_objet);
441: return(NULL);
442: }
443: }
444:
445: (*((struct_fonction *) (*s_objet).objet)).fonction = NULL;
446: (*((struct_fonction *) (*s_objet).objet)).prediction_saut = NULL;
447: (*((struct_fonction *) (*s_objet).objet)).prediction_execution
448: = d_faux;
449: break;
450: }
451:
452: case INT :
453: {
454: if ((*s_etat_processus).pointeur_int > 0)
455: {
456: (*s_objet).objet = (*s_etat_processus).objets_int
457: [--(*s_etat_processus).pointeur_int];
458: }
459: else
460: {
461: if (((*s_objet).objet = malloc(sizeof(integer8))) == NULL)
462: {
463: free(s_objet);
464: return(NULL);
465: }
466: }
467:
468: break;
469: }
470:
471: case LST :
472: {
473: (*s_objet).objet = NULL;
474: break;
475: }
476:
477: case MCX :
478: {
479: if ((*s_etat_processus).pointeur_mat > 0)
480: {
481: (*s_objet).objet = (*s_etat_processus).objets_mat
482: [--(*s_etat_processus).pointeur_mat];
483: }
484: else
485: {
486: if (((*s_objet).objet = malloc(sizeof(struct_matrice))) == NULL)
487: {
488: free(s_objet);
489: return(NULL);
490: }
491: }
492:
493: (*((struct_matrice *) (*s_objet).objet)).type = 'C';
494: (*((struct_matrice *) (*s_objet).objet)).nombre_lignes = 0;
495: (*((struct_matrice *) (*s_objet).objet)).nombre_colonnes = 0;
496: (*((struct_matrice *) (*s_objet).objet)).tableau = NULL;
497: break;
498: }
499:
500: case MIN :
501: {
502: if ((*s_etat_processus).pointeur_mat > 0)
503: {
504: (*s_objet).objet = (*s_etat_processus).objets_mat
505: [--(*s_etat_processus).pointeur_mat];
506: }
507: else
508: {
509: if (((*s_objet).objet = malloc(sizeof(struct_matrice))) == NULL)
510: {
511: free(s_objet);
512: return(NULL);
513: }
514: }
515:
516: (*((struct_matrice *) (*s_objet).objet)).type = 'I';
517: (*((struct_matrice *) (*s_objet).objet)).nombre_lignes = 0;
518: (*((struct_matrice *) (*s_objet).objet)).nombre_colonnes = 0;
519: (*((struct_matrice *) (*s_objet).objet)).tableau = NULL;
520: break;
521: }
522:
523: case MRL :
524: {
525: if ((*s_etat_processus).pointeur_mat > 0)
526: {
527: (*s_objet).objet = (*s_etat_processus).objets_mat
528: [--(*s_etat_processus).pointeur_mat];
529: }
530: else
531: {
532: if (((*s_objet).objet = malloc(sizeof(struct_matrice))) == NULL)
533: {
534: free(s_objet);
535: return(NULL);
536: }
537: }
538:
539: (*((struct_matrice *) (*s_objet).objet)).type = 'R';
540: (*((struct_matrice *) (*s_objet).objet)).nombre_lignes = 0;
541: (*((struct_matrice *) (*s_objet).objet)).nombre_colonnes = 0;
542: (*((struct_matrice *) (*s_objet).objet)).tableau = NULL;
543: break;
544: }
545:
546: case MTX :
547: {
548: if (((*s_objet).objet = malloc(sizeof(struct_mutex))) == NULL)
549: {
550: free(s_objet);
551: return(NULL);
552: }
553:
554: (*((struct_mutex *) (*s_objet).objet)).tid = pthread_self();
555: break;
556: }
557:
558: case NOM :
559: {
560: if ((*s_etat_processus).pointeur_nom > 0)
561: {
562: (*s_objet).objet = (*s_etat_processus).objets_nom
563: [--(*s_etat_processus).pointeur_nom];
564: }
565: else
566: {
567: if (((*s_objet).objet = malloc(sizeof(struct_nom))) == NULL)
568: {
569: free(s_objet);
570: return(NULL);
571: }
572: }
573:
574: break;
575: }
576:
577: case NON :
578: {
579: (*s_objet).objet = NULL;
580: break;
581: }
582:
583: case PRC :
584: {
585: if (((*s_objet).objet = malloc(sizeof(struct_processus_fils)))
586: == NULL)
587: {
588: free(s_objet);
589: return(NULL);
590: }
591:
592: break;
593: }
594:
595: case REL :
596: {
597: if ((*s_etat_processus).pointeur_rel > 0)
598: {
599: (*s_objet).objet = (*s_etat_processus).objets_rel
600: [--(*s_etat_processus).pointeur_rel];
601: }
602: else
603: {
604: if (((*s_objet).objet = malloc(sizeof(real8))) == NULL)
605: {
606: free(s_objet);
607: return(NULL);
608: }
609: }
610:
611: break;
612: }
613:
614: case RPN :
615: {
616: (*s_objet).objet = NULL;
617: break;
618: }
619:
620: case SCK :
621: {
622: if (((*s_objet).objet = malloc(sizeof(struct_socket))) == NULL)
623: {
624: free(s_objet);
625: return(NULL);
626: }
627:
628: break;
629: }
630:
631: case SLB :
632: {
633: if (((*s_objet).objet = malloc(sizeof(struct_bibliotheque)))
634: == NULL)
635: {
636: free(s_objet);
637: return(NULL);
638: }
639:
640: break;
641: }
642:
643: case SPH :
644: {
645: if (((*s_objet).objet = malloc(sizeof(struct_semaphore))) == NULL)
646: {
647: free(s_objet);
648: return(NULL);
649: }
650:
651: break;
652: }
653:
654: case SQL :
655: {
656: if (((*s_objet).objet = malloc(sizeof(struct_connecteur_sql)))
657: == NULL)
658: {
659: free(s_objet);
660: return(NULL);
661: }
662:
663: break;
664: }
665:
666: case TBL :
667: {
668: if ((*s_etat_processus).pointeur_tab > 0)
669: {
670: (*s_objet).objet = (*s_etat_processus).objets_tab
671: [--(*s_etat_processus).pointeur_tab];
672: }
673: else
674: {
675: if (((*s_objet).objet = malloc(sizeof(struct_tableau))) == NULL)
676: {
677: free(s_objet);
678: return(NULL);
679: }
680: }
681:
682: (*((struct_tableau *) (*s_objet).objet)).nombre_elements = 0;
683: (*((struct_tableau *) (*s_objet).objet)).elements = NULL;
684: break;
685: }
686:
687: case VCX :
688: {
689: if ((*s_etat_processus).pointeur_vec > 0)
690: {
691: (*s_objet).objet = (*s_etat_processus).objets_vec
692: [--(*s_etat_processus).pointeur_vec];
693: }
694: else
695: {
696: if (((*s_objet).objet = malloc(sizeof(struct_vecteur))) == NULL)
697: {
698: free(s_objet);
699: return(NULL);
700: }
701: }
702:
703: (*((struct_vecteur *) (*s_objet).objet)).type = 'C';
704: (*((struct_vecteur *) (*s_objet).objet)).taille = 0;
705: (*((struct_vecteur *) (*s_objet).objet)).tableau = NULL;
706: break;
707: }
708:
709: case VIN :
710: {
711: if ((*s_etat_processus).pointeur_vec > 0)
712: {
713: (*s_objet).objet = (*s_etat_processus).objets_vec
714: [--(*s_etat_processus).pointeur_vec];
715: }
716: else
717: {
718: if (((*s_objet).objet = malloc(sizeof(struct_vecteur))) == NULL)
719: {
720: free(s_objet);
721: return(NULL);
722: }
723: }
724:
725: (*((struct_vecteur *) (*s_objet).objet)).type = 'I';
726: (*((struct_vecteur *) (*s_objet).objet)).taille = 0;
727: (*((struct_vecteur *) (*s_objet).objet)).tableau = NULL;
728: break;
729: }
730:
731: case VRL :
732: {
733: if ((*s_etat_processus).pointeur_vec > 0)
734: {
735: (*s_objet).objet = (*s_etat_processus).objets_vec
736: [--(*s_etat_processus).pointeur_vec];
737: }
738: else
739: {
740: if (((*s_objet).objet = malloc(sizeof(struct_vecteur))) == NULL)
741: {
742: free(s_objet);
743: return(NULL);
744: }
745: }
746:
747: (*((struct_vecteur *) (*s_objet).objet)).type = 'R';
748: (*((struct_vecteur *) (*s_objet).objet)).taille = 0;
749: (*((struct_vecteur *) (*s_objet).objet)).tableau = NULL;
750: break;
751: }
752:
753: default :
754: {
755: free(s_objet);
756: BUG(1, printf("Allocation failure (type %d)\n", type));
757:
758: return(NULL);
759: }
760: }
761:
762: return(s_objet);
763: }
764:
765:
766: /*
767: ================================================================================
768: Routine de libération d'une structure *s_objet
769: ================================================================================
770: Entrées : structure sur l'état du processus et objet à afficher
771: --------------------------------------------------------------------------------
772: Sorties : chaine de caractères
773: --------------------------------------------------------------------------------
774: Effets de bord : néant
775: ================================================================================
776: */
777:
778: void
779: liberation(struct_processus *s_etat_processus, struct_objet *s_objet)
780: {
781: logical1 drapeau;
782:
783: struct_liste_chainee *l_element_courant;
784: struct_liste_chainee *l_element_suivant;
785:
786: unsigned long i;
787:
788: if (s_objet == NULL)
789: {
790: return;
791: }
792:
793: if (pthread_mutex_lock(&((*s_objet).mutex)) != 0)
794: {
795: (*s_etat_processus).erreur_systeme = d_es_processus;
796: return;
797: }
798:
799: #define return \
800: if (pthread_mutex_unlock(&((*s_objet).mutex)) != 0) \
801: { (*s_etat_processus).erreur_systeme = d_es_processus; return; } \
802: return
803:
804: BUG((*s_objet).nombre_occurrences <= 0,
805: pthread_mutex_unlock(&((*s_objet).mutex)),
806: printf("(*s_objet).nombre_occurrences=%ld\n",
807: (*s_objet).nombre_occurrences));
808:
809: switch((*s_objet).type)
810: {
811: case ADR :
812: {
813: if (decrementation_atomique(s_objet) > 0)
814: {
815: return;
816: }
817:
818: if ((*s_etat_processus).pointeur_adr < TAILLE_CACHE)
819: {
820: (*s_etat_processus).objets_adr
821: [(*s_etat_processus).pointeur_adr++] = (*s_objet).objet;
822: }
823: else
824: {
825: free((unsigned long *) ((*s_objet).objet));
826: }
827:
828: break;
829: }
830:
831: case ALG :
832: {
833: l_element_courant = (struct_liste_chainee *) ((*s_objet).objet);
834:
835: if (decrementation_atomique(s_objet) > 0)
836: { // Il reste un pointeur sur l'objet.
837: while(l_element_courant != NULL)
838: {
839: BUG((*(*l_element_courant).donnee).nombre_occurrences <= 1,
840: pthread_mutex_unlock(&((*s_objet).mutex)),
841: printf("(*(*l_element_courant).donnee)"
842: ".nombre_occurrences=%ld\n",
843: (*(*l_element_courant).donnee).nombre_occurrences));
844:
845: liberation(s_etat_processus, (*l_element_courant).donnee);
846: l_element_courant = (*l_element_courant).suivant;
847: }
848:
849: return;
850: }
851: else
852: { // Il ne reste plus aucun pointeur sur l'objet.
853: while(l_element_courant != NULL)
854: {
855: l_element_suivant = (*l_element_courant).suivant;
856: liberation(s_etat_processus, (*l_element_courant).donnee);
857: liberation_maillon(s_etat_processus, l_element_courant);
858: l_element_courant = l_element_suivant;
859: }
860: }
861:
862: break;
863: }
864:
865: case BIN :
866: {
867: if (decrementation_atomique(s_objet) > 0)
868: {
869: return;
870: }
871:
872: if ((*s_etat_processus).pointeur_bin < TAILLE_CACHE)
873: {
874: (*s_etat_processus).objets_bin
875: [(*s_etat_processus).pointeur_bin++] = (*s_objet).objet;
876: }
877: else
878: {
879: free((logical8 *) ((*s_objet).objet));
880: }
881:
882: break;
883: }
884:
885: case CHN :
886: {
887: if (decrementation_atomique(s_objet) > 0)
888: {
889: return;
890: }
891:
892: free((unsigned char *) ((*s_objet).objet));
893: break;
894: }
895:
896: case CPL :
897: {
898: if (decrementation_atomique(s_objet) > 0)
899: {
900: return;
901: }
902:
903: if ((*s_etat_processus).pointeur_cpl < TAILLE_CACHE)
904: {
905: (*s_etat_processus).objets_cpl
906: [(*s_etat_processus).pointeur_cpl++] = (*s_objet).objet;
907: }
908: else
909: {
910: free((struct_complexe16 *) ((*s_objet).objet));
911: }
912:
913: break;
914: }
915:
916: case FCH :
917: {
918: if (decrementation_atomique(s_objet) > 0)
919: {
920: BUG((*(*((struct_fichier *) (*s_objet).objet)).format)
921: .nombre_occurrences <= 1,
922: pthread_mutex_unlock(&((*s_objet).mutex)),
923: printf("(*(*((struct_fichier *) (*s_objet).objet))"
924: ".format).nombre_occurrences=%ld\n",
925: (*(*((struct_fichier *) (*s_objet).objet)).format)
926: .nombre_occurrences));
927:
928: liberation(s_etat_processus,
929: (*((struct_fichier *) (*s_objet).objet)).format);
930: return;
931: }
932:
933: liberation(s_etat_processus,
934: (*((struct_fichier *) (*s_objet).objet)).format);
935: free((unsigned char *) (*((struct_fichier *)
936: (*s_objet).objet)).nom);
937: free((struct_fichier *) ((*s_objet).objet));
938: break;
939: }
940:
941: case FCT :
942: {
943: if (decrementation_atomique(s_objet) > 0)
944: {
945: return;
946: }
947:
948: free((unsigned char *) (*((struct_fonction *)
949: (*s_objet).objet)).nom_fonction);
950:
951: if ((*s_etat_processus).pointeur_fct < TAILLE_CACHE)
952: {
953: (*s_etat_processus).objets_fct
954: [(*s_etat_processus).pointeur_fct++] = (*s_objet).objet;
955: }
956: else
957: {
958: free((struct_fonction *) (*s_objet).objet);
959: }
960:
961: break;
962: }
963:
964: case INT :
965: {
966: if (decrementation_atomique(s_objet) > 0)
967: {
968: return;
969: }
970:
971: if ((*s_etat_processus).pointeur_int < TAILLE_CACHE)
972: {
973: (*s_etat_processus).objets_int
974: [(*s_etat_processus).pointeur_int++] = (*s_objet).objet;
975: }
976: else
977: {
978: free((integer8 *) ((*s_objet).objet));
979: }
980:
981: break;
982: }
983:
984: case LST :
985: {
986: l_element_courant = (struct_liste_chainee *) ((*s_objet).objet);
987:
988: if (decrementation_atomique(s_objet) > 0)
989: { // Il reste un pointeur sur l'objet.
990: while(l_element_courant != NULL)
991: {
992: BUG((*(*l_element_courant).donnee).nombre_occurrences <= 1,
993: pthread_mutex_unlock(&((*s_objet).mutex)),
994: printf("(*(*l_element_courant).donnee)"
995: ".nombre_occurrences=%ld\n",
996: (*(*l_element_courant).donnee).nombre_occurrences));
997:
998: liberation(s_etat_processus, (*l_element_courant).donnee);
999: l_element_courant = (*l_element_courant).suivant;
1000: }
1001:
1002: return;
1003: }
1004: else
1005: { // Il ne reste plus aucun pointeur sur l'objet.
1006: while(l_element_courant != NULL)
1007: {
1008: l_element_suivant = (*l_element_courant).suivant;
1009: liberation(s_etat_processus, (*l_element_courant).donnee);
1010: liberation_maillon(s_etat_processus, l_element_courant);
1011: l_element_courant = l_element_suivant;
1012: }
1013: }
1014:
1015: break;
1016: }
1017:
1018: case MIN :
1019: {
1020: if (decrementation_atomique(s_objet) > 0)
1021: {
1022: return;
1023: }
1024:
1025: for(i = 0; i < (*((struct_matrice *)
1026: ((*s_objet).objet))).nombre_lignes; i++)
1027: {
1028: free(((integer8 **) (*((struct_matrice *)
1029: (*s_objet).objet)).tableau)[i]);
1030: }
1031:
1032: free((integer8 **) (*((struct_matrice *)
1033: (*s_objet).objet)).tableau);
1034:
1035: if ((*s_etat_processus).pointeur_mat < TAILLE_CACHE)
1036: {
1037: (*s_etat_processus).objets_mat
1038: [(*s_etat_processus).pointeur_mat++] = (*s_objet).objet;
1039: }
1040: else
1041: {
1042: free((struct_matrice *) (*s_objet).objet);
1043: }
1044:
1045: break;
1046: }
1047:
1048: case MCX :
1049: {
1050: if (decrementation_atomique(s_objet) > 0)
1051: {
1052: return;
1053: }
1054:
1055: for(i = 0; i < (*((struct_matrice *)
1056: ((*s_objet).objet))).nombre_lignes; i++)
1057: {
1058: free(((struct_complexe16 **) (*((struct_matrice *)
1059: (*s_objet).objet)).tableau)[i]);
1060: }
1061:
1062: free((struct_complexe16 **) (*((struct_matrice *)
1063: (*s_objet).objet)).tableau);
1064:
1065: if ((*s_etat_processus).pointeur_mat < TAILLE_CACHE)
1066: {
1067: (*s_etat_processus).objets_mat
1068: [(*s_etat_processus).pointeur_mat++] = (*s_objet).objet;
1069: }
1070: else
1071: {
1072: free((struct_matrice *) (*s_objet).objet);
1073: }
1074:
1075: break;
1076: }
1077:
1078: case MRL :
1079: {
1080: if (decrementation_atomique(s_objet) > 0)
1081: {
1082: return;
1083: }
1084:
1085: for(i = 0; i < (*((struct_matrice *)
1086: ((*s_objet).objet))).nombre_lignes; i++)
1087: {
1088: free(((real8 **) (*((struct_matrice *)
1089: (*s_objet).objet)).tableau)[i]);
1090: }
1091:
1092: free((real8 **) (*((struct_matrice *) (*s_objet).objet)).tableau);
1093:
1094: if ((*s_etat_processus).pointeur_mat < TAILLE_CACHE)
1095: {
1096: (*s_etat_processus).objets_mat
1097: [(*s_etat_processus).pointeur_mat++] = (*s_objet).objet;
1098: }
1099: else
1100: {
1101: free((struct_matrice *) (*s_objet).objet);
1102: }
1103:
1104: break;
1105: }
1106:
1107: case MTX :
1108: {
1109: if (decrementation_atomique(s_objet) > 0)
1110: {
1111: return;
1112: }
1113:
1114: if (pthread_mutex_trylock(&((*((struct_mutex *)
1115: (*s_objet).objet)).mutex)) == 0)
1116: {
1117: // On a pu verrouiller le mutex. Il faut donc spécifier le tid.
1118: (*((struct_mutex *) (*s_objet).objet)).tid = pthread_self();
1119: }
1120:
1121: if (pthread_equal(pthread_self(),
1122: (*((struct_mutex *) (*s_objet).objet)).tid) != 0)
1123: {
1124: pthread_mutex_unlock(&((*((struct_mutex *)
1125: (*s_objet).objet)).mutex));
1126: }
1127: else
1128: {
1129: (*s_etat_processus).erreur_systeme =
1130: d_es_mutex_acquis_autre_thread;
1131: return;
1132: }
1133:
1134: pthread_mutex_destroy(&((*((struct_mutex *)
1135: (*s_objet).objet)).mutex));
1136: free((struct_mutex *) (*s_objet).objet);
1137: break;
1138: }
1139:
1140: case NOM :
1141: {
1142: if (decrementation_atomique(s_objet) > 0)
1143: {
1144: return;
1145: }
1146:
1147: free((*((struct_nom *) (*s_objet).objet)).nom);
1148:
1149: if ((*s_etat_processus).pointeur_nom < TAILLE_CACHE)
1150: {
1151: (*s_etat_processus).objets_nom
1152: [(*s_etat_processus).pointeur_nom++] = (*s_objet).objet;
1153: }
1154: else
1155: {
1156: free((struct_nom *) (*s_objet).objet);
1157: }
1158:
1159: break;
1160: }
1161:
1162: case NON :
1163: {
1164: if (decrementation_atomique(s_objet) > 0)
1165: {
1166: return;
1167: }
1168:
1169: break;
1170: }
1171:
1172: case PRC :
1173: {
1174: if (pthread_mutex_lock(&((*(*((struct_processus_fils *)
1175: (*s_objet).objet)).thread).mutex_nombre_references)) != 0)
1176: {
1177: (*s_etat_processus).erreur_systeme = d_es_processus;
1178: return;
1179: }
1180:
1181: (*(*((struct_processus_fils *) (*s_objet).objet)).thread)
1182: .nombre_references--;
1183:
1184: BUG((*(*((struct_processus_fils *) (*s_objet).objet)).thread)
1185: .nombre_references < 0, uprintf(
1186: "(*(*((struct_processus_fils"
1187: " *) (*s_objet).objet)).thread).nombre_references = %d\n",
1188: (int) (*(*((struct_processus_fils *) (*s_objet).objet))
1189: .thread).nombre_references));
1190:
1191: if ((*(*((struct_processus_fils *) (*s_objet).objet)).thread)
1192: .nombre_references == 0)
1193: {
1194: drapeau = d_vrai;
1195: }
1196: else
1197: {
1198: drapeau = d_faux;
1199: }
1200:
1201: if (pthread_mutex_unlock(&((*(*((struct_processus_fils *)
1202: (*s_objet).objet)).thread).mutex_nombre_references)) != 0)
1203: {
1204: (*s_etat_processus).erreur_systeme = d_es_processus;
1205: return;
1206: }
1207:
1208: if (drapeau == d_vrai)
1209: {
1210: pthread_mutex_destroy(&((*(*((struct_processus_fils *)
1211: (*s_objet).objet)).thread).mutex));
1212: pthread_mutex_destroy(&((*(*((struct_processus_fils *)
1213: (*s_objet).objet)).thread).mutex_nombre_references));
1214: free((*((struct_processus_fils *) (*s_objet).objet)).thread);
1215: }
1216:
1217: if (decrementation_atomique(s_objet) > 0)
1218: {
1219: BUG(drapeau == d_vrai, uprintf("(*(*((struct_processus_fils"
1220: " *) (*s_objet).objet)).thread).nombre_references "
1221: "= 0 with nombre_occurrences > 0\n"));
1222: return;
1223: }
1224:
1225: free((struct_processus_fils *) ((*s_objet).objet));
1226: break;
1227: }
1228:
1229: case REL :
1230: {
1231: if (decrementation_atomique(s_objet) > 0)
1232: {
1233: return;
1234: }
1235:
1236: if ((*s_etat_processus).pointeur_rel < TAILLE_CACHE)
1237: {
1238: (*s_etat_processus).objets_rel
1239: [(*s_etat_processus).pointeur_rel++] = (*s_objet).objet;
1240: }
1241: else
1242: {
1243: free((real8 *) ((*s_objet).objet));
1244: }
1245:
1246: break;
1247: }
1248:
1249: case RPN :
1250: {
1251: l_element_courant = (struct_liste_chainee *) ((*s_objet).objet);
1252:
1253: if (decrementation_atomique(s_objet) > 0)
1254: { // Il reste un pointeur sur l'objet.
1255: while(l_element_courant != NULL)
1256: {
1257: BUG((*(*l_element_courant).donnee).nombre_occurrences <= 1,
1258: pthread_mutex_unlock(&((*s_objet).mutex)),
1259: printf("(*(*l_element_courant).donnee)"
1260: ".nombre_occurrences=%ld\n",
1261: (*(*l_element_courant).donnee).nombre_occurrences));
1262:
1263: liberation(s_etat_processus, (*l_element_courant).donnee);
1264: l_element_courant = (*l_element_courant).suivant;
1265: }
1266:
1267: return;
1268: }
1269: else
1270: { // Il ne reste plus aucun pointeur sur l'objet.
1271: while(l_element_courant != NULL)
1272: {
1273: l_element_suivant = (*l_element_courant).suivant;
1274: liberation(s_etat_processus, (*l_element_courant).donnee);
1275: liberation_maillon(s_etat_processus, l_element_courant);
1276: l_element_courant = l_element_suivant;
1277: }
1278: }
1279:
1280: break;
1281: }
1282:
1283: case SCK :
1284: {
1285: if (decrementation_atomique(s_objet) > 0)
1286: {
1287: BUG((*(*((struct_socket *) (*s_objet).objet)).format)
1288: .nombre_occurrences <= 1,
1289: pthread_mutex_unlock(&((*s_objet).mutex)),
1290: printf("(*(*((struct_socket *) (*s_objet).objet))"
1291: ".format).nombre_occurrences=%ld\n",
1292: (*(*((struct_socket *) (*s_objet).objet)).format)
1293: .nombre_occurrences));
1294:
1295: liberation(s_etat_processus, (*((struct_socket *)
1296: (*s_objet).objet)).format);
1297: return;
1298: }
1299:
1300: liberation(s_etat_processus, (*((struct_socket *)
1301: (*s_objet).objet)).format);
1302:
1303: free((unsigned char *) (*((struct_socket *) (*s_objet).objet))
1304: .adresse);
1305: free((unsigned char *) (*((struct_socket *) (*s_objet).objet))
1306: .adresse_distante);
1307: free((struct_socket *) ((*s_objet).objet));
1308: break;
1309: }
1310:
1311: case SLB :
1312: {
1313: if (decrementation_atomique(s_objet) > 0)
1314: {
1315: return;
1316: }
1317:
1318: free((*((struct_bibliotheque *) (*s_objet).objet)).nom);
1319: free((struct_bibliotheque *) (*s_objet).objet);
1320: break;
1321: }
1322:
1323: case SPH :
1324: {
1325: if (decrementation_atomique(s_objet) > 0)
1326: {
1327: return;
1328: }
1329:
1330: free((*((struct_semaphore *) (*s_objet).objet)).nom);
1331: free((struct_bibliotheque *) (*s_objet).objet);
1332: break;
1333: }
1334:
1335: case SQL :
1336: {
1337: if (decrementation_atomique(s_objet) > 0)
1338: {
1339: return;
1340: }
1341:
1342: free((*((struct_connecteur_sql *) (*s_objet).objet)).type);
1343: free((*((struct_connecteur_sql *) (*s_objet).objet)).locale);
1344: free((struct_connecteur_sql *) (*s_objet).objet);
1345: break;
1346: }
1347:
1348: case TBL :
1349: {
1350: if (decrementation_atomique(s_objet) > 0)
1351: {
1352: for(i = 0; i < (*((struct_tableau *) (*s_objet).objet))
1353: .nombre_elements; i++)
1354: {
1355: BUG((*((*((struct_tableau *)
1356: (*s_objet).objet)).elements[i]))
1357: .nombre_occurrences <= 1,
1358: pthread_mutex_unlock(&((*s_objet).mutex)),
1359: printf("(*((*((struct_tableau *) (*s_objet).objet))"
1360: ".element[%lu])).nombre_occurrences=%ld\n", i,
1361: (*((*((struct_tableau *) (*s_objet).objet))
1362: .elements[i])).nombre_occurrences));
1363: liberation(s_etat_processus, (*((struct_tableau *)
1364: (*s_objet).objet)).elements[i]);
1365: }
1366:
1367: return;
1368: }
1369:
1370: for(i = 0; i < (*((struct_tableau *) (*s_objet).objet))
1371: .nombre_elements; i++)
1372: {
1373: liberation(s_etat_processus, (*((struct_tableau *)
1374: (*s_objet).objet)).elements[i]);
1375: }
1376:
1377: free((*((struct_tableau *) (*s_objet).objet)).elements);
1378:
1379: if ((*s_etat_processus).pointeur_tab < TAILLE_CACHE)
1380: {
1381: (*s_etat_processus).objets_tab
1382: [(*s_etat_processus).pointeur_tab++] = (*s_objet).objet;
1383: }
1384: else
1385: {
1386: free((struct_tableau *) (*s_objet).objet);
1387: }
1388:
1389: break;
1390: }
1391:
1392: case VIN :
1393: {
1394: if (decrementation_atomique(s_objet) > 0)
1395: {
1396: return;
1397: }
1398:
1399: free((integer8 *) (*((struct_vecteur *) (*s_objet).objet)).tableau);
1400:
1401: if ((*s_etat_processus).pointeur_vec < TAILLE_CACHE)
1402: {
1403: (*s_etat_processus).objets_vec
1404: [(*s_etat_processus).pointeur_vec++] = (*s_objet).objet;
1405: }
1406: else
1407: {
1408: free((struct_vecteur *) (*s_objet).objet);
1409: }
1410:
1411: break;
1412: }
1413:
1414: case VCX :
1415: {
1416: if (decrementation_atomique(s_objet) > 0)
1417: {
1418: return;
1419: }
1420:
1421: free((struct_complexe16 *) (*((struct_vecteur *)
1422: (*s_objet).objet)).tableau);
1423:
1424: if ((*s_etat_processus).pointeur_vec < TAILLE_CACHE)
1425: {
1426: (*s_etat_processus).objets_vec
1427: [(*s_etat_processus).pointeur_vec++] = (*s_objet).objet;
1428: }
1429: else
1430: {
1431: free((struct_vecteur *) (*s_objet).objet);
1432: }
1433:
1434: break;
1435: }
1436:
1437: case VRL :
1438: {
1439: if (decrementation_atomique(s_objet) > 0)
1440: {
1441: return;
1442: }
1443:
1444: free((real8 *) (*((struct_vecteur *) (*s_objet).objet)).tableau);
1445:
1446: if ((*s_etat_processus).pointeur_vec < TAILLE_CACHE)
1447: {
1448: (*s_etat_processus).objets_vec
1449: [(*s_etat_processus).pointeur_vec++] = (*s_objet).objet;
1450: }
1451: else
1452: {
1453: free((struct_vecteur *) (*s_objet).objet);
1454: }
1455:
1456: break;
1457: }
1458:
1459: default :
1460: {
1461: if (pthread_mutex_unlock(&((*s_objet).mutex)) != 0)
1462: {
1463: (*s_etat_processus).erreur_systeme = d_es_processus;
1464: return;
1465: }
1466:
1467: if (pthread_mutex_destroy(&((*s_objet).mutex)) != 0)
1468: {
1469: (*s_etat_processus).erreur_systeme = d_es_processus;
1470: return;
1471: }
1472:
1473: BUG(1, printf("Free failure (type %d)\n", (*s_objet).type));
1474: return;
1475: }
1476: }
1477:
1478: #undef return
1479:
1480: if (pthread_mutex_unlock(&((*s_objet).mutex)) != 0)
1481: {
1482: (*s_etat_processus).erreur_systeme = d_es_processus;
1483: return;
1484: }
1485:
1486: if (pthread_mutex_lock(&((*s_etat_processus).mutex_allocation)) != 0)
1487: {
1488: (*s_etat_processus).erreur_systeme = d_es_processus;
1489: return;
1490: }
1491:
1492: if ((*s_etat_processus).taille_pile_objets < TAILLE_CACHE)
1493: {
1494: (*s_objet).objet = (*s_etat_processus).pile_objets;
1495: (*s_etat_processus).pile_objets = s_objet;
1496: (*s_etat_processus).taille_pile_objets++;
1497: }
1498: else
1499: {
1500: if (pthread_mutex_destroy(&((*s_objet).mutex)) != 0)
1501: {
1502: pthread_mutex_unlock(&((*s_etat_processus).mutex_allocation));
1503: (*s_etat_processus).erreur_systeme = d_es_processus;
1504: return;
1505: }
1506:
1507: free(s_objet);
1508: }
1509:
1510: if (pthread_mutex_unlock(&((*s_etat_processus).mutex_allocation)) != 0)
1511: {
1512: (*s_etat_processus).erreur_systeme = d_es_processus;
1513: return;
1514: }
1515:
1516: return;
1517: }
1518:
1519:
1520: /*
1521: ================================================================================
1522: Routine de copie d'une structure *s_objet
1523: ================================================================================
1524: Entrées : structure *s_objet à copier
1525: type :
1526: 'P' : renvoie le même objet en incrémentant le nombre
1527: d'occurrence de chaque objet élémentaire ;
1528: 'O' : crée un nouvel objet en copiant chaque objet élémentaire ;
1529: 'N' : crée un nouvel objet mais les objets élémentaires
1530: sont réutilisés (voir 'P'). Dans le cas d'un objet
1531: élémentaire, 'N' et 'P' sont identiques.
1532: 'Q' : 'P' si nombre_occurrences vaut 1, 'O' sinon.
1533: 'R' : 'P' si nombre_occurrences vaut 1, 'N' sinon.
1534: --------------------------------------------------------------------------------
1535: Sorties : structure identique (tous les objets sont copiés)
1536: --------------------------------------------------------------------------------
1537: Effets de bord : néant
1538: ================================================================================
1539: */
1540:
1541: struct_objet *
1542: copie_objet(struct_processus *s_etat_processus,
1543: struct_objet *s_objet, unsigned char type)
1544: {
1545: struct_liste_chainee *l_element_base;
1546: struct_liste_chainee *l_element_courant;
1547: struct_liste_chainee *l_element_courant_ecriture;
1548: struct_liste_chainee *l_element_courant_lecture;
1549: struct_liste_chainee *l_element_suivant_ecriture;
1550: struct_liste_chainee *l_element_suivant_lecture;
1551:
1552: struct_objet *s_nouvel_objet;
1553: struct_objet *s_objet_tampon;
1554:
1555: unsigned long i;
1556: unsigned long j;
1557:
1558: if (pthread_mutex_lock(&((*s_objet).mutex)) != 0)
1559: {
1560: (*s_etat_processus).erreur_systeme = d_es_processus;
1561: return(NULL);
1562: }
1563:
1564: if (type == 'Q')
1565: {
1566: if ((*s_objet).nombre_occurrences == 1)
1567: {
1568: type = 'P';
1569: }
1570: else
1571: {
1572: type = 'O';
1573: }
1574: }
1575: else if (type == 'R')
1576: {
1577: if ((*s_objet).nombre_occurrences == 1)
1578: {
1579: type = 'P';
1580: }
1581: else
1582: {
1583: type = 'N';
1584: }
1585: }
1586:
1587: #define return(pointeur) \
1588: if (pthread_mutex_unlock(&((*s_objet).mutex))) \
1589: { (*s_etat_processus).erreur_systeme = d_es_processus; return(NULL); } \
1590: return(pointeur)
1591:
1592: switch((*s_objet).type)
1593: {
1594: case ADR :
1595: {
1596: if (type != 'O')
1597: {
1598: incrementation_atomique(s_objet);
1599: return(s_objet);
1600: }
1601:
1602: if ((s_nouvel_objet = allocation(s_etat_processus, ADR)) == NULL)
1603: {
1604: return(NULL);
1605: }
1606:
1607: (*((unsigned long *) ((*s_nouvel_objet).objet))) =
1608: (*((unsigned long *) ((*s_objet).objet)));
1609: break;
1610: }
1611:
1612: case ALG :
1613: {
1614: if (type != 'P')
1615: {
1616: if ((s_nouvel_objet = allocation(s_etat_processus, ALG))
1617: == NULL)
1618: {
1619: return(NULL);
1620: }
1621:
1622: l_element_courant_lecture = (struct_liste_chainee *)
1623: ((*s_objet).objet);
1624:
1625: l_element_base = NULL;
1626: l_element_courant_ecriture = l_element_base;
1627:
1628: while(l_element_courant_lecture != NULL)
1629: {
1630: s_objet_tampon = copie_objet(s_etat_processus,
1631: (*l_element_courant_lecture).donnee, type);
1632: l_element_suivant_ecriture = (struct_liste_chainee *)
1633: malloc(sizeof(struct_liste_chainee));
1634:
1635: if ((s_objet_tampon == NULL) ||
1636: (l_element_suivant_ecriture == NULL))
1637: {
1638: l_element_courant_lecture = (struct_liste_chainee *)
1639: ((*s_nouvel_objet).objet);
1640:
1641: while(l_element_courant_lecture != NULL)
1642: {
1643: l_element_suivant_lecture =
1644: (*l_element_courant_lecture).suivant;
1645: liberation(s_etat_processus,
1646: (*l_element_courant_lecture).donnee);
1647: free(l_element_courant_lecture);
1648: l_element_courant_lecture =
1649: l_element_suivant_lecture;
1650: }
1651:
1652: return(NULL);
1653: }
1654:
1655: if (l_element_courant_ecriture == NULL)
1656: {
1657: l_element_base = l_element_suivant_ecriture;
1658: }
1659: else
1660: {
1661: (*l_element_courant_ecriture).suivant =
1662: l_element_suivant_ecriture;
1663: }
1664:
1665: l_element_courant_ecriture = l_element_suivant_ecriture;
1666:
1667: (*l_element_courant_ecriture).donnee = s_objet_tampon;
1668: (*l_element_courant_ecriture).suivant = NULL;
1669: l_element_courant_lecture =
1670: (*l_element_courant_lecture).suivant;
1671: }
1672:
1673: (*s_nouvel_objet).objet = (void *) ((struct_liste_chainee *)
1674: l_element_base);
1675: }
1676: else // type == 'P'
1677: {
1678: incrementation_atomique(s_objet);
1679: l_element_courant = (*s_objet).objet;
1680:
1681: while(l_element_courant != NULL)
1682: {
1683: (*l_element_courant).donnee = copie_objet(s_etat_processus,
1684: (*l_element_courant).donnee, 'P');
1685: l_element_courant = (*l_element_courant).suivant;
1686: }
1687:
1688: return(s_objet);
1689: }
1690:
1691: break;
1692: }
1693:
1694: case BIN :
1695: {
1696: if (type != 'O')
1697: {
1698: incrementation_atomique(s_objet);
1699: return(s_objet);
1700: }
1701:
1702: if ((s_nouvel_objet = allocation(s_etat_processus, BIN)) == NULL)
1703: {
1704: return(NULL);
1705: }
1706:
1707: (*((logical8 *) ((*s_nouvel_objet).objet))) =
1708: (*((logical8 *) ((*s_objet).objet)));
1709: break;
1710: }
1711:
1712: case CHN :
1713: {
1714: if (type != 'O')
1715: {
1716: incrementation_atomique(s_objet);
1717: return(s_objet);
1718: }
1719:
1720: if ((s_nouvel_objet = allocation(s_etat_processus, CHN)) == NULL)
1721: {
1722: return(NULL);
1723: }
1724:
1725: (*s_nouvel_objet).objet = (void *) ((unsigned char *)
1726: malloc((strlen((unsigned char *) ((*s_objet).objet)) + 1)
1727: * sizeof(unsigned char)));
1728:
1729: if ((*s_nouvel_objet).objet == NULL)
1730: {
1731: free(s_nouvel_objet);
1732: return(NULL);
1733: }
1734:
1735: strcpy((unsigned char *) ((*s_nouvel_objet).objet),
1736: (unsigned char *) ((*s_objet).objet));
1737: break;
1738: }
1739:
1740: case CPL :
1741: {
1742: if (type != 'O')
1743: {
1744: incrementation_atomique(s_objet);
1745: return(s_objet);
1746: }
1747:
1748: if ((s_nouvel_objet = allocation(s_etat_processus, CPL)) == NULL)
1749: {
1750: return(NULL);
1751: }
1752:
1753: (*((struct_complexe16 *) ((*s_nouvel_objet).objet))) =
1754: (*((struct_complexe16 *) ((*s_objet).objet)));
1755: break;
1756: }
1757:
1758: case RPN :
1759: {
1760: if (type != 'P')
1761: {
1762: if ((s_nouvel_objet = allocation(s_etat_processus, RPN))
1763: == NULL)
1764: {
1765: return(NULL);
1766: }
1767:
1768: l_element_courant_lecture = (struct_liste_chainee *)
1769: ((*s_objet).objet);
1770:
1771: l_element_base = NULL;
1772: l_element_courant_ecriture = l_element_base;
1773:
1774: while(l_element_courant_lecture != NULL)
1775: {
1776: s_objet_tampon = copie_objet(s_etat_processus,
1777: (*l_element_courant_lecture).donnee, type);
1778: l_element_suivant_ecriture = (struct_liste_chainee *)
1779: malloc(sizeof(struct_liste_chainee));
1780:
1781: if ((s_objet_tampon == NULL) ||
1782: (l_element_suivant_ecriture == NULL))
1783: {
1784: l_element_courant_lecture = (struct_liste_chainee *)
1785: ((*s_nouvel_objet).objet);
1786:
1787: while(l_element_courant_lecture != NULL)
1788: {
1789: l_element_suivant_lecture =
1790: (*l_element_courant_lecture).suivant;
1791: liberation(s_etat_processus,
1792: (*l_element_courant_lecture).donnee);
1793: free(l_element_courant_lecture);
1794: l_element_courant_lecture =
1795: l_element_suivant_lecture;
1796: }
1797:
1798: return(NULL);
1799: }
1800:
1801: if (l_element_courant_ecriture == NULL)
1802: {
1803: l_element_base = l_element_suivant_ecriture;
1804: }
1805: else
1806: {
1807: (*l_element_courant_ecriture).suivant =
1808: l_element_suivant_ecriture;
1809: }
1810:
1811: l_element_courant_ecriture = l_element_suivant_ecriture;
1812:
1813: (*l_element_courant_ecriture).donnee = s_objet_tampon;
1814: (*l_element_courant_ecriture).suivant = NULL;
1815: l_element_courant_lecture =
1816: (*l_element_courant_lecture).suivant;
1817: }
1818:
1819: (*s_nouvel_objet).objet = (void *) ((struct_liste_chainee *)
1820: l_element_base);
1821: }
1822: else // type == 'P'
1823: {
1824: incrementation_atomique(s_objet);
1825: l_element_courant = (*s_objet).objet;
1826:
1827: while(l_element_courant != NULL)
1828: {
1829: (*l_element_courant).donnee = copie_objet(s_etat_processus,
1830: (*l_element_courant).donnee, 'P');
1831: l_element_courant = (*l_element_courant).suivant;
1832: }
1833:
1834: return(s_objet);
1835: }
1836:
1837: break;
1838: }
1839:
1840: case FCH :
1841: {
1842: if (type == 'P')
1843: {
1844: incrementation_atomique(s_objet);
1845:
1846: if (((*((struct_fichier *) ((*s_objet).objet))).format =
1847: copie_objet(s_etat_processus, (*((struct_fichier *)
1848: ((*s_objet).objet))).format, 'P')) == NULL)
1849: {
1850: return(NULL);
1851: }
1852:
1853: return(s_objet);
1854: }
1855:
1856: if ((s_nouvel_objet = allocation(s_etat_processus, FCH)) == NULL)
1857: {
1858: return(NULL);
1859: }
1860:
1861: (*((struct_fichier *) ((*s_nouvel_objet).objet))).descripteur =
1862: (*((struct_fichier *) ((*s_objet).objet))).descripteur;
1863: (*((struct_fichier *) ((*s_nouvel_objet).objet))).acces =
1864: (*((struct_fichier *) ((*s_objet).objet))).acces;
1865: (*((struct_fichier *) ((*s_nouvel_objet).objet))).binaire =
1866: (*((struct_fichier *) ((*s_objet).objet))).binaire;
1867: (*((struct_fichier *) ((*s_nouvel_objet).objet))).ouverture =
1868: (*((struct_fichier *) ((*s_objet).objet))).ouverture;
1869: (*((struct_fichier *) ((*s_nouvel_objet).objet))).protection =
1870: (*((struct_fichier *) ((*s_objet).objet))).protection;
1871: (*((struct_fichier *) ((*s_nouvel_objet).objet)))
1872: .position_clef = (*((struct_fichier *)
1873: ((*s_objet).objet))).position_clef;
1874: (*((struct_fichier *) ((*s_nouvel_objet).objet))).pid =
1875: (*((struct_fichier *) ((*s_objet).objet))).pid;
1876: (*((struct_fichier *) ((*s_nouvel_objet).objet))).tid =
1877: (*((struct_fichier *) ((*s_objet).objet))).tid;
1878:
1879: if (((*((struct_fichier *) ((*s_nouvel_objet).objet))).format =
1880: copie_objet(s_etat_processus, (*((struct_fichier *)
1881: ((*s_objet).objet))).format, type)) == NULL)
1882: {
1883: free((*s_nouvel_objet).objet);
1884: free(s_nouvel_objet);
1885: return(NULL);
1886: }
1887:
1888: if (((*((struct_fichier *) ((*s_nouvel_objet).objet))).nom =
1889: (unsigned char *) malloc((strlen((*((struct_fichier *)
1890: ((*s_objet).objet))).nom) + 1) * sizeof(unsigned char)))
1891: == NULL)
1892: {
1893: liberation(s_etat_processus, (*((struct_fichier *)
1894: (*s_nouvel_objet).objet)).format);
1895: free((*s_nouvel_objet).objet);
1896: free(s_nouvel_objet);
1897: return(NULL);
1898: }
1899:
1900: strcpy((*((struct_fichier *) ((*s_nouvel_objet).objet))).nom,
1901: (*((struct_fichier *) ((*s_objet).objet))).nom);
1902: break;
1903: }
1904:
1905: case FCT :
1906: {
1907: if (type != 'O')
1908: {
1909: /*
1910: * Remise à zéro de la prédiction pour respecter la cohérence
1911: * du saut dans les cas EXSUB et OBSUB.
1912: */
1913:
1914: (*((struct_fonction *) ((*s_objet).objet)))
1915: .prediction_saut = NULL;
1916: incrementation_atomique(s_objet);
1917: return(s_objet);
1918: }
1919:
1920: if ((s_nouvel_objet = allocation(s_etat_processus, FCT)) == NULL)
1921: {
1922: return(NULL);
1923: }
1924:
1925: if (((*((struct_fonction *) ((*s_nouvel_objet).objet)))
1926: .nom_fonction = (unsigned char *)
1927: malloc((strlen((*((struct_fonction *)
1928: ((*s_objet).objet))).nom_fonction) + 1) *
1929: sizeof(unsigned char))) == NULL)
1930: {
1931: free(s_nouvel_objet);
1932: return(NULL);
1933: }
1934:
1935: strcpy((unsigned char *) (*((struct_fonction *)
1936: ((*s_nouvel_objet).objet))).nom_fonction,
1937: (unsigned char *) (*((struct_fonction *)
1938: ((*s_objet).objet))).nom_fonction);
1939: (*((struct_fonction *) ((*s_nouvel_objet).objet)))
1940: .nombre_arguments = (*((struct_fonction *)
1941: ((*s_objet).objet))).nombre_arguments;
1942: (*((struct_fonction *) ((*s_nouvel_objet).objet))).fonction =
1943: (*((struct_fonction *) ((*s_objet).objet))).fonction;
1944: break;
1945: }
1946:
1947: case INT :
1948: {
1949: if (type != 'O')
1950: {
1951: incrementation_atomique(s_objet);
1952: return(s_objet);
1953: }
1954:
1955: if ((s_nouvel_objet = allocation(s_etat_processus, INT)) == NULL)
1956: {
1957: return(NULL);
1958: }
1959:
1960: (*((integer8 *) ((*s_nouvel_objet).objet))) =
1961: (*((integer8 *) ((*s_objet).objet)));
1962: break;
1963: }
1964:
1965: case LST :
1966: {
1967: if (type != 'P')
1968: {
1969: if ((s_nouvel_objet = allocation(s_etat_processus, LST))
1970: == NULL)
1971: {
1972: return(NULL);
1973: }
1974:
1975: l_element_courant_lecture = (struct_liste_chainee *)
1976: ((*s_objet).objet);
1977:
1978: l_element_base = NULL;
1979: l_element_courant_ecriture = l_element_base;
1980:
1981: while(l_element_courant_lecture != NULL)
1982: {
1983: s_objet_tampon = copie_objet(s_etat_processus,
1984: (*l_element_courant_lecture).donnee, type);
1985: l_element_suivant_ecriture = (struct_liste_chainee *)
1986: malloc(sizeof(struct_liste_chainee));
1987:
1988: if ((s_objet_tampon == NULL) ||
1989: (l_element_suivant_ecriture == NULL))
1990: {
1991: l_element_courant_lecture = (struct_liste_chainee *)
1992: ((*s_nouvel_objet).objet);
1993:
1994: while(l_element_courant_lecture != NULL)
1995: {
1996: l_element_suivant_lecture =
1997: (*l_element_courant_lecture).suivant;
1998: liberation(s_etat_processus,
1999: (*l_element_courant_lecture).donnee);
2000: free(l_element_courant_lecture);
2001: l_element_courant_lecture =
2002: l_element_suivant_lecture;
2003: }
2004:
2005: return(NULL);
2006: }
2007:
2008: if (l_element_courant_ecriture == NULL)
2009: {
2010: l_element_base = l_element_suivant_ecriture;
2011: }
2012: else
2013: {
2014: (*l_element_courant_ecriture).suivant =
2015: l_element_suivant_ecriture;
2016: }
2017:
2018: l_element_courant_ecriture = l_element_suivant_ecriture;
2019:
2020: (*l_element_courant_ecriture).donnee = s_objet_tampon;
2021: (*l_element_courant_ecriture).suivant = NULL;
2022: l_element_courant_lecture =
2023: (*l_element_courant_lecture).suivant;
2024: }
2025:
2026: (*s_nouvel_objet).objet = (void *) ((struct_liste_chainee *)
2027: l_element_base);
2028: }
2029: else
2030: {
2031: incrementation_atomique(s_objet);
2032: l_element_courant = (*s_objet).objet;
2033:
2034: while(l_element_courant != NULL)
2035: {
2036: (*l_element_courant).donnee = copie_objet(s_etat_processus,
2037: (*l_element_courant).donnee, 'P');
2038: l_element_courant = (*l_element_courant).suivant;
2039: }
2040:
2041: return(s_objet);
2042: }
2043:
2044: break;
2045: }
2046:
2047: case MIN :
2048: {
2049: if (type != 'O')
2050: {
2051: incrementation_atomique(s_objet);
2052: return(s_objet);
2053: }
2054:
2055: if ((s_nouvel_objet = allocation(s_etat_processus, MIN)) == NULL)
2056: {
2057: return(NULL);
2058: }
2059:
2060: (*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau =
2061: (void **) ((integer8 **) malloc(
2062: ((*((struct_matrice *) ((*s_objet).objet))).nombre_lignes)
2063: * sizeof(integer8 *)));
2064:
2065: if ((*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau
2066: == NULL)
2067: {
2068: free((*s_nouvel_objet).objet);
2069: free(s_nouvel_objet);
2070: return(NULL);
2071: }
2072:
2073: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_colonnes =
2074: (*((struct_matrice *) ((*s_objet).objet))).nombre_colonnes;
2075: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_lignes =
2076: (*((struct_matrice *) ((*s_objet).objet))).nombre_lignes;
2077: (*((struct_matrice *) ((*s_nouvel_objet).objet))).type =
2078: (*((struct_matrice *) ((*s_objet).objet))).type;
2079:
2080: for(i = 0; i < (*((struct_matrice *)
2081: ((*s_objet).objet))).nombre_lignes; i++)
2082: {
2083: if ((((integer8 **) ((*((struct_matrice *)
2084: ((*s_nouvel_objet).objet))).tableau))[i] =
2085: (void *) ((integer8 *) malloc(
2086: ((*((struct_matrice *) ((*s_objet).objet)))
2087: .nombre_colonnes) * sizeof(integer8)))) == NULL)
2088: {
2089: for(j = 0; j < i; j++)
2090: {
2091: free(((integer8 **) ((*((struct_matrice *)
2092: ((*s_nouvel_objet).objet))).tableau))[j]);
2093: }
2094:
2095: free((*s_nouvel_objet).objet);
2096: free(s_nouvel_objet);
2097: return(NULL);
2098: }
2099:
2100: for(j = 0; j < (*((struct_matrice *)
2101: ((*s_objet).objet))).nombre_colonnes; j++)
2102: {
2103: ((integer8 **) ((*((struct_matrice *)
2104: ((*s_nouvel_objet).objet))).tableau))[i][j] =
2105: ((integer8 **) ((*((struct_matrice *)
2106: ((*s_objet).objet))).tableau))[i][j];
2107: }
2108: }
2109:
2110: break;
2111: }
2112:
2113: case MCX :
2114: {
2115: if (type != 'O')
2116: {
2117: incrementation_atomique(s_objet);
2118: return(s_objet);
2119: }
2120:
2121: if ((s_nouvel_objet = allocation(s_etat_processus, MCX))
2122: == NULL)
2123: {
2124: return(NULL);
2125: }
2126:
2127: (*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau =
2128: (void **) ((struct_complexe16 **) malloc(
2129: ((*((struct_matrice *) ((*s_objet).objet))).nombre_lignes)
2130: * sizeof(struct_complexe16 *)));
2131:
2132: if ((*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau
2133: == NULL)
2134: {
2135: free((*s_nouvel_objet).objet);
2136: free(s_nouvel_objet);
2137: return(NULL);
2138: }
2139:
2140: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_colonnes =
2141: (*((struct_matrice *) ((*s_objet).objet))).nombre_colonnes;
2142: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_lignes =
2143: (*((struct_matrice *) ((*s_objet).objet))).nombre_lignes;
2144: (*((struct_matrice *) ((*s_nouvel_objet).objet))).type =
2145: (*((struct_matrice *) ((*s_objet).objet))).type;
2146:
2147: for(i = 0; i < (*((struct_matrice *)
2148: ((*s_objet).objet))).nombre_lignes; i++)
2149: {
2150: if ((((struct_complexe16 **) ((*((struct_matrice *)
2151: ((*s_nouvel_objet).objet))).tableau))[i] =
2152: (void *) ((struct_complexe16 *) malloc(
2153: ((*((struct_matrice *) ((*s_objet).objet)))
2154: .nombre_colonnes) * sizeof(struct_complexe16))))
2155: == NULL)
2156: {
2157: for(j = 0; j < i; j++)
2158: {
2159: free(((struct_complexe16 **) ((*((struct_matrice *)
2160: ((*s_nouvel_objet).objet))).tableau))[j]);
2161: }
2162:
2163: free((*s_nouvel_objet).objet);
2164: free(s_nouvel_objet);
2165: return(NULL);
2166: }
2167:
2168: for(j = 0; j < (*((struct_matrice *)
2169: ((*s_objet).objet))).nombre_colonnes; j++)
2170: {
2171: ((struct_complexe16 **) ((*((struct_matrice *)
2172: ((*s_nouvel_objet).objet))).tableau))[i][j] =
2173: ((struct_complexe16 **) ((*((struct_matrice *)
2174: ((*s_objet).objet))).tableau))[i][j];
2175: }
2176: }
2177:
2178: break;
2179: }
2180:
2181: case MRL :
2182: {
2183: if (type != 'O')
2184: {
2185: incrementation_atomique(s_objet);
2186: return(s_objet);
2187: }
2188:
2189: if ((s_nouvel_objet = allocation(s_etat_processus, MRL)) == NULL)
2190: {
2191: return(NULL);
2192: }
2193:
2194: (*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau =
2195: (void **) ((real8 **) malloc(
2196: ((*((struct_matrice *) ((*s_objet).objet))).nombre_lignes)
2197: * sizeof(real8 *)));
2198:
2199: if ((*((struct_matrice *) ((*s_nouvel_objet).objet))).tableau
2200: == NULL)
2201: {
2202: free((*s_nouvel_objet).objet);
2203: free(s_nouvel_objet);
2204: return(NULL);
2205: }
2206:
2207: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_colonnes =
2208: (*((struct_matrice *) ((*s_objet).objet))).nombre_colonnes;
2209: (*((struct_matrice *) ((*s_nouvel_objet).objet))).nombre_lignes =
2210: (*((struct_matrice *) ((*s_objet).objet))).nombre_lignes;
2211: (*((struct_matrice *) ((*s_nouvel_objet).objet))).type =
2212: (*((struct_matrice *) ((*s_objet).objet))).type;
2213:
2214: for(i = 0; i < (*((struct_matrice *)
2215: ((*s_objet).objet))).nombre_lignes; i++)
2216: {
2217: if ((((real8 **) ((*((struct_matrice *)
2218: ((*s_nouvel_objet).objet))).tableau))[i] =
2219: (void *) ((real8 *) malloc(
2220: ((*((struct_matrice *) ((*s_objet).objet)))
2221: .nombre_colonnes) * sizeof(real8)))) == NULL)
2222: {
2223: for(j = 0; j < i; j++)
2224: {
2225: free(((real8 **) ((*((struct_matrice *)
2226: ((*s_nouvel_objet).objet))).tableau))[j]);
2227: }
2228:
2229: free((*s_nouvel_objet).objet);
2230: free(s_nouvel_objet);
2231: return(NULL);
2232: }
2233:
2234: for(j = 0; j < (*((struct_matrice *)
2235: ((*s_objet).objet))).nombre_colonnes; j++)
2236: {
2237: ((real8 **) ((*((struct_matrice *)
2238: ((*s_nouvel_objet).objet))).tableau))[i][j] =
2239: ((real8 **) ((*((struct_matrice *)
2240: ((*s_objet).objet))).tableau))[i][j];
2241: }
2242: }
2243:
2244: break;
2245: }
2246:
2247: case MTX :
2248: {
2249: // La duplication d'un mutex renvoie le même objet.
2250: incrementation_atomique(s_objet);
2251: return(s_objet);
2252: }
2253:
2254: case NOM :
2255: {
2256: if (type != 'O')
2257: {
2258: incrementation_atomique(s_objet);
2259: return(s_objet);
2260: }
2261:
2262: if ((s_nouvel_objet = allocation(s_etat_processus, NOM)) == NULL)
2263: {
2264: return(NULL);
2265: }
2266:
2267: (*((struct_nom *) (*s_nouvel_objet).objet)).nom = malloc((
2268: strlen((*((struct_nom *) (*s_objet).objet)).nom) + 1) *
2269: sizeof(unsigned char));
2270:
2271: if ((*((struct_nom *) (*s_nouvel_objet).objet)).nom == NULL)
2272: {
2273: free((*s_nouvel_objet).objet);
2274: free(s_nouvel_objet);
2275: return(NULL);
2276: }
2277:
2278: strcpy((*((struct_nom *) (*s_nouvel_objet).objet)).nom,
2279: (*((struct_nom *) (*s_objet).objet)).nom);
2280: (*((struct_nom *) (*s_nouvel_objet).objet)).symbole =
2281: (*((struct_nom *) (*s_objet).objet)).symbole;
2282: break;
2283: }
2284:
2285: case NON :
2286: {
2287: if (type != 'O')
2288: {
2289: incrementation_atomique(s_objet);
2290: return(s_objet);
2291: }
2292:
2293: // Un objet de type NON est un objet encapsulé dans une
2294: // structure de type struct_objet. Elle peut très bien contenir
2295: // une donnée, mais c'est à l'utilisateur de la libérer
2296: // explicitement avec un free().
2297:
2298: if ((s_nouvel_objet = allocation(s_etat_processus, NON)) == NULL)
2299: {
2300: return(NULL);
2301: }
2302:
2303: (*s_nouvel_objet).objet = (*s_objet).objet;
2304: break;
2305: }
2306:
2307: case PRC :
2308: {
2309: if (pthread_mutex_lock(&((*(*((struct_processus_fils *)
2310: (*s_objet).objet)).thread).mutex_nombre_references)) != 0)
2311: {
2312: return(NULL);
2313: }
2314:
2315: (*(*((struct_processus_fils *) (*s_objet).objet)).thread)
2316: .nombre_references++;
2317:
2318: if (pthread_mutex_unlock(&((*(*((struct_processus_fils *)
2319: (*s_objet).objet)).thread).mutex_nombre_references)) != 0)
2320: {
2321: return(NULL);
2322: }
2323:
2324: if (type != 'O')
2325: {
2326: incrementation_atomique(s_objet);
2327: return(s_objet);
2328: }
2329:
2330: if ((s_nouvel_objet = allocation(s_etat_processus, PRC)) == NULL)
2331: {
2332: return(NULL);
2333: }
2334:
2335: (*((struct_processus_fils *) (*s_nouvel_objet).objet)) =
2336: (*((struct_processus_fils *) (*s_objet).objet));
2337: break;
2338: }
2339:
2340: case REL :
2341: {
2342: if (type != 'O')
2343: {
2344: incrementation_atomique(s_objet);
2345: return(s_objet);
2346: }
2347:
2348: if ((s_nouvel_objet = allocation(s_etat_processus, REL)) == NULL)
2349: {
2350: return(NULL);
2351: }
2352:
2353: (*((real8 *) ((*s_nouvel_objet).objet))) =
2354: (*((real8 *) ((*s_objet).objet)));
2355: break;
2356: }
2357:
2358: case SCK :
2359: {
2360: if (type == 'P')
2361: {
2362: incrementation_atomique(s_objet);
2363:
2364: if (((*((struct_socket *) ((*s_objet).objet)))
2365: .format = copie_objet(s_etat_processus,
2366: (*((struct_socket *) ((*s_objet).objet))).format, 'P'))
2367: == NULL)
2368: {
2369: return(NULL);
2370: }
2371:
2372: return(s_objet);
2373: }
2374:
2375: if ((s_nouvel_objet = allocation(s_etat_processus, SCK)) == NULL)
2376: {
2377: return(NULL);
2378: }
2379:
2380: (*((struct_socket *) ((*s_nouvel_objet).objet))).socket =
2381: (*((struct_socket *) ((*s_objet).objet))).socket;
2382: (*((struct_socket *) ((*s_nouvel_objet).objet))).domaine =
2383: (*((struct_socket *) ((*s_objet).objet))).domaine;
2384: (*((struct_socket *) ((*s_nouvel_objet).objet))).socket_en_ecoute =
2385: (*((struct_socket *) ((*s_objet).objet))).socket_en_ecoute;
2386: (*((struct_socket *) ((*s_nouvel_objet).objet))).socket_connectee =
2387: (*((struct_socket *) ((*s_objet).objet))).socket_connectee;
2388: (*((struct_socket *) ((*s_nouvel_objet).objet))).pid =
2389: (*((struct_socket *) ((*s_objet).objet))).pid;
2390: (*((struct_socket *) ((*s_nouvel_objet).objet))).binaire =
2391: (*((struct_socket *) ((*s_objet).objet))).binaire;
2392: (*((struct_socket *) ((*s_nouvel_objet).objet))).effacement =
2393: (*((struct_socket *) ((*s_objet).objet))).effacement;
2394: (*((struct_socket *) ((*s_nouvel_objet).objet))).protection =
2395: (*((struct_socket *) ((*s_objet).objet))).protection;
2396: (*((struct_socket *) ((*s_nouvel_objet).objet))).localisation =
2397: (*((struct_socket *) ((*s_objet).objet))).localisation;
2398: (*((struct_socket *) ((*s_nouvel_objet).objet))).pid =
2399: (*((struct_socket *) ((*s_objet).objet))).pid;
2400: (*((struct_socket *) ((*s_nouvel_objet).objet))).tid =
2401: (*((struct_socket *) ((*s_objet).objet))).tid;
2402:
2403: if (((*((struct_socket *) ((*s_nouvel_objet).objet))).format =
2404: copie_objet(s_etat_processus, (*((struct_socket *)
2405: ((*s_objet).objet))).format, type)) == NULL)
2406: {
2407: free((*s_nouvel_objet).objet);
2408: free(s_nouvel_objet);
2409: return(NULL);
2410: }
2411:
2412: if (((*((struct_socket *) ((*s_nouvel_objet).objet))).adresse =
2413: (unsigned char *) malloc((strlen((*((struct_socket *)
2414: ((*s_objet).objet))).adresse) + 1) * sizeof(unsigned char)))
2415: == NULL)
2416: {
2417: liberation(s_etat_processus, (*((struct_fichier *)
2418: (*s_nouvel_objet).objet)).format);
2419: free((*s_nouvel_objet).objet);
2420: free(s_nouvel_objet);
2421: return(NULL);
2422: }
2423:
2424: strcpy((*((struct_socket *) ((*s_nouvel_objet).objet)))
2425: .adresse, (*((struct_socket *) ((*s_objet).objet)))
2426: .adresse);
2427:
2428: if (((*((struct_socket *) ((*s_nouvel_objet).objet)))
2429: .adresse_distante = malloc((strlen((*((struct_socket *)
2430: ((*s_objet).objet))).adresse_distante) + 1) *
2431: sizeof(unsigned char))) == NULL)
2432: {
2433: liberation(s_etat_processus, (*((struct_fichier *)
2434: (*s_nouvel_objet).objet)).format);
2435: free((*s_nouvel_objet).objet);
2436: free(s_nouvel_objet);
2437: return(NULL);
2438: }
2439:
2440: strcpy((*((struct_socket *) ((*s_nouvel_objet).objet)))
2441: .adresse_distante, (*((struct_socket *) ((*s_objet).objet)))
2442: .adresse_distante);
2443:
2444: strcpy((*((struct_socket *) ((*s_nouvel_objet).objet))).type,
2445: (*((struct_socket *) ((*s_objet).objet))).type);
2446: break;
2447: }
2448:
2449: case SLB :
2450: {
2451: if (type != 'O')
2452: {
2453: incrementation_atomique(s_objet);
2454: return(s_objet);
2455: }
2456:
2457: if ((s_nouvel_objet = allocation(s_etat_processus, SLB)) == NULL)
2458: {
2459: return(NULL);
2460: }
2461:
2462: if (((*((struct_bibliotheque *) ((*s_nouvel_objet).objet))).nom =
2463: (unsigned char *) malloc((strlen((*((struct_bibliotheque *)
2464: ((*s_objet).objet))).nom) + 1) * sizeof(unsigned char)))
2465: == NULL)
2466: {
2467: free((*s_nouvel_objet).objet);
2468: free(s_nouvel_objet);
2469: return(NULL);
2470: }
2471:
2472: strcpy((*((struct_bibliotheque *) ((*s_nouvel_objet).objet))).nom,
2473: (*((struct_bibliotheque *) ((*s_objet).objet))).nom);
2474:
2475: /*
2476: * C'est objet est non modifiable et est un pointeur
2477: * sur un objet système. Seul la référence est copiée.
2478: */
2479:
2480: (*((struct_bibliotheque *) (*s_nouvel_objet).objet)).descripteur =
2481: (*((struct_bibliotheque *) (*s_objet).objet)).descripteur;
2482: (*((struct_bibliotheque *) (*s_nouvel_objet).objet)).pid =
2483: (*((struct_bibliotheque *) (*s_objet).objet)).pid;
2484: (*((struct_bibliotheque *) (*s_nouvel_objet).objet)).tid =
2485: (*((struct_bibliotheque *) (*s_objet).objet)).tid;
2486: break;
2487: }
2488:
2489: case SPH :
2490: {
2491: if (type != 'O')
2492: {
2493: incrementation_atomique(s_objet);
2494: return(s_objet);
2495: }
2496:
2497: if ((s_nouvel_objet = allocation(s_etat_processus, SPH)) == NULL)
2498: {
2499: return(NULL);
2500: }
2501:
2502: if (((*((struct_semaphore *) (*s_nouvel_objet).objet)).nom =
2503: malloc((strlen((*((struct_semaphore *) (*s_objet).objet))
2504: .nom) + 1) * sizeof(unsigned char))) == NULL)
2505: {
2506: free((*s_nouvel_objet).objet);
2507: free(s_nouvel_objet);
2508: return(NULL);
2509: }
2510:
2511: (*((struct_semaphore *) (*s_nouvel_objet).objet)).semaphore =
2512: (*((struct_semaphore *) (*s_objet).objet)).semaphore;
2513: strcpy((*((struct_semaphore *) (*s_nouvel_objet).objet)).nom,
2514: (*((struct_semaphore *) (*s_objet).objet)).nom);
2515: break;
2516: }
2517:
2518: case SQL :
2519: {
2520: if (type != 'O')
2521: {
2522: incrementation_atomique(s_objet);
2523: return(s_objet);
2524: }
2525:
2526: if ((s_nouvel_objet = allocation(s_etat_processus, SQL)) == NULL)
2527: {
2528: return(NULL);
2529: }
2530:
2531: (*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).pid =
2532: (*((struct_connecteur_sql *) (*s_objet).objet)).pid;
2533: (*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).tid =
2534: (*((struct_connecteur_sql *) (*s_objet).objet)).tid;
2535: (*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).descripteur =
2536: (*((struct_connecteur_sql *) (*s_objet).objet)).descripteur;
2537:
2538: if (((*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).type =
2539: malloc((strlen((*((struct_connecteur_sql *)
2540: (*s_objet).objet)).type) + 1) * sizeof(unsigned char)))
2541: == NULL)
2542: {
2543: free(s_nouvel_objet);
2544: return(NULL);
2545: }
2546:
2547: strcpy((*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).type,
2548: (*((struct_connecteur_sql *) (*s_objet).objet)).type);
2549:
2550: if ((*((struct_connecteur_sql *) (*s_objet).objet)).locale != NULL)
2551: {
2552: if (((*((struct_connecteur_sql *) (*s_nouvel_objet).objet))
2553: .locale = malloc((strlen((*((struct_connecteur_sql *)
2554: (*s_objet).objet)).locale) + 1) *
2555: sizeof(unsigned char))) == NULL)
2556: {
2557: free((*((struct_connecteur_sql *) (*s_nouvel_objet).objet))
2558: .locale);
2559: free(s_nouvel_objet);
2560: return(NULL);
2561: }
2562:
2563: strcpy((*((struct_connecteur_sql *) (*s_nouvel_objet).objet))
2564: .locale, (*((struct_connecteur_sql *)
2565: (*s_objet).objet)).locale);
2566: }
2567: else
2568: {
2569: (*((struct_connecteur_sql *) (*s_nouvel_objet).objet)).locale
2570: = NULL;
2571: }
2572:
2573: break;
2574: }
2575:
2576: case TBL :
2577: {
2578: if (type != 'P')
2579: {
2580: if ((s_nouvel_objet = allocation(s_etat_processus, TBL))
2581: == NULL)
2582: {
2583: return(NULL);
2584: }
2585:
2586: (*((struct_tableau *) (*s_nouvel_objet).objet))
2587: .nombre_elements = (*((struct_tableau *)
2588: (*s_objet).objet)).nombre_elements;
2589:
2590: if (((*((struct_tableau *) (*s_nouvel_objet).objet)).elements =
2591: malloc((*((struct_tableau *) (*s_objet).objet))
2592: .nombre_elements * sizeof(struct_objet *))) == NULL)
2593: {
2594: return(NULL);
2595: }
2596:
2597: for(i = 0; i < (*((struct_tableau *) (*s_objet).objet))
2598: .nombre_elements; i++)
2599: {
2600: if (((*((struct_tableau *) (*s_nouvel_objet).objet))
2601: .elements[i] = copie_objet(s_etat_processus,
2602: (*((struct_tableau *) (*s_objet).objet))
2603: .elements[i], type)) == NULL)
2604: {
2605: for(j = 0; j < i; j++)
2606: {
2607: liberation(s_etat_processus, (*((struct_tableau *)
2608: (*s_nouvel_objet).objet)).elements[j]);
2609: }
2610:
2611: free((*((struct_tableau *) (*s_nouvel_objet).objet))
2612: .elements);
2613: free((*s_nouvel_objet).objet);
2614: free(s_nouvel_objet);
2615:
2616: return(NULL);
2617: }
2618: }
2619: }
2620: else
2621: {
2622: incrementation_atomique(s_objet);
2623:
2624: for(i = 0; i < (*((struct_tableau *) (*s_objet).objet))
2625: .nombre_elements; i++)
2626: {
2627: (*((struct_tableau *) (*s_objet).objet)).elements[i] =
2628: copie_objet(s_etat_processus, (*((struct_tableau *)
2629: (*s_objet).objet)).elements[i], 'P');
2630: }
2631:
2632: return(s_objet);
2633: }
2634:
2635: break;
2636: }
2637:
2638: case VIN :
2639: {
2640: if (type != 'O')
2641: {
2642: incrementation_atomique(s_objet);
2643: return(s_objet);
2644: }
2645:
2646: if ((s_nouvel_objet = allocation(s_etat_processus, VIN)) == NULL)
2647: {
2648: return(NULL);
2649: }
2650:
2651: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau =
2652: (void *) ((integer8 *) malloc(
2653: ((*((struct_vecteur *) ((*s_objet).objet))).taille)
2654: * sizeof(integer8)));
2655:
2656: if ((*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau
2657: == NULL)
2658: {
2659: free((*s_nouvel_objet).objet);
2660: free(s_nouvel_objet);
2661: return(NULL);
2662: }
2663:
2664: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).taille =
2665: (*((struct_vecteur *) ((*s_objet).objet))).taille;
2666: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).type =
2667: (*((struct_vecteur *) ((*s_objet).objet))).type;
2668:
2669: for(i = 0; i < (*((struct_vecteur *) ((*s_objet).objet))).taille;
2670: i++)
2671: {
2672: ((integer8 *) ((*((struct_vecteur *)
2673: ((*s_nouvel_objet).objet))).tableau))[i] =
2674: ((integer8 *) ((*((struct_vecteur *)
2675: ((*s_objet).objet))).tableau))[i];
2676: }
2677:
2678: break;
2679: }
2680:
2681: case VCX :
2682: {
2683: if (type != 'O')
2684: {
2685: incrementation_atomique(s_objet);
2686: return(s_objet);
2687: }
2688:
2689: if ((s_nouvel_objet = allocation(s_etat_processus, VCX)) == NULL)
2690: {
2691: return(NULL);
2692: }
2693:
2694: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau =
2695: (void *) ((struct_complexe16 *) malloc(
2696: ((*((struct_vecteur *) ((*s_objet).objet))).taille)
2697: * sizeof(struct_complexe16)));
2698:
2699: if ((*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau
2700: == NULL)
2701: {
2702: free((*s_nouvel_objet).objet);
2703: free(s_nouvel_objet);
2704: return(NULL);
2705: }
2706:
2707: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).taille =
2708: (*((struct_vecteur *) ((*s_objet).objet))).taille;
2709: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).type =
2710: (*((struct_vecteur *) ((*s_objet).objet))).type;
2711:
2712: for(i = 0; i < (*((struct_vecteur *) ((*s_objet).objet))).taille;
2713: i++)
2714: {
2715: ((struct_complexe16 *) ((*((struct_vecteur *)
2716: ((*s_nouvel_objet).objet))).tableau))[i] =
2717: ((struct_complexe16 *) ((*((struct_vecteur *)
2718: ((*s_objet).objet))).tableau))[i];
2719: }
2720:
2721: break;
2722: }
2723:
2724: case VRL :
2725: {
2726: if (type != 'O')
2727: {
2728: incrementation_atomique(s_objet);
2729: return(s_objet);
2730: }
2731:
2732: if ((s_nouvel_objet = allocation(s_etat_processus, VRL)) == NULL)
2733: {
2734: return(NULL);
2735: }
2736:
2737: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau =
2738: (void *) ((real8 *) malloc(
2739: ((*((struct_vecteur *) ((*s_objet).objet))).taille)
2740: * sizeof(real8)));
2741:
2742: if ((*((struct_vecteur *) ((*s_nouvel_objet).objet))).tableau
2743: == NULL)
2744: {
2745: free((*s_nouvel_objet).objet);
2746: free(s_nouvel_objet);
2747: return(NULL);
2748: }
2749:
2750: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).taille =
2751: (*((struct_vecteur *) ((*s_objet).objet))).taille;
2752: (*((struct_vecteur *) ((*s_nouvel_objet).objet))).type =
2753: (*((struct_vecteur *) ((*s_objet).objet))).type;
2754:
2755: for(i = 0; i < (*((struct_vecteur *) ((*s_objet).objet))).taille;
2756: i++)
2757: {
2758: ((real8 *) ((*((struct_vecteur *)
2759: ((*s_nouvel_objet).objet))).tableau))[i] =
2760: ((real8 *) ((*((struct_vecteur *)
2761: ((*s_objet).objet))).tableau))[i];
2762: }
2763:
2764: break;
2765: }
2766:
2767: default :
2768: {
2769: return(NULL);
2770: }
2771: }
2772:
2773: return(s_nouvel_objet);
2774:
2775: #undef return
2776: }
2777:
2778:
2779: /*
2780: ================================================================================
2781: Routine de copie d'une structure de description d'un processus
2782: ================================================================================
2783: Entrées : pointeur sur la structure de description d'un processus
2784: --------------------------------------------------------------------------------
2785: Sorties : structure identique (tous les objets sont copiés)
2786: --------------------------------------------------------------------------------
2787: Effets de bord : néant
2788: ================================================================================
2789: */
2790:
2791: struct_processus *
2792: copie_etat_processus(struct_processus *s_etat_processus)
2793: {
2794: pthread_mutexattr_t attributs_mutex;
2795:
2796: struct_liste_chainee *l_element_lecture;
2797: struct_liste_chainee *l_element_precedent;
2798: struct_liste_chainee *l_element_suivant;
2799:
2800: struct_processus *s_nouvel_etat_processus;
2801:
2802: unsigned long i;
2803:
2804: if (pthread_mutex_lock(&((*s_etat_processus).mutex)) != 0)
2805: {
2806: (*s_etat_processus).erreur_systeme = d_es_processus;
2807: return(NULL);
2808: }
2809:
2810: if ((s_nouvel_etat_processus = malloc(sizeof(struct_processus))) == NULL)
2811: {
2812: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2813: return(NULL);
2814: }
2815:
2816: (*s_nouvel_etat_processus) = (*s_etat_processus);
2817:
2818: // On réinitialise l'allocateur.
2819:
2820: initialisation_allocateur(s_nouvel_etat_processus);
2821:
2822: /*
2823: * (*s_etat_processus).definition_chainee,
2824: * (*s_etat_processus).nom_fichier_source,
2825: * (*s_etat_processus).nom_fichier_historique et
2826: * (*s_etat_processus).chemin_fichier_temporaires
2827: * n'ont aucune raison de changer.
2828: */
2829:
2830: pthread_mutexattr_init(&attributs_mutex);
2831: pthread_mutexattr_settype(&attributs_mutex, PTHREAD_MUTEX_NORMAL);
2832: (*s_nouvel_etat_processus).sections_critiques = 0;
2833:
2834: // Les sémaphores sont initialisés dans le nouveau thread. Il
2835: // s'agit d'une limitation de l'implantation de l'émulation
2836: // de sem_init().
2837:
2838: initialisation_contexte_cas(s_etat_processus);
2839:
2840: (*s_nouvel_etat_processus).var_volatile_processus_pere = 0;
2841: (*s_nouvel_etat_processus).var_volatile_processus_racine = 0;
2842: (*s_nouvel_etat_processus).fichiers_graphiques = NULL;
2843: (*s_nouvel_etat_processus).entree_standard = NULL;
2844: (*s_nouvel_etat_processus).s_marques = NULL;
2845: (*s_nouvel_etat_processus).requete_nouveau_plan = d_vrai;
2846: (*s_nouvel_etat_processus).mise_a_jour_trace_requise = d_faux;
2847: (*s_nouvel_etat_processus).nom_fichier_impression = NULL;
2848: (*s_nouvel_etat_processus).expression_courante = NULL;
2849: (*s_nouvel_etat_processus).objet_courant = NULL;
2850: (*s_nouvel_etat_processus).processus_detache = d_faux;
2851: (*s_nouvel_etat_processus).evaluation_forcee = 'N';
2852:
2853: (*s_nouvel_etat_processus).nombre_objets_envoyes_non_lus = 0;
2854: (*s_nouvel_etat_processus).nombre_objets_injectes = 0;
2855: (*s_nouvel_etat_processus).presence_fusible = d_faux;
2856: (*s_nouvel_etat_processus).thread_fusible = 0;
2857: (*s_nouvel_etat_processus).niveau_initial =
2858: (*s_etat_processus).niveau_courant;
2859: (*s_nouvel_etat_processus).presence_pipes = d_faux;
2860: (*s_nouvel_etat_processus).debug_programme = d_faux;
2861: (*s_nouvel_etat_processus).s_fichiers = NULL;
2862: (*s_nouvel_etat_processus).s_connecteurs_sql = NULL;
2863:
2864: // On réinitialise toutes les interruptions.
2865:
2866: (*s_nouvel_etat_processus).traitement_interruption = 'N';
2867: (*s_nouvel_etat_processus).traitement_interruptible = 'Y';
2868: (*s_nouvel_etat_processus).nombre_interruptions_en_queue = 0;
2869: (*s_nouvel_etat_processus).nombre_interruptions_non_affectees = 0;
2870:
2871: (*s_nouvel_etat_processus).at_exit = NULL;
2872: (*s_nouvel_etat_processus).at_poke = NULL;
2873: (*s_nouvel_etat_processus).traitement_at_poke = 'N';
2874:
2875: for(i = 0; i < d_NOMBRE_INTERRUPTIONS; i++)
2876: {
2877: (*s_nouvel_etat_processus).corps_interruptions[i] = NULL;
2878: (*s_nouvel_etat_processus).masque_interruptions[i] = 'N';
2879: (*s_nouvel_etat_processus).queue_interruptions[i] = 0;
2880: (*s_nouvel_etat_processus).pile_origine_interruptions[i] = NULL;
2881: }
2882:
2883: if ((*s_nouvel_etat_processus).generateur_aleatoire != NULL)
2884: {
2885: if (((*s_nouvel_etat_processus).generateur_aleatoire =
2886: gsl_rng_clone((*s_etat_processus).generateur_aleatoire))
2887: == NULL)
2888: {
2889: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2890: return(NULL);
2891: }
2892:
2893: gsl_rng_set((*s_nouvel_etat_processus).generateur_aleatoire,
2894: gsl_rng_get((*s_etat_processus).generateur_aleatoire));
2895: }
2896:
2897: // Copie de la localisation
2898:
2899: if (((*s_nouvel_etat_processus).localisation = malloc((strlen(
2900: (*s_etat_processus).localisation) + 1) * sizeof(unsigned char)))
2901: == NULL)
2902: {
2903: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2904: return(NULL);
2905: }
2906:
2907: strcpy((*s_nouvel_etat_processus).localisation,
2908: (*s_etat_processus).localisation);
2909:
2910: if ((*s_etat_processus).indep != NULL)
2911: {
2912: if (((*s_nouvel_etat_processus).indep = copie_objet(s_etat_processus,
2913: (*s_etat_processus).indep, 'P')) == NULL)
2914: {
2915: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
2916: {
2917: (*s_etat_processus).erreur_systeme = d_es_processus;
2918: return(NULL);
2919: }
2920:
2921: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2922: return(NULL);
2923: }
2924: }
2925: else
2926: {
2927: (*s_nouvel_etat_processus).indep = NULL;
2928: }
2929:
2930: if ((*s_etat_processus).depend != NULL)
2931: {
2932: if (((*s_nouvel_etat_processus).depend = copie_objet(s_etat_processus,
2933: (*s_etat_processus).depend, 'P')) == NULL)
2934: {
2935: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
2936: {
2937: (*s_etat_processus).erreur_systeme = d_es_processus;
2938: return(NULL);
2939: }
2940:
2941: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2942: return(NULL);
2943: }
2944: }
2945: else
2946: {
2947: (*s_nouvel_etat_processus).depend = NULL;
2948: }
2949:
2950: if ((*s_etat_processus).parametres_courbes_de_niveau != NULL)
2951: {
2952: if (((*s_nouvel_etat_processus).parametres_courbes_de_niveau =
2953: copie_objet(s_etat_processus, (*s_etat_processus)
2954: .parametres_courbes_de_niveau, 'P')) == NULL)
2955: {
2956: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
2957: {
2958: (*s_etat_processus).erreur_systeme = d_es_processus;
2959: return(NULL);
2960: }
2961:
2962: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2963: return(NULL);
2964: }
2965: }
2966: else
2967: {
2968: (*s_nouvel_etat_processus).parametres_courbes_de_niveau = NULL;
2969: }
2970:
2971: (*s_nouvel_etat_processus).instruction_derniere_erreur = NULL;
2972:
2973: if (((*s_etat_processus).instruction_courante != NULL) &&
2974: (*s_etat_processus).evaluation_expression_compilee == 'N')
2975: {
2976: if (((*s_nouvel_etat_processus).instruction_courante = malloc((strlen(
2977: (*s_etat_processus).instruction_courante) + 1) *
2978: sizeof(unsigned char))) == NULL)
2979: {
2980: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
2981: {
2982: (*s_etat_processus).erreur_systeme = d_es_processus;
2983: return(NULL);
2984: }
2985:
2986: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
2987: return(NULL);
2988: }
2989:
2990: strcpy((*s_nouvel_etat_processus).instruction_courante,
2991: (*s_etat_processus).instruction_courante);
2992: }
2993: else
2994: {
2995: (*s_nouvel_etat_processus).instruction_courante = NULL;
2996: }
2997:
2998: if ((*s_etat_processus).label_x != NULL)
2999: {
3000: if (((*s_nouvel_etat_processus).label_x = malloc((strlen(
3001: (*s_etat_processus).label_x) + 1) *
3002: sizeof(unsigned char))) == NULL)
3003: {
3004: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3005: {
3006: (*s_etat_processus).erreur_systeme = d_es_processus;
3007: return(NULL);
3008: }
3009:
3010: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3011: return(NULL);
3012: }
3013:
3014: strcpy((*s_nouvel_etat_processus).label_x,
3015: (*s_etat_processus).label_x);
3016: }
3017: else
3018: {
3019: (*s_nouvel_etat_processus).label_x = NULL;
3020: }
3021:
3022: if ((*s_etat_processus).label_y != NULL)
3023: {
3024: if (((*s_nouvel_etat_processus).label_y = malloc((strlen(
3025: (*s_etat_processus).label_y) + 1) *
3026: sizeof(unsigned char))) == NULL)
3027: {
3028: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3029: {
3030: (*s_etat_processus).erreur_systeme = d_es_processus;
3031: return(NULL);
3032: }
3033:
3034: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3035: return(NULL);
3036: }
3037:
3038: strcpy((*s_nouvel_etat_processus).label_y,
3039: (*s_etat_processus).label_y);
3040: }
3041: else
3042: {
3043: (*s_nouvel_etat_processus).label_y = NULL;
3044: }
3045:
3046: if ((*s_etat_processus).label_z != NULL)
3047: {
3048: if (((*s_nouvel_etat_processus).label_z = malloc((strlen(
3049: (*s_etat_processus).label_z) + 1) *
3050: sizeof(unsigned char))) == NULL)
3051: {
3052: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3053: {
3054: (*s_etat_processus).erreur_systeme = d_es_processus;
3055: return(NULL);
3056: }
3057:
3058: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3059: return(NULL);
3060: }
3061:
3062: strcpy((*s_nouvel_etat_processus).label_z,
3063: (*s_etat_processus).label_z);
3064: }
3065: else
3066: {
3067: (*s_nouvel_etat_processus).label_z = NULL;
3068: }
3069:
3070: if ((*s_etat_processus).titre != NULL)
3071: {
3072: if (((*s_nouvel_etat_processus).titre = malloc((strlen(
3073: (*s_etat_processus).titre) + 1) *
3074: sizeof(unsigned char))) == NULL)
3075: {
3076: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3077: {
3078: (*s_etat_processus).erreur_systeme = d_es_processus;
3079: return(NULL);
3080: }
3081:
3082: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3083: return(NULL);
3084: }
3085:
3086: strcpy((*s_nouvel_etat_processus).titre,
3087: (*s_etat_processus).titre);
3088: }
3089: else
3090: {
3091: (*s_nouvel_etat_processus).titre = NULL;
3092: }
3093:
3094: if ((*s_etat_processus).legende != NULL)
3095: {
3096: if (((*s_nouvel_etat_processus).legende = malloc((strlen(
3097: (*s_etat_processus).legende) + 1) *
3098: sizeof(unsigned char))) == NULL)
3099: {
3100: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3101: {
3102: (*s_etat_processus).erreur_systeme = d_es_processus;
3103: return(NULL);
3104: }
3105:
3106: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3107: return(NULL);
3108: }
3109:
3110: strcpy((*s_nouvel_etat_processus).legende,
3111: (*s_etat_processus).legende);
3112: }
3113: else
3114: {
3115: (*s_nouvel_etat_processus).legende = NULL;
3116: }
3117:
3118: /*
3119: * Copie de la table des variables
3120: */
3121:
3122: (*s_nouvel_etat_processus).l_liste_variables_statiques = NULL;
3123: copie_arbre_variables(s_etat_processus, s_nouvel_etat_processus);
3124:
3125: if ((*s_nouvel_etat_processus).erreur_systeme != d_es)
3126: {
3127: return(NULL);
3128: }
3129:
3130: (*(*s_nouvel_etat_processus).l_liste_variables_partagees) =
3131: (*(*s_etat_processus).l_liste_variables_partagees);
3132: (*(*s_nouvel_etat_processus).s_arbre_variables_partagees) =
3133: (*(*s_etat_processus).s_arbre_variables_partagees);
3134:
3135: /*
3136: * Copie de la pile opérationnelle
3137: */
3138:
3139: (*s_nouvel_etat_processus).l_base_pile = NULL;
3140: l_element_lecture = (*s_etat_processus).l_base_pile;
3141: l_element_precedent = NULL;
3142:
3143: while(l_element_lecture != NULL)
3144: {
3145: if ((l_element_suivant = malloc(sizeof(struct_liste_chainee))) == NULL)
3146: {
3147: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3148: {
3149: (*s_etat_processus).erreur_systeme = d_es_processus;
3150: return(NULL);
3151: }
3152:
3153: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3154: return(NULL);
3155: }
3156:
3157: if (((*l_element_suivant).donnee = copie_objet(s_etat_processus,
3158: (*l_element_lecture).donnee, 'P')) == NULL)
3159: {
3160: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3161: {
3162: (*s_etat_processus).erreur_systeme = d_es_processus;
3163: return(NULL);
3164: }
3165:
3166: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3167: return(NULL);
3168: }
3169:
3170: (*l_element_suivant).suivant = NULL;
3171:
3172: if ((*s_nouvel_etat_processus).l_base_pile == NULL)
3173: {
3174: (*s_nouvel_etat_processus).l_base_pile = l_element_suivant;
3175: }
3176: else
3177: {
3178: (*l_element_precedent).suivant = l_element_suivant;
3179: }
3180:
3181: l_element_precedent = l_element_suivant;
3182: l_element_lecture = (*l_element_lecture).suivant;
3183: }
3184:
3185: /*
3186: * Copie de la pile système
3187: */
3188:
3189: (*s_nouvel_etat_processus).l_base_pile_systeme = NULL;
3190: (*s_nouvel_etat_processus).hauteur_pile_systeme = 0;
3191:
3192: empilement_pile_systeme(s_nouvel_etat_processus);
3193:
3194: if ((*s_nouvel_etat_processus).erreur_systeme != d_es)
3195: {
3196: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3197: {
3198: (*s_etat_processus).erreur_systeme = d_es_processus;
3199: return(NULL);
3200: }
3201:
3202: (*s_etat_processus).erreur_systeme =
3203: (*s_nouvel_etat_processus).erreur_systeme;
3204: return(NULL);
3205: }
3206:
3207: (*(*s_nouvel_etat_processus).l_base_pile_systeme).retour_definition = 'Y';
3208:
3209: /*
3210: * On empile deux valeurs retour_definition pour pouvoir récupérer
3211: * les variables dans le cas d'un programme compilé.
3212: */
3213:
3214: empilement_pile_systeme(s_nouvel_etat_processus);
3215:
3216: if ((*s_nouvel_etat_processus).erreur_systeme != d_es)
3217: {
3218: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3219: {
3220: (*s_etat_processus).erreur_systeme = d_es_processus;
3221: return(NULL);
3222: }
3223:
3224: (*s_etat_processus).erreur_systeme =
3225: (*s_nouvel_etat_processus).erreur_systeme;
3226: return(NULL);
3227: }
3228:
3229: (*(*s_nouvel_etat_processus).l_base_pile_systeme).retour_definition = 'Y';
3230:
3231: /*
3232: * Destruction de la pile last pour le thread en cours.
3233: */
3234:
3235: (*s_nouvel_etat_processus).l_base_pile_last = NULL;
3236: (*s_nouvel_etat_processus).l_base_pile_processus = NULL;
3237:
3238: /*
3239: * Copie des différents contextes
3240: */
3241:
3242: (*s_nouvel_etat_processus).pointeur_signal_lecture = d_faux;
3243: (*s_nouvel_etat_processus).pointeur_signal_ecriture = d_faux;
3244:
3245: (*s_nouvel_etat_processus).l_base_pile_contextes = NULL;
3246: l_element_lecture = (*s_etat_processus).l_base_pile_contextes;
3247:
3248: while(l_element_lecture != NULL)
3249: {
3250: if ((l_element_suivant = malloc(sizeof(struct_liste_chainee))) == NULL)
3251: {
3252: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3253: {
3254: (*s_etat_processus).erreur_systeme = d_es_processus;
3255: return(NULL);
3256: }
3257:
3258: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3259: return(NULL);
3260: }
3261:
3262: if (((*l_element_suivant).donnee = copie_objet(s_etat_processus,
3263: (*l_element_lecture).donnee, 'P')) == NULL)
3264: {
3265: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3266: {
3267: (*s_etat_processus).erreur_systeme = d_es_processus;
3268: return(NULL);
3269: }
3270:
3271: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3272: return(NULL);
3273: }
3274:
3275: (*l_element_suivant).suivant = NULL;
3276:
3277: if ((*s_nouvel_etat_processus).l_base_pile_contextes == NULL)
3278: {
3279: (*s_nouvel_etat_processus).l_base_pile_contextes =
3280: l_element_suivant;
3281: }
3282: else
3283: {
3284: (*l_element_precedent).suivant = l_element_suivant;
3285: }
3286:
3287: l_element_precedent = l_element_suivant;
3288: l_element_lecture = (*l_element_lecture).suivant;
3289: }
3290:
3291: (*s_nouvel_etat_processus).l_base_pile_taille_contextes = NULL;
3292: l_element_lecture = (*s_etat_processus).l_base_pile_taille_contextes;
3293:
3294: while(l_element_lecture != NULL)
3295: {
3296: if ((l_element_suivant = malloc(sizeof(struct_liste_chainee))) == NULL)
3297: {
3298: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3299: {
3300: (*s_etat_processus).erreur_systeme = d_es_processus;
3301: return(NULL);
3302: }
3303:
3304: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3305: return(NULL);
3306: }
3307:
3308: if (((*l_element_suivant).donnee = copie_objet(s_etat_processus,
3309: (*l_element_lecture).donnee, 'P')) == NULL)
3310: {
3311: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3312: {
3313: (*s_etat_processus).erreur_systeme = d_es_processus;
3314: return(NULL);
3315: }
3316:
3317: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3318: return(NULL);
3319: }
3320:
3321: (*l_element_suivant).suivant = NULL;
3322:
3323: if ((*s_nouvel_etat_processus).l_base_pile_taille_contextes == NULL)
3324: {
3325: (*s_nouvel_etat_processus).l_base_pile_taille_contextes =
3326: l_element_suivant;
3327: }
3328: else
3329: {
3330: (*l_element_precedent).suivant = l_element_suivant;
3331: }
3332:
3333: l_element_precedent = l_element_suivant;
3334: l_element_lecture = (*l_element_lecture).suivant;
3335: }
3336:
3337: /*
3338: * Copies des piles s_sockets, s_bibliotheques et
3339: * s_instructions_externes.
3340: */
3341:
3342: (*s_nouvel_etat_processus).s_sockets = NULL;
3343: l_element_lecture = (*s_etat_processus).s_sockets;
3344:
3345: while(l_element_lecture != NULL)
3346: {
3347: if ((l_element_suivant = malloc(sizeof(struct_liste_chainee))) == NULL)
3348: {
3349: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3350: {
3351: (*s_etat_processus).erreur_systeme = d_es_processus;
3352: return(NULL);
3353: }
3354:
3355: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3356: return(NULL);
3357: }
3358:
3359: if (((*l_element_suivant).donnee = copie_objet(s_etat_processus,
3360: (*l_element_lecture).donnee, 'P')) == NULL)
3361: {
3362: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3363: {
3364: (*s_etat_processus).erreur_systeme = d_es_processus;
3365: return(NULL);
3366: }
3367:
3368: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3369: return(NULL);
3370: }
3371:
3372: (*l_element_suivant).suivant = NULL;
3373:
3374: if ((*s_nouvel_etat_processus).s_sockets == NULL)
3375: {
3376: (*s_nouvel_etat_processus).s_sockets = l_element_suivant;
3377: }
3378: else
3379: {
3380: (*l_element_precedent).suivant = l_element_suivant;
3381: }
3382:
3383: l_element_precedent = l_element_suivant;
3384: l_element_lecture = (*l_element_lecture).suivant;
3385: }
3386:
3387: (*s_nouvel_etat_processus).s_bibliotheques = NULL;
3388: l_element_precedent = NULL;
3389: l_element_lecture = (*s_etat_processus).s_bibliotheques;
3390:
3391: while(l_element_lecture != NULL)
3392: {
3393: if ((l_element_suivant = malloc(sizeof(struct_liste_chainee))) == NULL)
3394: {
3395: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3396: {
3397: (*s_etat_processus).erreur_systeme = d_es_processus;
3398: return(NULL);
3399: }
3400:
3401: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3402: return(NULL);
3403: }
3404:
3405: if (((*l_element_suivant).donnee = malloc(sizeof(struct_bibliotheque)))
3406: == NULL)
3407: {
3408: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3409: return(NULL);
3410: }
3411:
3412: (*((struct_bibliotheque *) (*l_element_suivant).donnee)).descripteur
3413: = (*((struct_bibliotheque *) (*l_element_lecture).donnee))
3414: .descripteur;
3415: (*((struct_bibliotheque *) (*l_element_suivant).donnee)).pid
3416: = (*((struct_bibliotheque *) (*l_element_lecture).donnee)).pid;
3417: (*((struct_bibliotheque *) (*l_element_suivant).donnee)).tid
3418: = (*((struct_bibliotheque *) (*l_element_lecture).donnee)).tid;
3419:
3420: if (((*((struct_bibliotheque *) (*l_element_suivant).donnee)).nom =
3421: malloc((strlen((*((struct_bibliotheque *) (*l_element_lecture)
3422: .donnee)).nom) + 1) * sizeof(unsigned char))) == NULL)
3423: {
3424: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3425: {
3426: (*s_etat_processus).erreur_systeme = d_es_processus;
3427: return(NULL);
3428: }
3429:
3430: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
3431: return(NULL);
3432: }
3433:
3434: strcpy((*((struct_bibliotheque *) (*l_element_suivant).donnee)).nom,
3435: (*((struct_bibliotheque *) (*l_element_lecture).donnee)).nom);
3436:
3437: (*l_element_suivant).suivant = NULL;
3438:
3439: if ((*s_nouvel_etat_processus).s_bibliotheques == NULL)
3440: {
3441: (*s_nouvel_etat_processus).s_bibliotheques = l_element_suivant;
3442: }
3443: else
3444: {
3445: (*l_element_precedent).suivant = l_element_suivant;
3446: }
3447:
3448: l_element_precedent = l_element_suivant;
3449: l_element_lecture = (*l_element_lecture).suivant;
3450: }
3451:
3452: if ((*s_etat_processus).nombre_instructions_externes != 0)
3453: {
3454: if (((*s_nouvel_etat_processus).s_instructions_externes =
3455: malloc((*s_etat_processus).nombre_instructions_externes *
3456: sizeof(struct_instruction_externe))) == NULL)
3457: {
3458: (*s_etat_processus).erreur_systeme = d_es_processus;
3459: return(NULL);
3460: }
3461:
3462: for(i = 0; i < (*s_etat_processus).nombre_instructions_externes; i++)
3463: {
3464: if (((*s_nouvel_etat_processus).s_instructions_externes[i].nom =
3465: malloc((strlen((*s_etat_processus).s_instructions_externes
3466: [i].nom) + 1) * sizeof(unsigned char))) == NULL)
3467: {
3468: (*s_etat_processus).erreur_systeme = d_es_processus;
3469: return(NULL);
3470: }
3471:
3472: strcpy((*s_nouvel_etat_processus).s_instructions_externes[i].nom,
3473: (*s_etat_processus).s_instructions_externes[i].nom);
3474:
3475: if (((*s_nouvel_etat_processus).s_instructions_externes[i]
3476: .nom_bibliotheque = malloc((strlen((*s_etat_processus)
3477: .s_instructions_externes[i].nom_bibliotheque) + 1) *
3478: sizeof(unsigned char))) == NULL)
3479: {
3480: (*s_etat_processus).erreur_systeme = d_es_processus;
3481: return(NULL);
3482: }
3483:
3484: strcpy((*s_nouvel_etat_processus).s_instructions_externes[i]
3485: .nom_bibliotheque, (*s_etat_processus)
3486: .s_instructions_externes[i].nom_bibliotheque);
3487:
3488: (*s_nouvel_etat_processus).s_instructions_externes[i]
3489: .descripteur_bibliotheque = (*s_etat_processus)
3490: .s_instructions_externes[i].descripteur_bibliotheque;
3491: }
3492: }
3493: else
3494: {
3495: (*s_nouvel_etat_processus).s_instructions_externes = NULL;
3496: }
3497:
3498: pthread_mutexattr_init(&attributs_mutex);
3499: pthread_mutexattr_settype(&attributs_mutex, PTHREAD_MUTEX_NORMAL);
3500: pthread_mutex_init(&((*s_nouvel_etat_processus).mutex), &attributs_mutex);
3501: pthread_mutexattr_destroy(&attributs_mutex);
3502:
3503: pthread_mutexattr_init(&attributs_mutex);
3504: pthread_mutexattr_settype(&attributs_mutex, PTHREAD_MUTEX_NORMAL);
3505: pthread_mutex_init(&((*s_nouvel_etat_processus).mutex_allocation),
3506: &attributs_mutex);
3507: pthread_mutexattr_destroy(&attributs_mutex);
3508:
3509: if (pthread_mutex_unlock(&((*s_etat_processus).mutex)) != 0)
3510: {
3511: (*s_etat_processus).erreur_systeme = d_es_processus;
3512: return(NULL);
3513: }
3514:
3515: return(s_nouvel_etat_processus);
3516:
3517: #undef return
3518: }
3519:
3520:
3521: /*
3522: ================================================================================
3523: Routines de debug
3524: ================================================================================
3525: entrées :
3526: --------------------------------------------------------------------------------
3527: sorties :
3528: --------------------------------------------------------------------------------
3529: effets de bord : néant
3530: ================================================================================
3531: */
3532:
3533: #ifdef DEBUG_MEMOIRE
3534:
3535: #undef malloc
3536: #undef realloc
3537: #undef free
3538: #undef fork
3539:
3540: #ifdef return
3541: # undef return
3542: #endif
3543:
3544: #ifdef __BACKTRACE
3545: #define PROFONDEUR_PILE 64
3546: #define return(a) { if (a == NULL) \
3547: { BACKTRACE(PROFONDEUR_PILE); \
3548: fprintf(stderr, ">>> MEDITATION %d\n", __LINE__); } \
3549: return(a); } while(0)
3550: #endif
3551:
3552: #undef fprintf
3553: #define check(a, b) ((strcmp(#a, fonction) == 0) && (ligne == b))
3554: #undef CORE_DUMP
3555:
3556: typedef struct memoire
3557: {
3558: void *pointeur;
3559: unsigned char *fonction;
3560: unsigned char *argument;
3561: unsigned long ligne;
3562: size_t taille;
3563: unsigned long long ordre;
3564: # ifdef __BACKTRACE
3565: void *pile[PROFONDEUR_PILE];
3566: int profondeur;
3567: # endif
3568: struct memoire *suivant;
3569: } struct_memoire;
3570:
3571: static struct_memoire *debug = NULL;
3572: static unsigned long long ordre = 0;
3573: static pthread_mutex_t mutex_allocation;
3574:
3575: void
3576: debug_memoire_initialisation()
3577: {
3578: pthread_mutexattr_t attributs_mutex;
3579:
3580: pthread_mutexattr_init(&attributs_mutex);
3581: pthread_mutexattr_settype(&attributs_mutex, PTHREAD_MUTEX_RECURSIVE);
3582: pthread_mutex_init(&mutex_allocation, &attributs_mutex);
3583: pthread_mutexattr_destroy(&attributs_mutex);
3584:
3585: return;
3586: }
3587:
3588: void *
3589: debug_memoire_ajout(size_t taille, const unsigned char *fonction,
3590: unsigned long ligne, const unsigned char *argument)
3591: {
3592: struct_memoire *ancienne_base;
3593:
3594: void *pointeur;
3595:
3596: pthread_mutex_lock(&mutex_allocation);
3597:
3598: ancienne_base = debug;
3599:
3600: if ((debug = malloc(sizeof(struct_memoire))) == NULL)
3601: {
3602: pthread_mutex_unlock(&mutex_allocation);
3603: return(NULL);
3604: }
3605:
3606: if (((*debug).pointeur = malloc(taille)) == NULL)
3607: {
3608: pthread_mutex_unlock(&mutex_allocation);
3609: return(NULL);
3610: }
3611:
3612: (*debug).suivant = ancienne_base;
3613: (*debug).ligne = ligne;
3614: (*debug).taille = taille;
3615: (*debug).ordre = ordre;
3616:
3617: pointeur = (*debug).pointeur;
3618:
3619: # ifdef __BACKTRACE
3620: (*debug).profondeur = backtrace((*debug).pile, PROFONDEUR_PILE);
3621: # endif
3622:
3623: if (((*debug).fonction = malloc((strlen(fonction) + 1) *
3624: sizeof(unsigned char))) == NULL)
3625: {
3626: pthread_mutex_unlock(&mutex_allocation);
3627: return(NULL);
3628: }
3629:
3630: if (((*debug).argument = malloc((strlen(argument) + 1) *
3631: sizeof(unsigned char))) == NULL)
3632: {
3633: pthread_mutex_unlock(&mutex_allocation);
3634: return(NULL);
3635: }
3636:
3637: strcpy((*debug).fonction, fonction);
3638: strcpy((*debug).argument, argument);
3639:
3640: memset((*debug).pointeur, 0, (*debug).taille);
3641:
3642: pthread_mutex_unlock(&mutex_allocation);
3643: ordre++;
3644:
3645: return(pointeur);
3646: }
3647:
3648: void *
3649: debug_memoire_modification(void *pointeur, size_t taille,
3650: const unsigned char *fonction, unsigned long ligne,
3651: const unsigned char *argument)
3652: {
3653: struct_memoire *element_courant;
3654:
3655: if (pointeur != NULL)
3656: {
3657: if (taille == 0)
3658: {
3659: // Revient à free(). Il n'y a pas de parenthèses car on ne veut
3660: // pas utiliser la macro return().
3661:
3662: debug_memoire_retrait(pointeur);
3663: return NULL ;
3664: }
3665: else
3666: {
3667: // Réallocation réelle
3668:
3669: pthread_mutex_lock(&mutex_allocation);
3670:
3671: element_courant = debug;
3672:
3673: while(element_courant != NULL)
3674: {
3675: if ((*element_courant).pointeur == pointeur)
3676: {
3677: break;
3678: }
3679:
3680: element_courant = (*element_courant).suivant;
3681: }
3682:
3683: if (element_courant == NULL)
3684: {
3685: pthread_mutex_unlock(&mutex_allocation);
3686:
3687: uprintf("[%d-%llu] ILLEGAL POINTER (realloc)\n",
3688: getpid(), (unsigned long long) pthread_self());
3689: # ifdef __BACKTRACE
3690: BACKTRACE(PROFONDEUR_PILE);
3691: # endif
3692:
3693: return(realloc(pointeur, taille));
3694: }
3695: else
3696: {
3697: if (((*element_courant).pointeur = realloc(pointeur, taille))
3698: == NULL)
3699: {
3700: pthread_mutex_unlock(&mutex_allocation);
3701: return(NULL);
3702: }
3703:
3704: (*element_courant).ligne = ligne;
3705: (*element_courant).taille = taille;
3706: free((*element_courant).fonction);
3707: free((*element_courant).argument);
3708:
3709: if (((*element_courant).fonction = malloc((strlen(fonction)
3710: + 1) * sizeof(unsigned char))) == NULL)
3711: {
3712: pthread_mutex_unlock(&mutex_allocation);
3713: return(NULL);
3714: }
3715:
3716: if (((*element_courant).argument = malloc((strlen(argument)
3717: + 1) * sizeof(unsigned char))) == NULL)
3718: {
3719: pthread_mutex_unlock(&mutex_allocation);
3720: return(NULL);
3721: }
3722:
3723: strcpy((*element_courant).fonction, fonction);
3724: strcpy((*element_courant).argument, argument);
3725:
3726: pthread_mutex_unlock(&mutex_allocation);
3727:
3728: return((*element_courant).pointeur);
3729: }
3730: }
3731: }
3732: else
3733: {
3734: // Revient à malloc()
3735: pointeur = debug_memoire_ajout(taille, fonction, ligne, argument);
3736: return(pointeur);
3737: }
3738: }
3739:
3740: void
3741: debug_memoire_retrait(void *pointeur)
3742: {
3743: struct_memoire *element_courant;
3744: struct_memoire *element_precedent;
3745:
3746: pthread_mutex_lock(&mutex_allocation);
3747:
3748: element_courant = debug;
3749: element_precedent = NULL;
3750:
3751: while(element_courant != NULL)
3752: {
3753: if ((*element_courant).pointeur == pointeur)
3754: {
3755: if (element_precedent == NULL)
3756: {
3757: debug = (*debug).suivant;
3758: }
3759: else
3760: {
3761: (*element_precedent).suivant = (*element_courant).suivant;
3762: }
3763:
3764: if (pointeur != NULL)
3765: {
3766: memset(pointeur, 0, (*element_courant).taille);
3767: }
3768:
3769: free((*element_courant).fonction);
3770: free((*element_courant).argument);
3771: free(element_courant);
3772:
3773: break;
3774: }
3775:
3776: element_precedent = element_courant;
3777: element_courant = (*element_courant).suivant;
3778: }
3779:
3780: pthread_mutex_unlock(&mutex_allocation);
3781:
3782: if (element_courant == NULL)
3783: {
3784: uprintf("[%d-%llu] ILLEGAL POINTER (free)\n",
3785: getpid(), (unsigned long long) pthread_self());
3786: # ifdef __BACKTRACE
3787: BACKTRACE(PROFONDEUR_PILE);
3788: # endif
3789: }
3790:
3791: free(pointeur);
3792: return;
3793: }
3794:
3795: void
3796: debug_memoire_verification()
3797: {
3798: # ifdef __BACKTRACE
3799: char **appels;
3800:
3801: int j;
3802: # endif
3803:
3804: integer8 i;
3805:
3806: struct_memoire *element_courant;
3807: struct_memoire *element_suivant;
3808:
3809: fprintf(stderr, "[%d-%llu] LIST OF MEMORY LEAKS\n",
3810: getpid(), (unsigned long long) pthread_self());
3811:
3812: pthread_mutex_lock(&mutex_allocation);
3813:
3814: element_courant = debug;
3815: i = 1;
3816:
3817: while(element_courant != NULL)
3818: {
3819: fprintf(stderr, "[%d-%llu] MEDITATION %lld (%llu)\n", getpid(),
3820: (unsigned long long) pthread_self(), i,
3821: (*element_courant).ordre);
3822: fprintf(stderr, "[%d-%llu] P: %p, F: %s(), L: %lu, S: %d\n",
3823: getpid(), (unsigned long long) pthread_self(),
3824: (*element_courant).pointeur,
3825: (*element_courant).fonction, (*element_courant).ligne,
3826: (int) (*element_courant).taille);
3827: fprintf(stderr, "[%d-%llu] A: %s\n", getpid(),
3828: (unsigned long long) pthread_self(),
3829: (*element_courant).argument);
3830:
3831: if (strstr((*element_courant).argument, "sizeof(unsigned char)")
3832: != NULL)
3833: {
3834: fprintf(stderr, "[%d-%llu] ", getpid(),
3835: (unsigned long long) pthread_self());
3836: fprintf(stderr, "O: %s\n", (unsigned char *)
3837: (*element_courant).pointeur);
3838: }
3839: else if (strcmp((*element_courant).argument, "sizeof(struct_objet)")
3840: == 0)
3841: {
3842: fprintf(stderr, "[%d-%llu] ", getpid(),
3843: (unsigned long long) pthread_self());
3844: fprintf(stderr, "O: %d\n", (*((struct_objet *)
3845: (*element_courant).pointeur)).type);
3846: }
3847: else if (strcmp((*element_courant).argument,
3848: "sizeof(struct_liste_chainee)") == 0)
3849: {
3850: fprintf(stderr, "[%d-%llu] ", getpid(),
3851: (unsigned long long) pthread_self());
3852: fprintf(stderr, "O: data=%p next=%p\n", (*((struct_liste_chainee *)
3853: (*element_courant).pointeur)).donnee,
3854: (*((struct_liste_chainee *) (*element_courant).pointeur))
3855: .suivant);
3856: }
3857:
3858: # ifdef __BACKTRACE
3859: appels = backtrace_symbols((*element_courant).pile,
3860: (*element_courant).profondeur);
3861:
3862: fprintf(stderr, "[%d-%llu] BACKTRACE\n",
3863: getpid(), (unsigned long long) pthread_self());
3864:
3865: if (appels != NULL)
3866: {
3867: for(j = 0; j < (*element_courant).profondeur; j++)
3868: {
3869: fprintf(stderr, "[%d-%llu] %s\n", getpid(),
3870: (unsigned long long) pthread_self(), appels[j]);
3871: }
3872:
3873: free(appels);
3874: }
3875: # endif
3876:
3877: fprintf(stderr, "\n");
3878:
3879: i++;
3880:
3881: element_suivant = (*element_courant).suivant;
3882:
3883: # ifndef CORE_DUMP
3884: free((*element_courant).fonction);
3885: free((*element_courant).argument);
3886: free(element_courant);
3887: # endif
3888:
3889: element_courant = element_suivant;
3890: }
3891:
3892: pthread_mutex_unlock(&mutex_allocation);
3893: pthread_mutex_destroy(&mutex_allocation);
3894:
3895: fprintf(stderr, "[%d-%llu] END OF LIST\n", getpid(),
3896: (unsigned long long) pthread_self());
3897:
3898: return;
3899: }
3900:
3901: pid_t
3902: debug_fork()
3903: {
3904: pid_t pid;
3905:
3906: pthread_mutex_lock(&mutex_allocation);
3907: pid = fork();
3908:
3909: if (pid == 0)
3910: {
3911: liberation_queue_signaux(s_etat_processus);
3912: creation_queue_signaux(s_etat_processus);
3913:
3914: pthread_mutex_destroy(&mutex_allocation);
3915: debug_memoire_initialisation();
3916: }
3917: else
3918: {
3919: pthread_mutex_unlock(&mutex_allocation);
3920: }
3921:
3922: // Pas de parenthèses pour ne pas remplacer return par sa macro.
3923: return pid;
3924: }
3925:
3926: void
3927: analyse_post_mortem()
3928: {
3929: # ifdef CORE_DUMP
3930: BUG(debug != NULL, uprintf("[%d-%llu] CREATE CORE DUMP FILE FOR "
3931: "POST MORTEM ANALYZE\n", getpid(),
3932: (unsigned long long) pthread_self()));
3933: # endif
3934:
3935: return;
3936: }
3937:
3938: #endif
3939:
3940: // vim: ts=4
CVSweb interface <joel.bertrand@systella.fr>