Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
start new example with parsing lex/yacc of automaton in promela
[simgrid.git] / examples / msg / mc / automaton.c
1 #include "automaton.h"
2
3 xbt_automaton_t xbt_automaton_new_automaton(){
4   xbt_automaton_t automaton = NULL;
5   automaton = xbt_new0(struct xbt_automaton, 1);
6   automaton->states = xbt_dynar_new(sizeof(xbt_state_t), NULL);
7   automaton->transitions = xbt_dynar_new(sizeof(xbt_transition_t), NULL);
8   automaton->propositional_symbols = xbt_dynar_new(sizeof(xbt_propositional_symbol_t), NULL);
9   return automaton;
10 }
11
12 xbt_state_t xbt_automaton_new_state(xbt_automaton_t a, int type, char* id){
13   xbt_state_t state = NULL;
14   state = xbt_new0(struct xbt_state, 1);
15   state->visited = 0;
16   state->type = type;
17   state->id = strdup(id);
18   state->in = xbt_dynar_new(sizeof(xbt_transition_t), NULL);
19   state->out = xbt_dynar_new(sizeof(xbt_transition_t), NULL); 
20   xbt_dynar_push(a->states, &state);
21   return state;
22 }
23
24 xbt_transition_t xbt_automaton_new_transition(xbt_automaton_t a, xbt_state_t src, xbt_state_t dst, xbt_exp_label_t label){
25   xbt_transition_t transition = NULL;
26   transition = xbt_new0(struct xbt_transition, 1);
27   if(src != NULL){
28     xbt_dynar_push(src->out, &transition);
29     transition->src = src;
30   }
31   if(dst != NULL){
32     xbt_dynar_push(dst->in, &transition);
33     transition->dst = dst;
34   }
35   transition->label = label;
36   xbt_dynar_push(a->transitions, &transition);
37   return transition;
38 }
39
40 xbt_exp_label_t xbt_automaton_new_label(int type, ...){
41   xbt_exp_label_t label = NULL;
42   label = xbt_new0(struct xbt_exp_label, 1);
43   label->type = type;
44
45   va_list ap;
46   va_start(ap, type);
47   switch(type){
48   case 0 : {
49     xbt_exp_label_t left = va_arg(ap, xbt_exp_label_t);
50     xbt_exp_label_t right = va_arg(ap, xbt_exp_label_t);
51     label->u.or_and.left_exp = left;
52     label->u.or_and.right_exp = right;
53     break;
54   }
55   case 1 : {
56     xbt_exp_label_t left = va_arg(ap, xbt_exp_label_t);
57     xbt_exp_label_t right = va_arg(ap, xbt_exp_label_t);
58     label->u.or_and.left_exp = left;
59     label->u.or_and.right_exp = right;
60     break;
61   }
62   case 2 : {
63     xbt_exp_label_t exp_not = va_arg(ap, xbt_exp_label_t);
64     label->u.exp_not = exp_not;
65     break;
66   }
67   case 3 :{
68     char* p = va_arg(ap, char*);
69     label->u.predicat = strdup(p);
70     break;
71   }
72   }
73   va_end(ap);
74   return label;
75 }
76
77
78 xbt_dynar_t xbt_automaton_get_states(xbt_automaton_t a){
79   return a->states;
80 }
81
82 xbt_dynar_t xbt_automaton_get_transitions(xbt_automaton_t a){
83   return a->transitions;
84 }
85
86 xbt_transition_t xbt_automaton_get_transition(xbt_automaton_t a, xbt_state_t src, xbt_state_t dst){
87   xbt_transition_t transition;
88   unsigned int cursor;
89   xbt_dynar_foreach(src->out, cursor, transition){
90     if((transition->src == src) && (transition->dst == dst))
91       return transition;
92   }
93   return NULL;
94 }
95
96 void xbt_automaton_free_automaton(xbt_automaton_t a, void_f_pvoid_t transition_free_function){
97   unsigned int cursor = 0;
98   xbt_state_t state = NULL;
99   xbt_transition_t transition = NULL;
100
101   xbt_dynar_foreach(a->states, cursor, state){
102     xbt_dynar_free(&(state->out));
103     xbt_dynar_free(&(state->in));
104   }
105
106   xbt_dynar_foreach(a->transitions, cursor, transition){
107     if(transition_free_function) 
108       (*transition_free_function) (transition->label);
109   }
110
111   xbt_dynar_foreach(a->states, cursor, state)
112     free(state);
113   xbt_dynar_free(&(a->states));
114
115   xbt_dynar_foreach(a->transitions, cursor, state)
116     free(transition);
117   xbt_dynar_free(&(a->transitions));
118
119   free(a);
120
121   return;
122 }
123
124 void xbt_automaton_free_state(xbt_automaton_t a, xbt_state_t s, void_f_pvoid_t transition_free_function){
125   unsigned long nbr;
126   unsigned long i;
127   unsigned int cursor = 0;
128   xbt_state_t state = NULL;
129   xbt_transition_t transition = NULL;
130
131   nbr = xbt_dynar_length(a->transitions);
132   for(i = 0; i <nbr; i++){
133     xbt_dynar_get_cpy(a->transitions, cursor, &transition);
134     if((transition->src == s) || (transition->dst == s)){
135       xbt_automaton_free_transition(a, transition, transition_free_function);
136     }else{
137       cursor++;
138     }
139   }
140
141   cursor = 0;
142   xbt_dynar_foreach(a->states, cursor, state)
143     if(state == s)
144       xbt_dynar_cursor_rm(a->states, &cursor);
145
146   xbt_dynar_free(&(s->in));
147   xbt_dynar_free(&(s->out));
148
149   free(s);
150
151   return;
152 }
153
154 void xbt_automaton_free_transition(xbt_automaton_t a, xbt_transition_t t, void_f_pvoid_t transition_free_function){
155   int index;
156   unsigned int cursor = 0;
157   xbt_transition_t transition = NULL;
158
159   if((transition_free_function) && (t->label))
160     (*transition_free_function) (t->label);
161
162   xbt_dynar_foreach(a->transitions, cursor, transition) {
163     if(transition == t){
164       index = __xbt_find_in_dynar(transition->dst->in, transition);
165       xbt_dynar_remove_at(transition->dst->in, index, NULL);
166       index = __xbt_find_in_dynar(transition->src->out, transition);
167       xbt_dynar_remove_at(transition->src->out, index, NULL);
168       xbt_dynar_cursor_rm(a->transitions, & cursor);
169       free(transition);
170       break;
171     }  
172   }
173
174
175 xbt_state_t xbt_automaton_transition_get_source(xbt_transition_t t){
176   return t->src;
177 }
178
179 xbt_state_t xbt_automaton_transition_get_destination(xbt_transition_t t){
180   return t->dst;
181 }
182
183 void xbt_automaton_transition_set_source(xbt_transition_t t, xbt_state_t src){
184   t->src = src;
185   xbt_dynar_push(src->out,&t);
186 }
187
188 void xbt_automaton_transition_set_destination(xbt_transition_t t, xbt_state_t dst){
189   t->dst = dst;
190   xbt_dynar_push(dst->in,&t);
191 }
192
193 xbt_dynar_t xbt_automaton_state_get_out_transitions(xbt_state_t s){
194   return s->out;
195 }
196
197 xbt_dynar_t xbt_automaton_state_get_in_transitions(xbt_state_t s){
198   return s->in;
199 }
200
201 xbt_state_t xbt_automaton_state_exists(xbt_automaton_t a, char *id){
202   xbt_state_t state = NULL;
203   unsigned int cursor = 0;
204   xbt_dynar_foreach(a->states, cursor, state){
205    if(strcmp(state->id, id)==0)
206      return state;
207   }
208   return NULL;
209 }
210
211 void  xbt_automaton_display(xbt_automaton_t a){
212   unsigned int cursor = 0;
213   xbt_state_t state = NULL;
214
215   printf("\n\nEtat courant : %s\n", a->current_state->id);
216
217   printf("\nListe des ├ętats : %lu\n\n", xbt_dynar_length(a->states));
218  
219   
220   xbt_dynar_foreach(a->states, cursor, state){
221     printf("ID : %s, type : %d\n", state->id, state->type);
222   }
223
224   cursor=0;
225   xbt_transition_t transition = NULL;
226   printf("\nListe des transitions : %lu\n\n", xbt_dynar_length(a->transitions));
227   
228   xbt_dynar_foreach(a->transitions, cursor, transition){
229     printf("label :");
230     xbt_automaton_display_exp(transition->label);
231     printf(", %s -> %s\n", transition->src->id, transition->dst->id);
232   }
233 }
234
235 void xbt_automaton_display_exp(xbt_exp_label_t label){
236
237   switch(label->type){
238   case 0 :
239     printf("(");
240     xbt_automaton_display_exp(label->u.or_and.left_exp);
241     printf(" || ");
242     xbt_automaton_display_exp(label->u.or_and.right_exp);
243     printf(")");
244     break;
245   case 1 : 
246     printf("(");
247     xbt_automaton_display_exp(label->u.or_and.left_exp);
248     printf(" && ");
249     xbt_automaton_display_exp(label->u.or_and.right_exp);
250     printf(")");
251     break;
252   case 2 : 
253     printf("(!");
254     xbt_automaton_display_exp(label->u.exp_not);
255     printf(")");
256     break;
257   case 3 :
258     printf("(%s)",label->u.predicat);
259     break;
260   case 4 :
261     printf("(1)");
262     break;
263   }
264
265 }
266
267 xbt_state_t xbt_automaton_get_current_state(xbt_automaton_t a){
268   return a->current_state;
269 }
270
271 xbt_propositional_symbol_t xbt_new_propositional_symbol(xbt_automaton_t a, char* id, void* fct){
272   xbt_propositional_symbol_t prop_symb = NULL;
273   prop_symb = xbt_new0(struct xbt_propositional_symbol, 1);
274   prop_symb->pred = strdup(id);
275   prop_symb->function = fct;
276   xbt_dynar_push(a->propositional_symbols, &prop_symb);
277   return prop_symb;
278 }