File:
[local] /
rpl /
src /
bibliotheques_externes.c
Revision
1.27:
download - view:
text,
annotated -
select for diffs -
revision graph
Tue Jun 21 15:26:28 2011 UTC (13 years, 3 months ago) by
bertrand
Branches:
MAIN
CVS tags:
HEAD
Correction d'une réinitialisation sauvage de la pile des variables par niveau
dans la copie de la structure de description du processus. Cela corrige
la fonction SPAWN qui échouait sur un segmentation fault car la pile des
variables par niveau était vide alors même que l'arbre des variables contenait
bien les variables. Passage à la prerelease 2.
1: /*
2: ================================================================================
3: RPL/2 (R) version 4.1.0.prerelease.2
4: Copyright (C) 1989-2011 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: static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
26:
27:
28: /*
29: ================================================================================
30: Procédure de chargement d'une bibliothèque dynamique
31: ================================================================================
32: Entrée :
33: --------------------------------------------------------------------------------
34: Sortie :
35: --------------------------------------------------------------------------------
36: Effets de bord : néant
37: ================================================================================
38: */
39:
40: void *
41: chargement_bibliotheque(struct_processus *s_etat_processus,
42: unsigned char *bibliotheque)
43: {
44: char **(*fonction)(unsigned long *, const char *);
45: char *message;
46:
47: long i;
48: long nombre_symboles;
49:
50: struct_rpl_arguments rpl_arguments;
51:
52: struct_liste_chainee *l_element_courant;
53: struct_liste_chainee *l_nouvel_element;
54:
55: unsigned char **tableau;
56: unsigned char *tampon;
57:
58: void *descripteur_bibliotheque;
59: void (*onloading)(struct_rpl_arguments *);
60:
61: /*
62: * On vérifie que la bibliothèque n'est pas déjà chargée.
63: */
64:
65: l_element_courant = (*s_etat_processus).s_bibliotheques;
66:
67: while(l_element_courant != NULL)
68: {
69: if (strcmp((*((struct_bibliotheque *) (*l_element_courant).donnee)).nom,
70: bibliotheque) == 0)
71: {
72: (*s_etat_processus).erreur_execution = d_ex_bibliotheque_chargee;
73: return(NULL);
74: }
75:
76: l_element_courant = (*l_element_courant).suivant;
77: }
78:
79: /*
80: * Ouverture de la bibliothèque
81: */
82:
83: if ((descripteur_bibliotheque = dlopen(bibliotheque,
84: RTLD_NOW | RTLD_LOCAL)) == NULL)
85: {
86: if (pthread_mutex_lock(&mutex) != 0)
87: {
88: (*s_etat_processus).erreur_systeme = d_es_processus;
89: return(NULL);
90: }
91:
92: printf("%s\n", dlerror());
93:
94: if (pthread_mutex_unlock(&mutex) != 0)
95: {
96: (*s_etat_processus).erreur_systeme = d_es_processus;
97: return(NULL);
98: }
99:
100: (*s_etat_processus).erreur_execution = d_ex_erreur_bibliotheque;
101: return(NULL);
102: }
103:
104: if (pthread_mutex_lock(&mutex) != 0)
105: {
106: (*s_etat_processus).erreur_systeme = d_es_processus;
107: return(NULL);
108: }
109:
110: dlerror();
111: onloading = dlsym(descripteur_bibliotheque, "__runOnLoading");
112:
113: if (((message = dlerror()) == NULL) && (onloading != NULL))
114: {
115: if (pthread_mutex_unlock(&mutex) != 0)
116: {
117: (*s_etat_processus).erreur_systeme = d_es_processus;
118: return(NULL);
119: }
120:
121: rpl_arguments.l_base_pile = (*s_etat_processus).l_base_pile;
122: rpl_arguments.l_base_pile_last = (*s_etat_processus).l_base_pile_last;
123:
124: for(i = 0; i < 8; i++)
125: {
126: rpl_arguments.drapeaux_etat[i] =
127: (*s_etat_processus).drapeaux_etat[i];
128: }
129:
130: rpl_arguments.message_erreur = NULL;
131: rpl_arguments.type_erreur = 'E';
132: rpl_arguments.erreur = 0;
133: rpl_arguments.aide = ((*s_etat_processus).affichage_arguments
134: == 'N') ? d_faux : d_vrai;
135: rpl_arguments.affichage_arguments = (*s_etat_processus)
136: .affichage_arguments;
137: rpl_arguments.test_instruction = (*s_etat_processus).test_instruction;
138: rpl_arguments.constante_symbolique = (*s_etat_processus)
139: .constante_symbolique;
140: rpl_arguments.instruction_valide = 'N';
141: rpl_arguments.s_etat_processus = s_etat_processus;
142:
143: (*s_etat_processus).erreur_execution = d_ex;
144:
145: if ((*s_etat_processus).profilage == d_vrai)
146: {
147: if ((tampon = malloc((strlen(bibliotheque) + 14) *
148: sizeof(unsigned char))) == NULL)
149: {
150: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
151: return(NULL);
152: }
153:
154: sprintf(tampon, "%s$runOnLoading", bibliotheque);
155: profilage(s_etat_processus, tampon);
156: free(tampon);
157:
158: if ((*s_etat_processus).erreur_systeme != d_es)
159: {
160: return(NULL);
161: }
162: }
163:
164: # ifndef SEMAPHORES_NOMMES
165: if (sem_post(&((*s_etat_processus).semaphore_fork)) != 0)
166: {
167: (*s_etat_processus).erreur_systeme = d_es_processus;
168: return(NULL);
169: }
170: # else
171: if (sem_post((*s_etat_processus).semaphore_fork) != 0)
172: {
173: (*s_etat_processus).erreur_systeme = d_es_processus;
174: return(NULL);
175: }
176: # endif
177:
178: (*onloading)(&rpl_arguments);
179:
180: # ifndef SEMAPHORES_NOMMES
181: while(sem_wait(&((*s_etat_processus).semaphore_fork)) == -1)
182: {
183: if (errno != EINTR)
184: {
185: (*s_etat_processus).erreur_systeme = d_es_processus;
186: return(NULL);
187: }
188: }
189: # else
190: while(sem_wait((*s_etat_processus).semaphore_fork) == -1)
191: {
192: if (errno != EINTR)
193: {
194: (*s_etat_processus).erreur_systeme = d_es_processus;
195: return(NULL);
196: }
197: }
198: # endif
199:
200: if ((*s_etat_processus).profilage == d_vrai)
201: {
202: profilage(s_etat_processus, NULL);
203: }
204:
205: (*s_etat_processus).nombre_arguments = rpl_arguments.nombre_arguments;
206: (*s_etat_processus).constante_symbolique = rpl_arguments
207: .constante_symbolique;
208: (*s_etat_processus).instruction_valide = rpl_arguments
209: .instruction_valide;
210:
211: if ((*s_etat_processus).test_instruction == 'Y')
212: {
213: if ((*s_etat_processus).nombre_arguments == 0)
214: {
215: (*s_etat_processus).nombre_arguments = -1;
216: }
217: }
218:
219: if (rpl_arguments.erreur != 0)
220: {
221: if (((*s_etat_processus).arret_si_exception == d_vrai) ||
222: (rpl_arguments.type_erreur == 'S'))
223: {
224: if (test_cfsf(s_etat_processus, 51) == d_faux)
225: {
226: printf("%s", ds_beep);
227: }
228:
229: if (rpl_arguments.type_erreur == 'S')
230: {
231: (*s_etat_processus).derniere_erreur_execution = -1;
232:
233: if ((*s_etat_processus).langue == 'F')
234: {
235: printf("+++Système : Fonction dynamique %s "
236: "(ligne %lld)\n",
237: "onLoading", rpl_arguments.erreur);
238: }
239: else
240: {
241: printf("+++System : %s dynamic function (line %lld)\n",
242: "onLoading", rpl_arguments.erreur);
243: }
244: }
245: else
246: {
247: (*s_etat_processus).derniere_erreur_systeme = -1;
248:
249: if ((*s_etat_processus).langue == 'F')
250: {
251: printf("+++Erreur : Fonction dynamique %s "
252: "(ligne %lld)\n",
253: "onLoading" , rpl_arguments.erreur);
254: }
255: else
256: {
257: printf("+++Error : %s dynamic function (line %lld)\n",
258: "onLoading", rpl_arguments.erreur);
259: }
260: }
261:
262: if (rpl_arguments.message_erreur != NULL)
263: {
264: printf("%s\n", rpl_arguments.message_erreur);
265: }
266:
267: fflush(stdout);
268: }
269:
270: if (rpl_arguments.type_erreur == 'S')
271: {
272: (*s_etat_processus).erreur_systeme =
273: d_es_execution_bibliotheque;
274: }
275: else
276: {
277: (*s_etat_processus).erreur_execution =
278: d_ex_execution_bibliotheque;
279: }
280: }
281:
282: (*s_etat_processus).l_base_pile = rpl_arguments.l_base_pile;
283: (*s_etat_processus).l_base_pile_last = rpl_arguments.l_base_pile_last;
284:
285: for(i = 0; i < 8; i++)
286: {
287: (*s_etat_processus).drapeaux_etat[i] =
288: rpl_arguments.drapeaux_etat[i];
289: }
290:
291: l_element_courant = (*s_etat_processus).l_base_pile;
292: (*s_etat_processus).hauteur_pile_operationnelle = 0;
293:
294: while(l_element_courant != NULL)
295: {
296: (*s_etat_processus).hauteur_pile_operationnelle++;
297: l_element_courant = (*l_element_courant).suivant;
298: }
299: }
300: else
301: {
302: printf("%s\n", message);
303:
304: if (pthread_mutex_unlock(&mutex) != 0)
305: {
306: (*s_etat_processus).erreur_systeme = d_es_processus;
307: return(NULL);
308: }
309: }
310:
311: if (pthread_mutex_lock(&mutex) != 0)
312: {
313: (*s_etat_processus).erreur_systeme = d_es_processus;
314: return(NULL);
315: }
316:
317: dlerror();
318: fonction = dlsym(descripteur_bibliotheque, "__external_symbols");
319:
320: if (fonction == NULL)
321: {
322: if ((message = dlerror()) != NULL)
323: {
324: printf("%s\n", message);
325:
326: if (pthread_mutex_unlock(&mutex) != 0)
327: {
328: (*s_etat_processus).erreur_systeme = d_es_processus;
329: return(NULL);
330: }
331:
332: (*s_etat_processus).erreur_execution = d_ex_erreur_bibliotheque;
333: return(NULL);
334: }
335: }
336:
337: dlerror();
338:
339: if (pthread_mutex_unlock(&mutex) != 0)
340: {
341: (*s_etat_processus).erreur_systeme = d_es_processus;
342: return(NULL);
343: }
344:
345: /*
346: * Ajout des symboles externes
347: */
348:
349: if ((tableau = (unsigned char **) (*fonction)((&nombre_symboles),
350: d_version_rpl)) == NULL)
351: {
352: /*
353: * Nombre symboles :
354: * 0 : aucun symbole exporté
355: * >0 : nombre de symboles exportés
356: * -1 : version de bibliothèque incompatible
357: */
358:
359: if (nombre_symboles == 0)
360: {
361: (*s_etat_processus).erreur_execution = d_ex_aucun_symbole;
362: }
363: else if (nombre_symboles == -1)
364: {
365: (*s_etat_processus).erreur_execution = d_ex_version_bibliotheque;
366: }
367: else
368: {
369: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
370: }
371:
372: return(NULL);
373: }
374:
375: if (((*s_etat_processus).s_instructions_externes = realloc(
376: (*s_etat_processus).s_instructions_externes,
377: ((*s_etat_processus).nombre_instructions_externes + nombre_symboles)
378: * sizeof(struct_instruction_externe))) == NULL)
379: {
380: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
381: return(NULL);
382: }
383:
384: for(i = 0; i < nombre_symboles; i++)
385: {
386: (*s_etat_processus).s_instructions_externes[(*s_etat_processus)
387: .nombre_instructions_externes].descripteur_bibliotheque =
388: descripteur_bibliotheque;
389:
390: if (((*s_etat_processus).s_instructions_externes[(*s_etat_processus)
391: .nombre_instructions_externes].nom =
392: malloc((strlen(index(tableau[i], '$') + 1) + 1) *
393: sizeof(unsigned char))) == NULL)
394: {
395: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
396: return(NULL);
397: }
398:
399: strcpy((*s_etat_processus).s_instructions_externes[(*s_etat_processus)
400: .nombre_instructions_externes].nom,
401: index(tableau[i], '$') + 1);
402:
403: *(index(tableau[i], '$')) = d_code_fin_chaine;
404:
405: if (((*s_etat_processus).s_instructions_externes[(*s_etat_processus)
406: .nombre_instructions_externes].nom_bibliotheque = malloc(
407: (strlen(tableau[i]) + 1) * sizeof(unsigned char))) == NULL)
408: {
409: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
410: return(NULL);
411: }
412:
413: strcpy((*s_etat_processus).s_instructions_externes[(*s_etat_processus)
414: .nombre_instructions_externes].nom_bibliotheque, tableau[i]);
415: (*s_etat_processus).nombre_instructions_externes++;
416:
417: free(tableau[i]);
418: }
419:
420: /*
421: * Ajout de la nouvelle bibliothèque
422: */
423:
424: if ((l_nouvel_element = (struct_liste_chainee *)
425: malloc(sizeof(struct_liste_chainee))) == NULL)
426: {
427: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
428: return(NULL);
429: }
430:
431: if (((*l_nouvel_element).donnee = malloc(sizeof(struct_bibliotheque)))
432: == NULL)
433: {
434: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
435: return(NULL);
436: }
437:
438: (*((struct_bibliotheque *) (*l_nouvel_element).donnee)).descripteur =
439: descripteur_bibliotheque;
440: (*((struct_bibliotheque *) (*l_nouvel_element).donnee)).pid =
441: getpid();
442: (*((struct_bibliotheque *) (*l_nouvel_element).donnee)).tid =
443: pthread_self();
444:
445: if (((*((struct_bibliotheque *) (*l_nouvel_element).donnee)).nom =
446: malloc((strlen((*s_etat_processus).s_instructions_externes
447: [(*s_etat_processus).nombre_instructions_externes - 1]
448: .nom_bibliotheque) + 1) * sizeof(unsigned char))) == NULL)
449: {
450: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
451: return(NULL);
452: }
453:
454: strcpy((*((struct_bibliotheque *) (*l_nouvel_element).donnee)).nom,
455: (*s_etat_processus).s_instructions_externes
456: [(*s_etat_processus).nombre_instructions_externes - 1]
457: .nom_bibliotheque);
458:
459: (*l_nouvel_element).suivant = (*s_etat_processus).s_bibliotheques;
460: (*s_etat_processus).s_bibliotheques = l_nouvel_element;
461:
462: tri_base_symboles_externes(s_etat_processus);
463:
464: free(tableau);
465:
466: return(descripteur_bibliotheque);
467: }
468:
469:
470: /*
471: ================================================================================
472: Procédure de retrait d'une bibliothèque dynamique
473: ================================================================================
474: Entrée :
475: --------------------------------------------------------------------------------
476: Sortie :
477: --------------------------------------------------------------------------------
478: Effets de bord : néant
479: ================================================================================
480: */
481:
482: logical1
483: retrait_bibliotheque(struct_processus *s_etat_processus,
484: struct_bibliotheque *descripteur)
485: {
486: char *message;
487:
488: logical1 presence_bibliotheque;
489:
490: struct_instruction_externe *registre;
491:
492: struct_liste_chainee *l_element_courant;
493: struct_liste_chainee *l_element_precedent;
494:
495: struct_rpl_arguments rpl_arguments;
496:
497: unsigned char *tampon;
498:
499: unsigned long i;
500: unsigned long j;
501: unsigned long nombre_symboles_residuels;
502:
503: void (*onclosing)(struct_rpl_arguments *);
504:
505: l_element_courant = (*s_etat_processus).s_bibliotheques;
506: presence_bibliotheque = d_faux;
507: l_element_precedent = NULL;
508:
509: /*
510: * Recherche de la bibliothèque à supprimer
511: */
512:
513: while(l_element_courant != NULL)
514: {
515: if (((*((struct_bibliotheque *) (*l_element_courant).donnee))
516: .descripteur == (*descripteur).descripteur) &&
517: ((*((struct_bibliotheque *) (*l_element_courant).donnee)).pid
518: == getpid()) && (pthread_equal((*((struct_bibliotheque *)
519: (*l_element_courant).donnee)).tid, pthread_self()) != 0))
520: {
521: presence_bibliotheque = d_vrai;
522: break;
523: }
524:
525: l_element_precedent = l_element_courant;
526: l_element_courant = (*l_element_courant).suivant;
527: }
528:
529: if (presence_bibliotheque == d_vrai)
530: {
531: if (pthread_mutex_lock(&mutex) != 0)
532: {
533: (*s_etat_processus).erreur_systeme = d_es_processus;
534: return(d_erreur);
535: }
536:
537: dlerror();
538: onclosing = dlsym((*descripteur).descripteur, "__runOnClosing");
539:
540: if (((message = dlerror()) == NULL) && (onclosing != NULL))
541: {
542: if (pthread_mutex_unlock(&mutex) != 0)
543: {
544: (*s_etat_processus).erreur_systeme = d_es_processus;
545: return(d_erreur);
546: }
547:
548: rpl_arguments.l_base_pile = (*s_etat_processus).l_base_pile;
549: rpl_arguments.l_base_pile_last =
550: (*s_etat_processus).l_base_pile_last;
551:
552: for(i = 0; i < 8; i++)
553: {
554: rpl_arguments.drapeaux_etat[i] =
555: (*s_etat_processus).drapeaux_etat[i];
556: }
557:
558: rpl_arguments.message_erreur = NULL;
559: rpl_arguments.type_erreur = 'E';
560: rpl_arguments.erreur = 0;
561: rpl_arguments.aide = ((*s_etat_processus).affichage_arguments
562: == 'N') ? d_faux : d_vrai;
563: rpl_arguments.affichage_arguments = (*s_etat_processus)
564: .affichage_arguments;
565: rpl_arguments.test_instruction =
566: (*s_etat_processus).test_instruction;
567: rpl_arguments.constante_symbolique = (*s_etat_processus)
568: .constante_symbolique;
569: rpl_arguments.instruction_valide = 'N';
570: rpl_arguments.s_etat_processus = s_etat_processus;
571:
572: (*s_etat_processus).erreur_execution = d_ex;
573:
574: if ((*s_etat_processus).profilage == d_vrai)
575: {
576: if ((tampon = malloc((strlen((*descripteur).nom) + 14) *
577: sizeof(unsigned char))) == NULL)
578: {
579: (*s_etat_processus).erreur_systeme =
580: d_es_allocation_memoire;
581: return(d_erreur);
582: }
583:
584: sprintf(tampon, "%s$runOnClosing", (*descripteur).nom);
585: profilage(s_etat_processus, tampon);
586: free(tampon);
587:
588: if ((*s_etat_processus).erreur_systeme != d_es)
589: {
590: return(d_erreur);
591: }
592: }
593:
594: # ifndef SEMAPHORES_NOMMES
595: if (sem_post(&((*s_etat_processus).semaphore_fork)) != 0)
596: {
597: (*s_etat_processus).erreur_systeme = d_es_processus;
598: return(d_erreur);
599: }
600: # else
601: if (sem_post((*s_etat_processus).semaphore_fork) != 0)
602: {
603: (*s_etat_processus).erreur_systeme = d_es_processus;
604: return(d_erreur);
605: }
606: # endif
607:
608: (*onclosing)(&rpl_arguments);
609:
610: # ifndef SEMAPHORES_NOMMES
611: while(sem_wait(&((*s_etat_processus).semaphore_fork)) == -1)
612: {
613: if (errno != EINTR)
614: {
615: (*s_etat_processus).erreur_systeme = d_es_processus;
616: return(d_erreur);
617: }
618: }
619: # else
620: while(sem_wait((*s_etat_processus).semaphore_fork) == -1)
621: {
622: if (errno != EINTR)
623: {
624: (*s_etat_processus).erreur_systeme = d_es_processus;
625: return(d_erreur);
626: }
627: }
628: # endif
629:
630: if ((*s_etat_processus).profilage == d_vrai)
631: {
632: profilage(s_etat_processus, NULL);
633: }
634:
635: (*s_etat_processus).nombre_arguments =
636: rpl_arguments.nombre_arguments;
637: (*s_etat_processus).constante_symbolique = rpl_arguments
638: .constante_symbolique;
639: (*s_etat_processus).instruction_valide = rpl_arguments
640: .instruction_valide;
641:
642: if ((*s_etat_processus).test_instruction == 'Y')
643: {
644: if ((*s_etat_processus).nombre_arguments == 0)
645: {
646: (*s_etat_processus).nombre_arguments = -1;
647: }
648: }
649:
650: if (rpl_arguments.erreur != 0)
651: {
652: if (((*s_etat_processus).arret_si_exception == d_vrai) ||
653: (rpl_arguments.type_erreur == 'S'))
654: {
655: if (test_cfsf(s_etat_processus, 51) == d_faux)
656: {
657: printf("%s", ds_beep);
658: }
659:
660: if (rpl_arguments.type_erreur == 'S')
661: {
662: (*s_etat_processus).derniere_erreur_execution = -1;
663:
664: if ((*s_etat_processus).langue == 'F')
665: {
666: printf("+++Système : Fonction dynamique "
667: "%s (ligne %lld)\n",
668: "onClosing" , rpl_arguments.erreur);
669: }
670: else
671: {
672: printf("+++System : %s dynamic function "
673: "(line %lld)\n",
674: "onClosing", rpl_arguments.erreur);
675: }
676: }
677: else
678: {
679: (*s_etat_processus).derniere_erreur_systeme = -1;
680:
681: if ((*s_etat_processus).langue == 'F')
682: {
683: printf("+++Erreur : Fonction dynamique %s "
684: "(ligne %lld)\n",
685: "onClosing", rpl_arguments.erreur);
686: }
687: else
688: {
689: printf("+++Error : %s dynamic function "
690: "(line %lld)\n",
691: "onClosing", rpl_arguments.erreur);
692: }
693: }
694:
695: if (rpl_arguments.message_erreur != NULL)
696: {
697: printf("%s\n", rpl_arguments.message_erreur);
698: }
699:
700: fflush(stdout);
701: }
702:
703: if (rpl_arguments.type_erreur == 'S')
704: {
705: (*s_etat_processus).erreur_systeme =
706: d_es_execution_bibliotheque;
707: }
708: else
709: {
710: (*s_etat_processus).erreur_execution =
711: d_ex_execution_bibliotheque;
712: }
713: }
714:
715: (*s_etat_processus).l_base_pile = rpl_arguments.l_base_pile;
716: (*s_etat_processus).l_base_pile_last =
717: rpl_arguments.l_base_pile_last;
718:
719: for(i = 0; i < 8; i++)
720: {
721: (*s_etat_processus).drapeaux_etat[i] =
722: rpl_arguments.drapeaux_etat[i];
723: }
724:
725: l_element_courant = (*s_etat_processus).l_base_pile;
726: (*s_etat_processus).hauteur_pile_operationnelle = 0;
727:
728: while(l_element_courant != NULL)
729: {
730: (*s_etat_processus).hauteur_pile_operationnelle++;
731: l_element_courant = (*l_element_courant).suivant;
732: }
733: }
734: else
735: {
736: printf("%s\n", message);
737:
738: if (pthread_mutex_unlock(&mutex) != 0)
739: {
740: (*s_etat_processus).erreur_systeme = d_es_processus;
741: return(d_erreur);
742: }
743: }
744:
745: /*
746: * Retrait de la bibliothèque de la pile
747: */
748:
749: dlclose((*descripteur).descripteur);
750:
751: l_element_courant = (*s_etat_processus).s_bibliotheques;
752:
753: while(l_element_courant != NULL)
754: {
755: if ((*((struct_bibliotheque *) (*l_element_courant).donnee))
756: .descripteur == (*descripteur).descripteur)
757: {
758: break;
759: }
760:
761: l_element_precedent = l_element_courant;
762: l_element_courant = (*l_element_courant).suivant;
763: }
764:
765: if (l_element_precedent == NULL)
766: {
767: (*s_etat_processus).s_bibliotheques = (*l_element_courant).suivant;
768: }
769: else
770: {
771: (*l_element_precedent).suivant = (*l_element_courant).suivant;
772: }
773:
774: free((*((struct_bibliotheque *) (*l_element_courant).donnee)).nom);
775: free((*l_element_courant).donnee);
776: free(l_element_courant);
777:
778: /*
779: * Retrait des symboles associés à la bibliothèque
780: */
781:
782: nombre_symboles_residuels = 0;
783:
784: for(i = 0; i < (*s_etat_processus).nombre_instructions_externes; i++)
785: {
786: if ((*s_etat_processus).s_instructions_externes[i]
787: .descripteur_bibliotheque != (*descripteur).descripteur)
788: {
789: nombre_symboles_residuels++;
790: }
791: }
792:
793: if (nombre_symboles_residuels == 0)
794: {
795: for(i = 0; i < (*s_etat_processus).nombre_instructions_externes;
796: i++)
797: {
798: free((*s_etat_processus).s_instructions_externes[i].nom);
799: free((*s_etat_processus).s_instructions_externes[i]
800: .nom_bibliotheque);
801: }
802:
803: free((*s_etat_processus).s_instructions_externes);
804: (*s_etat_processus).s_instructions_externes = NULL;
805: }
806: else
807: {
808: registre = (*s_etat_processus).s_instructions_externes;
809:
810: if (((*s_etat_processus).s_instructions_externes =
811: malloc(nombre_symboles_residuels *
812: sizeof(struct_instruction_externe))) == NULL)
813: {
814: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
815:
816: return(d_erreur);
817: }
818:
819: for(i = j = 0; i < (*s_etat_processus).nombre_instructions_externes;
820: i++)
821: {
822: if (registre[i].descripteur_bibliotheque !=
823: (*descripteur).descripteur)
824: {
825: (*s_etat_processus).s_instructions_externes[j].nom =
826: registre[i].nom;
827: (*s_etat_processus).s_instructions_externes[j]
828: .nom_bibliotheque = registre[i].nom_bibliotheque;
829: (*s_etat_processus).s_instructions_externes[j]
830: .descripteur_bibliotheque = registre[i]
831: .descripteur_bibliotheque;
832: j++;
833: }
834: else
835: {
836: free(registre[i].nom);
837: free(registre[i].nom_bibliotheque);
838: }
839: }
840:
841: free(registre);
842: }
843:
844: (*s_etat_processus).nombre_instructions_externes =
845: nombre_symboles_residuels;
846:
847: return(d_absence_erreur);
848: }
849: else
850: {
851: (*s_etat_processus).erreur_execution = d_ex_erreur_bibliotheque;
852:
853: return(d_erreur);
854: }
855: }
856:
857:
858: /*
859: ================================================================================
860: Procédure d'exécution d'une fonction d'une bibliothèque
861: ================================================================================
862: Entrée :
863: --------------------------------------------------------------------------------
864: Sortie :
865: --------------------------------------------------------------------------------
866: Effets de bord : néant
867: ================================================================================
868: */
869:
870: logical1
871: execution_fonction_de_bibliotheque(struct_processus *s_etat_processus,
872: unsigned char *nom_fonction, unsigned char *bibliotheque)
873: {
874: logical1 presence_bibliotheque;
875: logical1 unicite_symbole;
876:
877: long difference;
878: long difference_inferieure;
879: long difference_superieure;
880: long i;
881:
882: struct_liste_chainee *l_element_courant;
883:
884: struct_rpl_arguments rpl_arguments;
885:
886: unsigned char *nom_fonction_externe;
887: unsigned char *tampon;
888:
889: unsigned long borne_inferieure;
890: unsigned long borne_superieure;
891: unsigned long moyenne;
892: unsigned long nombre_iterations_maximal;
893: unsigned long ordre_iteration;
894:
895: void (*fonction)(struct_rpl_arguments *);
896:
897: /*
898: * Recherche dichotomique de la définition externe
899: */
900:
901: if ((*s_etat_processus).nombre_instructions_externes == 0)
902: {
903: return(d_faux);
904: }
905:
906: if (bibliotheque != NULL)
907: {
908: presence_bibliotheque = d_faux;
909: l_element_courant = (*s_etat_processus).s_bibliotheques;
910:
911: while(l_element_courant != NULL)
912: {
913: if (strcmp((*((struct_bibliotheque *) (*l_element_courant).donnee))
914: .nom, bibliotheque) == 0)
915: {
916: presence_bibliotheque = d_vrai;
917: break;
918: }
919:
920: l_element_courant = (*l_element_courant).suivant;
921: }
922:
923: if (presence_bibliotheque == d_faux)
924: {
925: return(d_faux);
926: }
927: }
928:
929: ordre_iteration = 0;
930: nombre_iterations_maximal = ((unsigned long)
931: (log((*s_etat_processus).nombre_instructions_externes) / log(2)))
932: + 2;
933:
934: borne_inferieure = 0;
935: borne_superieure = (*s_etat_processus).nombre_instructions_externes - 1;
936:
937: do
938: {
939: moyenne = (borne_inferieure + borne_superieure) / 2;
940: ordre_iteration++;
941:
942: if ((2 * ((unsigned long) ((borne_inferieure + borne_superieure) / 2)))
943: == (borne_inferieure + borne_superieure))
944: {
945: difference = strcmp(nom_fonction, (*s_etat_processus)
946: .s_instructions_externes[moyenne].nom);
947:
948: if (difference != 0)
949: {
950: if (difference > 0)
951: {
952: borne_inferieure = moyenne;
953: }
954: else
955: {
956: borne_superieure = moyenne;
957: }
958: }
959: }
960: else
961: {
962: difference_inferieure = strcmp(nom_fonction,
963: (*s_etat_processus).s_instructions_externes[moyenne].nom);
964: difference_superieure = strcmp(nom_fonction,
965: (*s_etat_processus).s_instructions_externes[moyenne + 1]
966: .nom);
967:
968: if (difference_inferieure == 0)
969: {
970: difference = 0;
971: }
972: else if (difference_superieure == 0)
973: {
974: difference = 0;
975: moyenne++;
976: }
977: else
978: {
979: difference = difference_inferieure;
980:
981: if (difference > 0)
982: {
983: borne_inferieure = moyenne;
984: }
985: else
986: {
987: borne_superieure = moyenne;
988: }
989: }
990: }
991: } while((difference != 0) &&
992: (ordre_iteration <= nombre_iterations_maximal));
993:
994: if (ordre_iteration > nombre_iterations_maximal)
995: {
996: return(d_faux);
997: }
998:
999: if (bibliotheque != NULL)
1000: { // Nom de la bibliothèque spécifié
1001: if (strcmp((*s_etat_processus).s_instructions_externes[moyenne]
1002: .nom_bibliotheque, bibliotheque) > 0)
1003: {
1004: i = moyenne;
1005:
1006: while(i >= 0)
1007: {
1008: if (strcmp((*s_etat_processus).s_instructions_externes[i]
1009: .nom, nom_fonction) != 0)
1010: {
1011: break;
1012: }
1013: else if (strcmp((*s_etat_processus).s_instructions_externes[i]
1014: .nom_bibliotheque, bibliotheque) == 0)
1015: {
1016: break;
1017: }
1018:
1019: i--;
1020: }
1021:
1022: moyenne = i;
1023: }
1024: else if (strcmp((*s_etat_processus).s_instructions_externes[moyenne]
1025: .nom_bibliotheque, bibliotheque) < 0)
1026: {
1027: i = moyenne;
1028:
1029: while((unsigned long) i <
1030: (*s_etat_processus).nombre_instructions_externes)
1031: {
1032: if (strcmp((*s_etat_processus).s_instructions_externes[i]
1033: .nom, nom_fonction) != 0)
1034: {
1035: break;
1036: }
1037: else if (strcmp((*s_etat_processus).s_instructions_externes[i]
1038: .nom_bibliotheque, bibliotheque) == 0)
1039: {
1040: break;
1041: }
1042:
1043: i++;
1044: }
1045:
1046: moyenne = i;
1047: }
1048: }
1049: else
1050: { // Nom de la bibliothèque non spécifié
1051:
1052: /*
1053: * Vérification de l'unicité du symbole
1054: */
1055:
1056: unicite_symbole = d_vrai;
1057:
1058: if (moyenne > 0)
1059: {
1060: if (strcmp((*s_etat_processus).s_instructions_externes
1061: [moyenne - 1].nom, nom_fonction) == 0)
1062: {
1063: unicite_symbole = d_faux;
1064: }
1065: }
1066:
1067: if ((moyenne + 1) < (*s_etat_processus)
1068: .nombre_instructions_externes)
1069: {
1070: if (strcmp((*s_etat_processus).s_instructions_externes
1071: [moyenne + 1].nom, nom_fonction) == 0)
1072: {
1073: unicite_symbole = d_faux;
1074: }
1075: }
1076:
1077: if (unicite_symbole == d_faux)
1078: {
1079: (*s_etat_processus).erreur_execution = d_ex_definition_ambigue;
1080: return(d_faux);
1081: }
1082: }
1083:
1084: if ((nom_fonction_externe = malloc((strlen(nom_fonction) + 12)
1085: * sizeof(unsigned char))) == NULL)
1086: {
1087: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
1088: return(d_faux);
1089: }
1090:
1091: sprintf(nom_fonction_externe, "__external_%s", nom_fonction);
1092:
1093: if (pthread_mutex_lock(&mutex) != 0)
1094: {
1095: (*s_etat_processus).erreur_systeme = d_es_processus;
1096: return(d_faux);
1097: }
1098:
1099: dlerror();
1100: fonction = dlsym((*s_etat_processus).s_instructions_externes
1101: [moyenne].descripteur_bibliotheque, nom_fonction_externe);
1102:
1103: free(nom_fonction_externe);
1104:
1105: /*
1106: * Vérification de la présence du symbole
1107: */
1108:
1109: if (fonction == NULL)
1110: {
1111: if (dlerror() != NULL)
1112: {
1113: if (pthread_mutex_unlock(&mutex) != 0)
1114: {
1115: (*s_etat_processus).erreur_systeme = d_es_processus;
1116: return(d_faux);
1117: }
1118:
1119: return(d_faux);
1120: }
1121: }
1122:
1123: dlerror();
1124:
1125: if (pthread_mutex_unlock(&mutex) != 0)
1126: {
1127: (*s_etat_processus).erreur_systeme = d_es_processus;
1128: return(d_faux);
1129: }
1130:
1131: /*
1132: * Exécution de la fonction externe
1133: */
1134:
1135: rpl_arguments.l_base_pile = (*s_etat_processus).l_base_pile;
1136: rpl_arguments.l_base_pile_last = (*s_etat_processus).l_base_pile_last;
1137:
1138: for(i = 0; i < 8; i++)
1139: {
1140: rpl_arguments.drapeaux_etat[i] =
1141: (*s_etat_processus).drapeaux_etat[i];
1142: }
1143:
1144: rpl_arguments.message_erreur = NULL;
1145: rpl_arguments.type_erreur = 'E';
1146: rpl_arguments.erreur = 0;
1147: rpl_arguments.aide = ((*s_etat_processus).affichage_arguments
1148: == 'N') ? d_faux : d_vrai;
1149: rpl_arguments.affichage_arguments = (*s_etat_processus)
1150: .affichage_arguments;
1151: rpl_arguments.test_instruction = (*s_etat_processus).test_instruction;
1152: rpl_arguments.constante_symbolique = (*s_etat_processus)
1153: .constante_symbolique;
1154: rpl_arguments.instruction_valide = 'N';
1155: rpl_arguments.s_etat_processus = s_etat_processus;
1156:
1157: (*s_etat_processus).erreur_execution = d_ex;
1158:
1159: if ((*s_etat_processus).profilage == d_vrai)
1160: {
1161: if ((tampon = malloc(strlen((*s_etat_processus)
1162: .s_instructions_externes[moyenne].nom_bibliotheque)
1163: + strlen(nom_fonction) + 2)) == NULL)
1164: {
1165: (*s_etat_processus).erreur_systeme = d_es_allocation_memoire;
1166: return(d_faux);
1167: }
1168:
1169: sprintf(tampon, "%s$%s", (*s_etat_processus).s_instructions_externes
1170: [moyenne].nom_bibliotheque, nom_fonction);
1171: profilage(s_etat_processus, tampon);
1172: free(tampon);
1173:
1174: if ((*s_etat_processus).erreur_systeme != d_es)
1175: {
1176: return(d_faux);
1177: }
1178: }
1179:
1180: # ifndef SEMAPHORES_NOMMES
1181: if (sem_post(&((*s_etat_processus).semaphore_fork)) != 0)
1182: {
1183: (*s_etat_processus).erreur_systeme = d_es_processus;
1184: return(d_faux);
1185: }
1186: # else
1187: if (sem_post((*s_etat_processus).semaphore_fork) != 0)
1188: {
1189: (*s_etat_processus).erreur_systeme = d_es_processus;
1190: return(d_faux);
1191: }
1192: # endif
1193:
1194: (*fonction)(&rpl_arguments);
1195:
1196: # ifndef SEMAPHORES_NOMMES
1197: while(sem_wait(&((*s_etat_processus).semaphore_fork)) == -1)
1198: {
1199: if (errno != EINTR)
1200: {
1201: (*s_etat_processus).erreur_systeme = d_es_processus;
1202: return(d_faux);
1203: }
1204: }
1205: # else
1206: while(sem_wait((*s_etat_processus).semaphore_fork) == -1)
1207: {
1208: if (errno != EINTR)
1209: {
1210: (*s_etat_processus).erreur_systeme = d_es_processus;
1211: return(d_faux);
1212: }
1213: }
1214: # endif
1215:
1216: if ((*s_etat_processus).profilage == d_vrai)
1217: {
1218: profilage(s_etat_processus, NULL);
1219: }
1220:
1221: (*s_etat_processus).nombre_arguments = rpl_arguments.nombre_arguments;
1222: (*s_etat_processus).constante_symbolique = rpl_arguments
1223: .constante_symbolique;
1224: (*s_etat_processus).instruction_valide = rpl_arguments
1225: .instruction_valide;
1226:
1227: if ((*s_etat_processus).test_instruction == 'Y')
1228: {
1229: if ((*s_etat_processus).nombre_arguments == 0)
1230: {
1231: (*s_etat_processus).nombre_arguments = -1;
1232: }
1233: }
1234:
1235: if (rpl_arguments.erreur != 0)
1236: {
1237: if (((*s_etat_processus).arret_si_exception == d_vrai) ||
1238: (rpl_arguments.type_erreur == 'S'))
1239: {
1240: if (test_cfsf(s_etat_processus, 51) == d_faux)
1241: {
1242: printf("%s", ds_beep);
1243: }
1244:
1245: if (rpl_arguments.type_erreur == 'S')
1246: {
1247: (*s_etat_processus).derniere_erreur_execution = -1;
1248:
1249: if ((*s_etat_processus).langue == 'F')
1250: {
1251: printf("+++Système : Fonction dynamique %s (ligne %lld)\n",
1252: nom_fonction, rpl_arguments.erreur);
1253: }
1254: else
1255: {
1256: printf("+++System : %s dynamic function (line %lld)\n",
1257: nom_fonction, rpl_arguments.erreur);
1258: }
1259: }
1260: else
1261: {
1262: (*s_etat_processus).derniere_erreur_systeme = -1;
1263:
1264: if ((*s_etat_processus).langue == 'F')
1265: {
1266: printf("+++Erreur : Fonction dynamique %s (ligne %lld)\n",
1267: nom_fonction, rpl_arguments.erreur);
1268: }
1269: else
1270: {
1271: printf("+++Error : %s dynamic function (line %lld)\n",
1272: nom_fonction, rpl_arguments.erreur);
1273: }
1274: }
1275:
1276: if (rpl_arguments.message_erreur != NULL)
1277: {
1278: printf("%s\n", rpl_arguments.message_erreur);
1279: }
1280:
1281: fflush(stdout);
1282: }
1283:
1284: if (rpl_arguments.type_erreur == 'S')
1285: {
1286: (*s_etat_processus).erreur_systeme =
1287: d_es_execution_bibliotheque;
1288: }
1289: else
1290: {
1291: (*s_etat_processus).erreur_execution =
1292: d_ex_execution_bibliotheque;
1293: }
1294: }
1295:
1296: (*s_etat_processus).l_base_pile = rpl_arguments.l_base_pile;
1297: (*s_etat_processus).l_base_pile_last = rpl_arguments.l_base_pile_last;
1298:
1299: for(i = 0; i < 8; i++)
1300: {
1301: (*s_etat_processus).drapeaux_etat[i] =
1302: rpl_arguments.drapeaux_etat[i];
1303: }
1304:
1305: l_element_courant = (*s_etat_processus).l_base_pile;
1306: (*s_etat_processus).hauteur_pile_operationnelle = 0;
1307:
1308: while(l_element_courant != NULL)
1309: {
1310: (*s_etat_processus).hauteur_pile_operationnelle++;
1311: l_element_courant = (*l_element_courant).suivant;
1312: }
1313:
1314: #undef return
1315: return(d_vrai);
1316: }
1317:
1318:
1319: /*
1320: ================================================================================
1321: Wrapper vers une fonction intrinsèque
1322: ================================================================================
1323: Entrée :
1324: --------------------------------------------------------------------------------
1325: Sortie :
1326: --------------------------------------------------------------------------------
1327: Effets de bord : néant
1328: ================================================================================
1329: */
1330:
1331: int
1332: wrapper_instruction_intrinseque(void (*fonction)(),
1333: struct_rpl_arguments *rpl_arguments)
1334: {
1335: int i;
1336:
1337: logical1 registre31;
1338:
1339: struct_liste_chainee *l_element_courant;
1340:
1341: struct_processus *s_etat_processus;
1342:
1343: s_etat_processus = (*rpl_arguments).s_etat_processus;
1344:
1345: (*s_etat_processus).nombre_arguments = (*rpl_arguments).nombre_arguments;
1346: (*s_etat_processus).constante_symbolique = (*rpl_arguments)
1347: .constante_symbolique;
1348: (*s_etat_processus).instruction_valide = (*rpl_arguments)
1349: .instruction_valide;
1350: (*s_etat_processus).l_base_pile = (*rpl_arguments).l_base_pile;
1351: (*s_etat_processus).l_base_pile_last = (*rpl_arguments).l_base_pile_last;
1352:
1353: for(i = 0; i < 8; i++)
1354: {
1355: (*s_etat_processus).drapeaux_etat[i] =
1356: (*rpl_arguments).drapeaux_etat[i];
1357: }
1358:
1359: l_element_courant = (*s_etat_processus).l_base_pile;
1360: (*s_etat_processus).hauteur_pile_operationnelle = 0;
1361:
1362: while(l_element_courant != NULL)
1363: {
1364: (*s_etat_processus).hauteur_pile_operationnelle++;
1365: l_element_courant = (*l_element_courant).suivant;
1366: }
1367:
1368: registre31 = test_cfsf(s_etat_processus, 31);
1369: cf(s_etat_processus, 31);
1370:
1371: (*fonction)(s_etat_processus);
1372:
1373: if (registre31 == d_vrai)
1374: {
1375: sf(s_etat_processus, 31);
1376: }
1377: else
1378: {
1379: cf(s_etat_processus, 31);
1380: }
1381:
1382: (*rpl_arguments).l_base_pile = (*s_etat_processus).l_base_pile;
1383: (*rpl_arguments).l_base_pile_last = (*s_etat_processus).l_base_pile_last;
1384:
1385: for(i = 0; i < 8; i++)
1386: {
1387: (*rpl_arguments).drapeaux_etat[i] =
1388: (*s_etat_processus).drapeaux_etat[i];
1389: }
1390:
1391: (*rpl_arguments).message_erreur = NULL;
1392: (*rpl_arguments).type_erreur = 'E';
1393: (*rpl_arguments).erreur = 0;
1394: (*rpl_arguments).aide = ((*s_etat_processus).affichage_arguments
1395: == 'N') ? d_faux : d_vrai;
1396: (*rpl_arguments).affichage_arguments = (*s_etat_processus)
1397: .affichage_arguments;
1398: (*rpl_arguments).test_instruction = (*s_etat_processus).test_instruction;
1399: (*rpl_arguments).constante_symbolique = (*s_etat_processus)
1400: .constante_symbolique;
1401: (*rpl_arguments).instruction_valide = 'Y';
1402: (*rpl_arguments).s_etat_processus = s_etat_processus;
1403:
1404: if (((*s_etat_processus).erreur_execution != d_ex) ||
1405: ((*s_etat_processus).exception != d_ep))
1406: {
1407: return(1);
1408: }
1409:
1410: if ((*s_etat_processus).erreur_systeme != d_es)
1411: {
1412: return(2);
1413: }
1414:
1415: (*s_etat_processus).erreur_execution = d_ex;
1416: (*s_etat_processus).erreur_systeme = d_es;
1417: (*s_etat_processus).exception = d_ep;
1418:
1419: return(0);
1420: }
1421:
1422:
1423: /*
1424: ================================================================================
1425: Procédure d'empilement d'un nouvel élément
1426: ================================================================================
1427: Entrée :
1428: --------------------------------------------------------------------------------
1429: Sortie :
1430: --------------------------------------------------------------------------------
1431: Effets de bord : néant
1432: ================================================================================
1433: */
1434:
1435: struct_liste_chainee *
1436: empilement_pile_operationnelle(struct_rpl_arguments *s_rpl_arguments,
1437: struct_objet *s_objet)
1438: {
1439: struct_liste_chainee *l_ancienne_base_liste;
1440: struct_liste_chainee *l_nouvelle_base_liste;
1441:
1442: l_ancienne_base_liste = (*s_rpl_arguments).l_base_pile;
1443:
1444: l_nouvelle_base_liste = (struct_liste_chainee *) malloc(
1445: sizeof(struct_liste_chainee));
1446:
1447: if (l_nouvelle_base_liste != NULL)
1448: {
1449: (*l_nouvelle_base_liste).donnee = s_objet;
1450: (*l_nouvelle_base_liste).suivant = l_ancienne_base_liste;
1451: }
1452:
1453: (*s_rpl_arguments).l_base_pile = l_nouvelle_base_liste;
1454:
1455: return l_nouvelle_base_liste;
1456: }
1457:
1458:
1459: /*
1460: ================================================================================
1461: Procédure de dépilement d'un élément. L'emplacement est libéré dans la pile.
1462: ================================================================================
1463: Entrée :
1464: --------------------------------------------------------------------------------
1465: Sortie :
1466: --------------------------------------------------------------------------------
1467: Effets de bord : néant
1468: ================================================================================
1469: */
1470:
1471: struct_liste_chainee *
1472: depilement_pile_operationnelle(struct_rpl_arguments *s_rpl_arguments,
1473: struct_objet **s_objet)
1474: {
1475: struct_liste_chainee *l_ancienne_base_liste;
1476: struct_liste_chainee *l_nouvelle_base_liste;
1477:
1478: if ((*s_rpl_arguments).l_base_pile == NULL)
1479: {
1480: *s_objet = NULL;
1481: return(NULL);
1482: }
1483: else
1484: {
1485: l_ancienne_base_liste = (*s_rpl_arguments).l_base_pile;
1486: l_nouvelle_base_liste = (*l_ancienne_base_liste).suivant;
1487:
1488: *s_objet = (*l_ancienne_base_liste).donnee;
1489: free(l_ancienne_base_liste);
1490:
1491: (*s_rpl_arguments).l_base_pile = l_nouvelle_base_liste;
1492:
1493: return(l_nouvelle_base_liste);
1494: }
1495: }
1496:
1497:
1498: /*
1499: ================================================================================
1500: Procédure de sauvegarde des arguments dans la pile last
1501: ================================================================================
1502: Entrée : structure processus et nombre d'aguments à empiler
1503: --------------------------------------------------------------------------------
1504: Sortie : drapeau d'erreur de la structure rpl_arguments
1505: --------------------------------------------------------------------------------
1506: Effets de bord : efface le précédent contenu de la pile LAST
1507: ================================================================================
1508: */
1509:
1510: struct_liste_chainee *
1511: sauvegarde_arguments(struct_rpl_arguments *s_rpl_arguments,
1512: unsigned long nombre_arguments)
1513: {
1514: struct_liste_chainee *l_ancienne_base_liste;
1515: struct_liste_chainee *l_element_courant;
1516: struct_liste_chainee *l_element_suivant;
1517: struct_liste_chainee *l_nouvelle_base_liste;
1518:
1519: struct_objet *s_objet;
1520:
1521: logical1 erreur;
1522:
1523: t_8_bits masque;
1524:
1525: unsigned char indice_bit;
1526: unsigned char indice_bloc;
1527: unsigned char indice_drapeau;
1528: unsigned char taille_bloc;
1529:
1530: unsigned long i;
1531:
1532: struct_processus *s_etat_processus;
1533:
1534: (*s_rpl_arguments).erreur = 0;
1535: s_etat_processus = (*s_rpl_arguments).s_etat_processus;
1536:
1537: indice_drapeau = 31;
1538: indice_drapeau--;
1539: taille_bloc = sizeof(t_8_bits) * 8;
1540: indice_bloc = indice_drapeau / taille_bloc;
1541: indice_bit = indice_drapeau % taille_bloc;
1542:
1543: masque = ((t_8_bits) 1) << (taille_bloc - indice_bit - 1);
1544:
1545: if (((*s_rpl_arguments).drapeaux_etat[indice_bloc] & masque) == 0)
1546: {
1547: return (*s_rpl_arguments).l_base_pile_last;
1548: }
1549:
1550: erreur = d_absence_erreur;
1551:
1552: l_element_courant = (*s_rpl_arguments).l_base_pile_last;
1553: while(l_element_courant != NULL)
1554: {
1555: liberation(s_etat_processus, (*l_element_courant).donnee);
1556: l_element_suivant = (*l_element_courant).suivant;
1557: free(l_element_courant);
1558: l_element_courant = l_element_suivant;
1559: }
1560:
1561: (*s_rpl_arguments).l_base_pile_last = NULL;
1562: l_element_courant = (*s_rpl_arguments).l_base_pile;
1563: l_nouvelle_base_liste = (*s_rpl_arguments).l_base_pile_last;
1564:
1565: for(i = 0; ((i < nombre_arguments) && (erreur == d_absence_erreur)
1566: && (l_element_courant != NULL)); i++)
1567: {
1568: s_objet = copie_objet(s_etat_processus,
1569: (*l_element_courant).donnee, 'P');
1570:
1571: if (s_objet != NULL)
1572: {
1573: l_ancienne_base_liste = l_nouvelle_base_liste;
1574: l_nouvelle_base_liste = (struct_liste_chainee *) malloc(
1575: sizeof(struct_liste_chainee));
1576:
1577: if (l_nouvelle_base_liste != NULL)
1578: {
1579: (*l_nouvelle_base_liste).donnee = s_objet;
1580: (*l_nouvelle_base_liste).suivant = l_ancienne_base_liste;
1581:
1582: }
1583: else
1584: {
1585: erreur = d_erreur;
1586: }
1587:
1588: l_element_courant = (*l_element_courant).suivant;
1589: }
1590: else
1591: {
1592: erreur = d_erreur;
1593: }
1594: }
1595:
1596: if (i != nombre_arguments)
1597: {
1598: /*
1599: * Erreur système : la pile est vidée et la routine renvoie NULL.
1600: */
1601:
1602: l_element_courant = l_nouvelle_base_liste;
1603: while(l_element_courant != NULL)
1604: {
1605: liberation(s_etat_processus, (*l_element_courant).donnee);
1606: l_element_suivant = (*l_element_courant).suivant;
1607: free(l_element_courant);
1608: l_element_courant = l_element_suivant;
1609: }
1610:
1611: l_nouvelle_base_liste = NULL;
1612: (*s_rpl_arguments).erreur = i;
1613: }
1614:
1615: return(l_nouvelle_base_liste);
1616: }
1617:
1618:
1619: /*
1620: ================================================================================
1621: Procédure de tri des symboles externes
1622:
1623: Principe du tri dit de Shell-Metzner
1624: ================================================================================
1625: Entrée :
1626: --------------------------------------------------------------------------------
1627: Sortie :
1628: --------------------------------------------------------------------------------
1629: Effets de bord : néant
1630: ================================================================================
1631: */
1632:
1633: void
1634: tri_base_symboles_externes(struct_processus *s_etat_processus)
1635: {
1636: logical1 terminaison_boucle;
1637: logical1 terminaison_boucle_1;
1638: logical1 terminaison_boucle_2;
1639: logical1 terminaison_boucle_3;
1640:
1641: signed long indice_i;
1642: signed long indice_j;
1643: signed long indice_k;
1644: signed long indice_l;
1645:
1646: unsigned long borne_inferieure;
1647: unsigned long borne_superieure;
1648: unsigned long ecartement;
1649: unsigned long indice;
1650:
1651: ecartement = (*s_etat_processus).nombre_instructions_externes;
1652:
1653: terminaison_boucle_1 = d_faux;
1654:
1655: do
1656: {
1657: ecartement = ecartement / 2;
1658:
1659: if (ecartement >= 1)
1660: {
1661: indice_j = 0;
1662: indice_k = (*s_etat_processus).nombre_instructions_externes
1663: - ecartement;
1664:
1665: terminaison_boucle_2 = d_faux;
1666:
1667: do
1668: {
1669: indice_i = indice_j;
1670: terminaison_boucle_3 = d_faux;
1671:
1672: do
1673: {
1674: indice_l = indice_i + ecartement;
1675:
1676: if ((indice_i > 0) && (indice_l > 0))
1677: {
1678: if (strcmp(((*s_etat_processus).s_instructions_externes
1679: [indice_i - 1]).nom, ((*s_etat_processus)
1680: .s_instructions_externes[indice_l - 1]).nom)
1681: > 0)
1682: {
1683: swap((void *) &((*s_etat_processus)
1684: .s_instructions_externes
1685: [indice_i - 1]), (void *)
1686: &((*s_etat_processus)
1687: .s_instructions_externes[indice_l - 1]),
1688: sizeof(struct_instruction_externe));
1689:
1690: indice_i -= ecartement;
1691:
1692: if (indice_i < 1)
1693: {
1694: terminaison_boucle_3 = d_vrai;
1695: }
1696: }
1697: else
1698: {
1699: terminaison_boucle_3 = d_vrai;
1700: }
1701: }
1702: else
1703: {
1704: terminaison_boucle_3 = d_vrai;
1705: }
1706: } while(terminaison_boucle_3 == d_faux);
1707:
1708: indice_j++;
1709:
1710: if (indice_j > indice_k)
1711: {
1712: terminaison_boucle_2 = d_vrai;
1713: }
1714: } while(terminaison_boucle_2 == d_faux);
1715: }
1716: else
1717: {
1718: terminaison_boucle_1 = d_vrai;
1719: }
1720: } while(terminaison_boucle_1 == d_faux);
1721:
1722: indice_i = 0;
1723:
1724: do
1725: {
1726: indice_j = indice_i;
1727:
1728: while(((unsigned long) (indice_i + 1) < (*s_etat_processus)
1729: .nombre_instructions_externes) && (strcmp(((*s_etat_processus)
1730: .s_instructions_externes[indice_i]).nom, ((*s_etat_processus)
1731: .s_instructions_externes[indice_i + 1]).nom) == 0))
1732: {
1733: indice_i++;
1734: }
1735:
1736: borne_inferieure = indice_j;
1737: borne_superieure = indice_i;
1738:
1739: do
1740: {
1741: terminaison_boucle = d_vrai;
1742:
1743: for(indice = borne_inferieure + 1; indice <= borne_superieure;
1744: indice++)
1745: {
1746: if (strcmp((*s_etat_processus).s_instructions_externes[indice]
1747: .nom_bibliotheque, (*s_etat_processus)
1748: .s_instructions_externes[indice - 1].nom_bibliotheque)
1749: < 0)
1750: {
1751: swap((void *) &((*s_etat_processus).s_instructions_externes
1752: [indice - 1]), (void *) &((*s_etat_processus)
1753: .s_instructions_externes[indice]),
1754: sizeof(struct_instruction_externe));
1755:
1756: terminaison_boucle = d_faux;
1757: }
1758: }
1759: } while(terminaison_boucle == d_faux);
1760:
1761: indice_i++;
1762: } while((unsigned long) (indice_i + 1) <
1763: (*s_etat_processus).nombre_instructions_externes);
1764:
1765: return;
1766: }
1767:
1768: // vim: ts=4
CVSweb interface <joel.bertrand@systella.fr>