/[pdpsoft]/trunk/grid-mw-security/ees/src/eval_man/pdl.c
ViewVC logotype

Annotation of /trunk/grid-mw-security/ees/src/eval_man/pdl.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1259 - (hide annotations) (download) (as text)
Wed Dec 9 14:13:11 2009 UTC (12 years, 5 months ago) by aramv
File MIME type: text/x-chdr
File size: 28242 byte(s)
Fixed silly bug in pdl parser. Updated Rspec test
1 aramv 526 #include "pdl.h"
2    
3 aramv 881 /* Lex/Yacc stuff */
4 aramv 1069 extern FILE * yyin;
5 aramv 1127 extern unsigned int lineno;
6 aramv 1069 extern int yyparse(void);
7     extern int yylex(void);
8 aramv 1127
9     /* Lex/Yacc cleanup functions */
10 aramv 1069 extern void delete_lex_buffer(void);
11 aramv 1127 #if HAVE_YYLEX_DESTROY
12     extern int yylex_destroy(void);
13     #endif
14 aramv 881
15 aramv 1069 /* internal data */
16 aramv 1085 static const char* config_file_s;
17 aramv 1077 FILE* config_file_fp;
18 aramv 1069 static char* _pdl_path;
19 aramv 1085
20 aramv 1235 int recursion_was_created;
21     int unknown_variable_was_referenced;
22 aramv 1236 int state_was_reused;
23 aramv 1235
24 aramv 1085 var_t* variables_list;
25     var_t* variables_list_last;
26 aramv 1077 var_t* current_variable;
27 aramv 891
28 aramv 1085 rule_t* rules_list;
29     rule_t* rules_list_last;
30     rule_t* current_rule;
31    
32 aramv 1123 policy_t* policies_list;
33     policy_t* policies_list_last;
34     policy_t* current_policy;
35    
36 aramv 1235 /* This function does everything parser related. After running yacc through wrap_yacc(), the created list is reduced to those in the array of named policies, of number_of_policies is greater than 0. The policies are checked for unreachable rules. After the parser has created a list of policies containing lists of rules, these rules are transformed to a tree by the link_dead_end_rules_in_policies() function. Finally, when a list of policies containing rules trees was created, the plug-ins are linked to each rule in the node. */
37     EES_RC start_pdl_parser(char *config_file, int number_of_policies, char* names_of_policies[]){
38     recursion_was_created = 0;
39 aramv 1236 unknown_variable_was_referenced = 0;
40     state_was_reused = 0;
41 aramv 1235
42     eef_log(LOG_NOTICE, "Loading config file: %s\n", config_file);
43     if(wrap_yacc(config_file) == EES_SUCCESS){
44     /* after the config file was successfully parsed, the policies and path to plugins are accessible. We can try to set the global (EEF-wide) modules path if one was provided */
45     eef_log(LOG_NOTICE, "Loaded config file: %s\n", config_file);
46    
47     /* set the EEF modules path to the path found by the evaluation manager */
48     set_modules_path(get_pdl_path());
49    
50     /* strip policies that are not explicitly passed in the names_of_policies array */
51     if(number_of_policies){
52 aramv 1259 policies_list = reduce_policies(policies_list, number_of_policies, names_of_policies);
53 aramv 1235 }
54    
55 aramv 1259 if(remove_unreachable_rules_in_policies(policies_list) == EES_SUCCESS){
56     if(policies_list){
57     link_dead_end_rules_in_policies(policies_list);
58     link_rules_to_plugins(policies_list);
59 aramv 1235 }
60     eef_log(LOG_INFO, "Your configuration file seems sane.\n");
61 aramv 1259 print_policies(policies_list);
62 aramv 1235
63     /* this is a callout to the plugin manager, which dlopen()'s the plugin, dlsym()'s the plugin's functions and calls the plugin's initialize function */
64     if(initialize_plugins() == EES_SUCCESS){
65     return EES_SUCCESS;
66     } else {
67     eef_log(LOG_ERR, "Failed to initialize plug-ins from policy config file %s\n", config_file);
68     }
69     } else {
70     eef_log(LOG_ERR, "The loaded configuration file defines unreachable rules. Please check your configuration file.");
71     }
72     } else {
73     if(recursion_was_created){
74     eef_log(LOG_ERR, "The loaded configuration file defines recursive rules. Please check your configuration file.");
75     }
76     if(unknown_variable_was_referenced){
77     eef_log(LOG_ERR, "The loaded configuration file references undefined variables. Please check your configuration file.");
78     }
79 aramv 1236 if(state_was_reused){
80     eef_log(LOG_ERR, "The loaded configuration file reuses a starting state. Please check your configuration file.");
81     }
82 aramv 1235 }
83     return EES_FAILURE;
84     }
85    
86    
87     /*! Initializes the parsing of the configuration file. When parsing has completed successfully, the policy_list is available. This can be transformed to a tree using the link_dead_end_rules_in_policies() function. */
88     EES_RC wrap_yacc(const char* config_file){
89     config_file_s = config_file;
90 aramv 1077 if((config_file_fp = fopen(config_file_s,"r")) != NULL){
91     yyin = config_file_fp;
92 aramv 592 yyparse();
93 aramv 1236 if(!recursion_was_created && !unknown_variable_was_referenced && !state_was_reused){
94 aramv 1235 /* callout to the plugin manager */
95     if(add_plugin_structs() == EES_SUCCESS){
96     return EES_SUCCESS;
97     } else {
98     eef_log(LOG_ERR, "Failed to load plug-ins from policy config file %s\n", config_file_s);
99 aramv 1233 }
100 aramv 890 }
101 aramv 526 } else {
102 aramv 1142 eef_log(LOG_ERR, "Failed to open policy config file %s", config_file_s);
103 aramv 526 }
104 aramv 1077 return EES_FAILURE;
105 aramv 526 }
106    
107 aramv 1156 policy_t* get_policies(){
108     return policies_list;
109     }
110    
111 aramv 1070 /*! sets the path to modules directory */
112 aramv 1142 void set_pdl_path(record_t* path){
113 aramv 592 size_t path_size = 0;
114 aramv 867 size_t string_size = (sizeof(char) * (strlen(path->string)+2)); /* size of string + extra slash + null byte */
115 aramv 881 _pdl_path = "";
116    
117 aramv 844 /*struct stat sb;*/
118     /*if stat(MODUL*/
119 aramv 867
120 aramv 592 if(string_size < FILENAME_MAX){
121     path_size = string_size;
122     } else {
123     path_size = FILENAME_MAX;
124     }
125    
126     if((_pdl_path = calloc(1, path_size))){
127     strncpy(_pdl_path, path->string, path_size);
128 aramv 867 strncat(_pdl_path, "/", 1);
129 aramv 592 }
130 aramv 1070
131     eef_log(LOG_DEBUG, "Found a new modules path: %s\n", _pdl_path);
132    
133 aramv 566 free(path->string);
134 aramv 1211 path->string = NULL;
135 aramv 566 free(path);
136 aramv 1211 path = NULL;
137 aramv 526 }
138    
139 aramv 1077 /*! Handles a variable representing a plug-in; creates a structure containing its values and adds it to the list of var_t structs variables_list */
140     void add_variable(record_t* name, record_t* value){
141 aramv 1142 eef_log(LOG_DEBUG, "Added variable name: %s\n", name->string);
142     eef_log(LOG_DEBUG, "Added variable value: %s\n", value->string);
143 aramv 566
144 aramv 1077 /* allocate struct and populate fields */
145     if((current_variable = calloc(1,sizeof(var_t)))){
146     current_variable->name = strdup(name->string);
147     current_variable->value = strdup(value->string);
148     current_variable->lineno = name->lineno;
149     current_variable->next = NULL;
150     } else {
151     eef_log(LOG_ERR, "Out of memory!");
152     }
153 aramv 526
154 aramv 1077 /* append to the end of the list */
155     if(variables_list){
156     variables_list_last->next = current_variable;
157     } else {
158     variables_list = current_variable;
159 aramv 890 }
160 aramv 1077 variables_list_last = current_variable;
161    
162     /* clean up */
163     free(name->string);
164 aramv 1211 name->string = NULL;
165 aramv 1077 free(name);
166 aramv 1211 name = NULL;
167 aramv 1077 free(value->string);
168 aramv 1211 value->string = NULL;
169 aramv 1077 free(value);
170 aramv 1211 value = NULL;
171 aramv 526 }
172    
173 aramv 1142 /* TODO I think this function is a bit of a kludge and could probably be rewritten to be more efficient and more legible - I think it might do too much, so extracting some functions might help */
174 aramv 1127 /*! Appends a rule to the global rules_list, which is to be added to a policy when add_policy is called
175 aramv 1235 Will return NULL and log an error when:
176 aramv 1127 - adding the rule to the list will create a recursion in the tree of rules
177     - an unknown variable is referenced
178     */
179 aramv 1077 rule_t* add_rule(record_t* state, record_t* true_branch, record_t* false_branch){
180 aramv 1127 rule_t *new_rule = NULL, *new_false_branch = NULL, *new_true_branch = NULL, *recursive_rule = NULL;
181 aramv 1142 var_t *temp_var = NULL;
182     char *unknown_var_format_string = "Unknown variable %s at line %i in config file %s";
183 aramv 1077
184 aramv 1224 if((new_rule = get_left_hand_rule(rules_list, state->string))){
185 aramv 1085 eef_log(LOG_WARNING, "State %s at line %i is already in use at line %i.\n", state->string, state->lineno, new_rule->lineno);
186 aramv 1236 state_was_reused = 1;
187 aramv 1085 } else {
188     /*find variables for rule */
189 aramv 1142 temp_var = get_variable_by_name(state->string);
190     if(temp_var == NULL){
191     /* Errorous state - variable referenced in rule not previously defined */
192     eef_log(LOG_ERR, unknown_var_format_string, state->string, state->lineno, config_file_s);
193 aramv 1235 unknown_variable_was_referenced = 1;
194 aramv 1224 new_rule = clean_rules_tree(new_rule);
195     goto cleanup;
196 aramv 1142 }
197     if(temp_var != NULL){
198 aramv 1085 if((new_rule = calloc(1, sizeof(rule_t)))){
199 aramv 1101 /* populate fields of current state */
200 aramv 1085 new_rule->state = strdup(state->string);
201     new_rule->lineno = state->lineno;
202    
203 aramv 1101 /* populate fields of branches */
204     if(false_branch){
205 aramv 1142 temp_var = get_variable_by_name(false_branch->string);
206     if(temp_var == NULL){
207     /* Errorous state - variable referenced in rule not previously defined */
208     eef_log(LOG_ERR, unknown_var_format_string, false_branch->string, false_branch->lineno, config_file_s);
209 aramv 1235 unknown_variable_was_referenced = 1;
210 aramv 1224 new_rule = clean_rules_tree(new_rule);
211     goto cleanup;
212     } else {
213     if((new_false_branch = calloc(1, sizeof(rule_t)))){
214     new_false_branch->state = strdup(false_branch->string);
215     new_false_branch->lineno = false_branch->lineno;
216     new_rule->false_branch = new_false_branch;
217     }
218 aramv 1142 }
219 aramv 1101 }
220 aramv 1127
221 aramv 1085 if(true_branch){
222 aramv 1142 temp_var = get_variable_by_name(true_branch->string);
223     if(temp_var == NULL){
224     /* Errorous state - variable referenced in rule not previously defined */
225     eef_log(LOG_ERR, unknown_var_format_string, true_branch->string, true_branch->lineno, config_file_s);
226 aramv 1235 unknown_variable_was_referenced = 1;
227 aramv 1224 new_rule = clean_rules_tree(new_rule);
228     goto cleanup;
229     } else {
230     if((new_true_branch = calloc(1, sizeof(rule_t)))){
231     new_true_branch->state = strdup(true_branch->string);
232     new_true_branch->lineno = true_branch->lineno;
233     new_rule->true_branch = new_true_branch;
234     }
235 aramv 1142 }
236 aramv 1085 }
237    
238 aramv 1101 /* check for recursion */
239     if((recursive_rule = check_for_recursion(rules_list, new_rule))){
240 aramv 1103 eef_log(LOG_WARNING, "Rule %s at line %i leads to recursion into state %s", new_rule->state, new_rule->lineno, recursive_rule->state);
241 aramv 1224 new_rule = clean_rules_tree(new_rule);
242 aramv 1235 recursion_was_created = 1;
243 aramv 1259 goto cleanup;
244 aramv 1085 } else {
245 aramv 1101 /* add new rule at the end of the rules list */
246     if(rules_list){
247     rules_list_last->next = new_rule;
248     } else {
249     rules_list = new_rule;
250     }
251     rules_list_last = new_rule;
252 aramv 1202
253 aramv 1201 eef_log(LOG_DEBUG, "Added a new rule: %s\n", new_rule->state);
254 aramv 1085 }
255 aramv 1101
256 aramv 1085 } else {
257     eef_log(LOG_ERR, "Out of memory!");
258     }
259 aramv 1077 }
260 aramv 566 }
261 aramv 1077
262 aramv 1224 cleanup:
263    
264 aramv 1077 /* clean up */
265     if(state != NULL){
266     free(state->string);
267     free(state);
268     }
269 aramv 566 if(true_branch != NULL){
270     free(true_branch->string);
271 aramv 1077 free(true_branch);
272 aramv 566 }
273     if(false_branch != NULL){
274     free(false_branch->string);
275 aramv 1077 free(false_branch);
276 aramv 566 }
277 aramv 1077
278 aramv 566 return new_rule;
279 aramv 526 }
280    
281 aramv 1127 /* Tries to find a recursion in the list of rules by iterating through all the tree branches. When the same rule is encountered in the current list a recursion has been found */
282 aramv 1101 rule_t* check_for_recursion(rule_t* rule_l, rule_t* rule_r){
283 aramv 1106 rule_t* temp_rule = rule_l;
284 aramv 1112
285     /* right hand rule leads to its own recursive state */
286 aramv 1127 /* still need to find a way to reuse the code from the while loop to do this check */
287 aramv 1112 if(rule_r){
288     if(rule_r->true_branch){
289     if(strcmp(rule_r->state, rule_r->true_branch->state) == 0){
290     return rule_r->true_branch;
291     }
292     }
293    
294     if(rule_r->false_branch){
295     if(strcmp(rule_r->state, rule_r->false_branch->state) == 0){
296     return rule_r->false_branch;
297     }
298     }
299     }
300    
301 aramv 1127 /* iterate list of rules */
302 aramv 1106 while(temp_rule){
303     if((temp_rule != NULL) && (rule_r != NULL)){
304     /* left hand and right hand state are equal */
305     if(strcmp(temp_rule->state, rule_r->state) == 0){
306     return rule_r;
307 aramv 1101 }
308 aramv 1112
309 aramv 1106 /* start state and true branch of right hand rule are equal */
310     if(rule_r->true_branch){
311     if(strcmp(temp_rule->state, rule_r->true_branch->state) == 0){
312     return rule_r->true_branch;
313     }
314     }
315 aramv 1108
316     /* start state and false branch of right hand side are equal */
317     if(rule_r->false_branch){
318     if(strcmp(temp_rule->state, rule_r->false_branch->state) == 0){
319     return rule_r->false_branch;
320     }
321     }
322 aramv 1101 }
323 aramv 1127
324 aramv 1106 /* move to next rule */
325     temp_rule = temp_rule->next;
326 aramv 1101 }
327 aramv 1106 return NULL;
328 aramv 1101 }
329    
330 aramv 1235 /* This function iterates the passed list of policies and removes unreachable rules from each policy */
331 aramv 1233 EES_RC remove_unreachable_rules_in_policies(policy_t* policies){
332 aramv 1224 policy_t *temp_policy = policies;
333 aramv 1233 EES_RC retval = EES_SUCCESS;
334 aramv 1224 while(temp_policy){
335 aramv 1235 temp_policy->rules = remove_unreachable_rules(temp_policy->rules, &retval);
336 aramv 1224 temp_policy = temp_policy->next;
337     }
338 aramv 1233 return retval;
339 aramv 1224 }
340    
341 aramv 1235 /* This function iterates the passed list of rules and removes those rules that, while they exist on the left-hand side, are never referenced on the right-hand side of a rule in the list */
342     rule_t* remove_unreachable_rules(rule_t* rules, EES_RC *retval){
343 aramv 1224 rule_t *temp_rule = NULL, *next_rule = NULL, *previous_rule = rules;
344     if(rules){
345     temp_rule = rules->next;
346     while(temp_rule){
347     next_rule = temp_rule->next;
348    
349     if(!(get_right_hand_rule(rules, temp_rule->state))){
350     eef_log(LOG_WARNING, "Removing unreachable rule %s at line %i\n", temp_rule->state, temp_rule->lineno);
351     clean_rules_tree(temp_rule);
352     previous_rule->next = next_rule;
353     temp_rule = previous_rule;
354 aramv 1235 *retval = EES_FAILURE;
355 aramv 1224 }
356     previous_rule = temp_rule;
357     temp_rule = next_rule;
358     }
359     }
360     return rules;
361     }
362    
363     void link_dead_end_rules_in_policies(policy_t* policy){
364 aramv 1208 policy_t* temp_policy = policy;
365     while(temp_policy){
366     link_dead_end_rules(temp_policy, temp_policy->rules);
367     temp_policy = temp_policy->next;
368     }
369     }
370    
371     void link_dead_end_rules(policy_t* policy, rule_t* rule){
372     rule_t *temp_rule = rule, *true_rule, *false_rule;
373     while(temp_rule){
374     if(temp_rule->true_branch){
375 aramv 1224 if((true_rule = get_left_hand_rule(policy->rules, temp_rule->true_branch->state))){
376 aramv 1208 eef_log(LOG_DEBUG, "Overwriting rule %s with %s\n", temp_rule->true_branch->state, true_rule->state);
377 aramv 1219 clean_rules_tree(temp_rule->true_branch);
378 aramv 1208 temp_rule->true_branch = true_rule;
379     }
380     }
381     if(temp_rule->false_branch){
382 aramv 1224 if((false_rule = get_left_hand_rule(policy->rules, temp_rule->false_branch->state))){
383 aramv 1208 eef_log(LOG_DEBUG, "Overwriting rule %s with %s\n", temp_rule->false_branch->state, false_rule->state);
384 aramv 1219 clean_rules_tree(temp_rule->false_branch);
385 aramv 1208 temp_rule->false_branch = false_rule;
386     }
387     }
388     temp_rule = temp_rule->next;
389     }
390 aramv 1219 policy->rules_list_transformed_to_tree = 1;
391 aramv 1208 }
392    
393     /*! Tries to find specified state in the rules_list */
394 aramv 1224 rule_t* get_left_hand_rule(rule_t* temp_rule, const char* name){
395 aramv 1202 if(!temp_rule || !name){
396     return NULL;
397     }
398    
399     /* iterate while the rule isn't associated with the given state */
400     while(temp_rule){
401     if(!strcmp(name, temp_rule->state)){
402     return temp_rule;
403     }
404     temp_rule = temp_rule->next;
405     }
406     return NULL;
407     }
408    
409 aramv 1224 /*! Tries to find specified state in the rules_list */
410     rule_t* get_right_hand_rule(rule_t* temp_rule, const char* name){
411     if(!temp_rule || !name){
412     return NULL;
413     } else {
414     /* iterate while the rule isn't associated with the given state */
415     if(temp_rule->true_branch){
416     if(strcmp(name, temp_rule->true_branch->state) == 0){
417     return temp_rule->true_branch;
418     }
419     }
420     if(temp_rule->false_branch){
421     if(strcmp(name, temp_rule->false_branch->state) == 0){
422     return temp_rule->false_branch;
423     }
424     }
425     }
426     return NULL;
427     }
428    
429 aramv 1127 /*! Adds a new policy_t structure to the policies_list which will hold the current rules_list. rules_list is nulled after creating a policy so a new list can be created for the next policy */
430     void add_policy(record_t* policy, rule_t* top_rule){
431 aramv 1123 policy_t* new_policy = NULL;
432     /*eef_log(LOG_DEBUG, "Found a new policy: %s\n", policy->string);*/
433 aramv 1077
434 aramv 1127 if((new_policy = calloc(1, sizeof(policy_t)))){
435 aramv 1123 new_policy->name = strdup(policy->string);
436     new_policy->lineno = policy->lineno;
437 aramv 1127 new_policy->rules = top_rule;
438 aramv 1219 new_policy->rules_list_transformed_to_tree = 0;
439 aramv 1211 new_policy->next = NULL;
440 aramv 1123 }
441    
442     /* append to the end of the list */
443     if(policies_list){
444     policies_list_last->next = new_policy;
445     } else {
446     policies_list = new_policy;
447     }
448     policies_list_last = new_policy;
449    
450 aramv 1212 /* start a new rules list */
451 aramv 1123 rules_list = NULL;
452    
453 aramv 1077 free(policy->string);
454 aramv 1211 policy->string = NULL;
455 aramv 1077 free(policy);
456 aramv 1211 policy = NULL;
457 aramv 1123 }
458 aramv 1077
459 aramv 1201 /* prints the list of policies */
460 aramv 1156 void print_policies(policy_t* policies){
461     policy_t* temp_policy = policies;
462 aramv 1123 while(temp_policy){
463     eef_log(LOG_DEBUG, "Policy: %s\n", temp_policy->name);
464 aramv 1208 print_rules(temp_policy, temp_policy->rules);
465 aramv 1123 temp_policy = temp_policy->next;
466     }
467 aramv 1158 return;
468 aramv 1077 }
469    
470 aramv 1201
471     /* prints the list of rules */
472 aramv 1208 void print_rules(policy_t* policy, rule_t* rule){
473     if(rule){
474     eef_log(LOG_DEBUG, " | Rule %s\n", rule->state);
475 aramv 1201 eef_log(LOG_DEBUG, " -------------------------\n");
476 aramv 1208 if(rule->true_branch){
477 aramv 1224 print_rules(policy, get_left_hand_rule(policy->rules, rule->true_branch->state));
478 aramv 1208 }
479     if(rule->false_branch){
480 aramv 1224 print_rules(policy, get_left_hand_rule(policy->rules, rule->false_branch->state));
481 aramv 1208 }
482 aramv 1201 }
483     return;
484     }
485    
486 aramv 1158 /* tries to link all policy rules to a plugin in the plugin manager */
487 aramv 1156 EES_RC link_rules_to_plugins(policy_t* policies){
488     policy_t *temp_policy = policies;
489 aramv 1147
490 aramv 1154 while(temp_policy){
491 aramv 1208 link_rule_to_plugin(temp_policy, temp_policy->rules);
492 aramv 1154 temp_policy = temp_policy->next;
493 aramv 1147 }
494 aramv 1158 return EES_SUCCESS;
495 aramv 1147 }
496    
497 aramv 1202 void link_rule_to_plugin(policy_t *policy, rule_t *rule){
498 aramv 1192 var_t *temp_var = NULL;
499 aramv 1201 char** argv;
500     int argc;
501    
502 aramv 1192 eef_plugindl_t *temp_plugin = NULL;
503     if(rule){
504 aramv 1211 if(!rule->plugin){
505     temp_var = get_variable_by_name(rule->state);
506     if(temp_var){
507     argv = _var_to_argv(temp_var->value, &argc);
508 aramv 1201
509 aramv 1211 temp_plugin = get_plugin(argv[0]);
510     if(temp_plugin){
511     rule->plugin = temp_plugin;
512     } else {
513 aramv 1227 eef_log(LOG_WARNING, "Unknown plugin in variable %s\n", temp_var->value);
514 aramv 1211 }
515     free_args(argc, argv);
516 aramv 1192 }
517 aramv 1211 } else {
518     eef_log(LOG_DEBUG, "Plugin already linked?\n");
519 aramv 1192 }
520 aramv 1202 link_rule_to_plugin(policy, rule->true_branch);
521     link_rule_to_plugin(policy, rule->false_branch);
522 aramv 1192 }
523 aramv 1201 return;
524 aramv 1192 }
525    
526 aramv 1158 /* iterates the policies and removes those that are not explicitly named in the passed array of strings */
527 aramv 1224 policy_t* reduce_policies(policy_t* policies, int number_of_policies, char* names_of_policies[]){
528 aramv 1158 int i, policy_should_be_removed;
529 aramv 1215 policy_t *temp_policy = policies, *next_policy = NULL;
530 aramv 1211
531 aramv 1215 while(temp_policy){
532 aramv 1158 policy_should_be_removed = 1;
533 aramv 1211 eef_log(LOG_DEBUG, "Checking policy: %s\n", (temp_policy)->name);
534 aramv 1158 for(i = 0; i < number_of_policies; i++){
535     if(strcmp(temp_policy->name, names_of_policies[i]) == 0){
536     /* if the policy is in the named list, we can continue to the next plugin */
537 aramv 1208 eef_log(LOG_DEBUG, "Allowed policy: %s\n", names_of_policies[i]);
538 aramv 1158 policy_should_be_removed = 0;
539     break;
540     }
541     }
542    
543 aramv 1215 next_policy = temp_policy->next;
544    
545 aramv 1158 if(policy_should_be_removed){
546 aramv 1208 eef_log(LOG_DEBUG, "Removing not-allowed policy: %s\n", temp_policy->name);
547 aramv 1215 policies = remove_policy_by_name(policies, temp_policy->name);
548 aramv 1158 }
549 aramv 1215 temp_policy = next_policy;
550 aramv 1212 }
551 aramv 1211
552 aramv 1158 return policies;
553     }
554    
555 aramv 1077 /*! concatenates two strings */
556     record_t* concat_strings(record_t* r1, record_t* r2){
557     record_t* new_record;
558 aramv 1123 /*eef_log(LOG_DEBUG, "Concating: %s with %s\n", r1->string, r2->string);*/
559 aramv 1077 if((new_record = malloc(sizeof(record_t)))){
560     if((new_record->string =
561     calloc(1, sizeof(char)*(strlen(r1->string) + strlen(r2->string)+1)))){
562     strncat(new_record->string, r1->string, strlen(r1->string));
563     strncat(new_record->string, r2->string, strlen(r2->string));
564     free(r1->string);
565     free(r1);
566     free(r2->string);
567     free(r2);
568     return new_record;
569     }
570     }
571     return NULL;
572     }
573    
574     /*! concatenates two strings with a space in between */
575     record_t* concat_strings_with_space(record_t *r1, record_t* r2){
576     record_t *r;
577 aramv 1123 /*eef_log(LOG_DEBUG, "Concating: %s with %s with spaces\n", r1->string, r2->string);*/
578 aramv 1077 if((r = malloc(sizeof(record_t)))){
579     r->string = calloc(1,(sizeof(char)*(strlen(r1->string)+strlen(r2->string)+2)));
580     strncat(r->string, r1->string, strlen(r1->string));
581     strncat(r->string, " ", 1);
582     strncat(r->string, r2->string, strlen(r2->string));
583     free(r1->string);
584     free(r1);
585     free(r2->string);
586     free(r2);
587     return r;
588     }
589     return NULL;
590     }
591    
592     /*! logs errors encountered during parsing */
593     int yyerror(char* string){
594     eef_log(LOG_ERR, "Parse error: %s at line %i in config file %s", string, lineno, config_file_s);
595     return 0;
596     }
597    
598     /*! get variable from list */
599     var_t* get_variable_by_name(char* name){
600     for(current_variable = variables_list; current_variable != NULL; current_variable = current_variable->next){
601     if(!strncmp(name, current_variable->name, strlen(current_variable->name))){
602     return current_variable;
603     }
604     }
605     return NULL;
606     }
607    
608 aramv 1070 /*! Removes a policy from the list of policies */
609 aramv 526 void remove_policy(record_t* policy){
610 aramv 1158 policy_t *temp_policy = policies_list, *next_policy = NULL;
611 aramv 810 eef_log(LOG_DEBUG, "Deleted policy: %s\n", policy->string);
612 aramv 1158
613     while(temp_policy){
614     if(strcmp(temp_policy->name, policy->string) == 0){
615     /* target policy was found */
616     next_policy = temp_policy->next;
617    
618     /* Clean policy fields */
619 aramv 1219 if(temp_policy->rules_list_transformed_to_tree){
620     temp_policy->rules = clean_rules_tree(temp_policy->rules);
621     } else {
622     temp_policy->rules = clean_rules_list(temp_policy->rules);
623     }
624 aramv 1158 free(temp_policy->name);
625 aramv 1211 temp_policy->name = NULL;
626 aramv 1158 free(temp_policy);
627 aramv 1211 temp_policy = NULL;
628 aramv 1158 }
629    
630     /* Move to next policy */
631     temp_policy = next_policy;
632     }
633    
634 aramv 526 free(policy->string);
635     free(policy);
636 aramv 1158 return;
637 aramv 526 }
638    
639 aramv 1158 /*! Removes a policy from the list of policies */
640 aramv 1212 policy_t* remove_policy_by_name(policy_t* policies, char* policy){
641 aramv 1215 policy_t *temp_policy = NULL, *next_policy = NULL, *previous_policy = NULL;
642 aramv 1158
643 aramv 1215 for(temp_policy = policies; temp_policy != NULL; ){
644 aramv 1211 next_policy = temp_policy->next;
645    
646 aramv 1158 if(strcmp(temp_policy->name, policy) == 0){
647     /* target policy was found */
648 aramv 1212
649 aramv 1158 /* Clean policy fields */
650 aramv 1219 if(temp_policy->rules_list_transformed_to_tree){
651 aramv 1220 clean_rules_tree(temp_policy->rules);
652 aramv 1219 } else {
653 aramv 1220 clean_rules_list(temp_policy->rules);
654 aramv 1219 }
655 aramv 1220
656 aramv 1212 eef_log(LOG_DEBUG, "Deleted policy: %s\n", policy);
657 aramv 1158 free(temp_policy->name);
658     free(temp_policy);
659 aramv 1224
660     /* if the head node is deleted, overwrite it with the next node */
661     if(previous_policy){
662     previous_policy->next = next_policy;
663     } else {
664     policies = next_policy;
665     }
666 aramv 1222 break;
667 aramv 1158 }
668    
669 aramv 1215 previous_policy = temp_policy;
670    
671 aramv 1158 /* Move to next policy */
672     temp_policy = next_policy;
673     }
674 aramv 1212
675     return policies;
676 aramv 1158 }
677    
678 aramv 1070 /*! converts a string to an array of strings by splitting it at each \t delimiter
679     - overwrites the second argument with a pointer to the number of elements in the array */
680 aramv 586 char** _var_to_argv(char* value, int *argc){
681     char *start_of_arg = NULL, *copy_of_value = NULL, **argv = NULL;
682     char *delimiters = " \t";
683 aramv 592 size_t size_of_arg = 0, size_of_array, i = 0;
684 aramv 586 char *str_ptr;
685     copy_of_value = strdup(value);
686     size_of_array = (sizeof(char)*(strlen(copy_of_value)+1));
687     if((argv = calloc(1, size_of_array)) != NULL){
688     start_of_arg = strtok_r(copy_of_value, delimiters, &str_ptr);
689     while(start_of_arg != NULL){
690     size_of_arg = (sizeof(char)*(strlen(start_of_arg)+1));
691     if((argv[i] = calloc(1, size_of_arg))){
692     memcpy(argv[i], start_of_arg, size_of_arg);
693     start_of_arg = strtok_r(NULL, delimiters, &str_ptr);
694     i++;
695     }
696     }
697     }
698     free(copy_of_value);
699 aramv 1211 copy_of_value = NULL;
700 aramv 805 if(i < ARG_MAX){
701     *argc = i;
702     } else {
703     *argc = ARG_MAX;
704     }
705 aramv 586 return argv;
706 aramv 572 }
707    
708 aramv 1127 /*! returns pdl path found in parsed config file */
709 aramv 1077 const char* get_pdl_path(){
710     return _pdl_path;
711     }
712 aramv 890
713 aramv 1156 /*! Iterates list of policies and the rules they contain and tries to let the plugin manager prepare plugin structs*/
714 aramv 1235 EES_RC add_plugin_structs(){
715 aramv 1131 char** argv;
716     int argc;
717 aramv 1235 EES_RC plugin_struct_added_ok = EES_SUCCESS;
718 aramv 1131 var_t *temp_var = variables_list;
719    
720 aramv 1235 while((temp_var != NULL) && (plugin_struct_added_ok == EES_SUCCESS)){
721 aramv 1131 argv = _var_to_argv(temp_var->value, &argc);
722    
723 aramv 1156 /* this is a callout to the plug-in manager, which adds a struct describing a single plug-in to its list */
724 aramv 1235 plugin_struct_added_ok = add_plugin_struct(argc, argv);
725 aramv 1131
726     /* Move to next variable */
727     temp_var = temp_var->next;
728     }
729    
730 aramv 1235 return plugin_struct_added_ok;
731 aramv 890 }
732    
733 aramv 1127 /*! Iterates the list of var_t structures and tries to free them */
734 aramv 1077 EES_RC clean_variables_list(){
735     current_variable = variables_list;
736     while(current_variable){
737     free(current_variable->name);
738 aramv 1211 current_variable->name = NULL;
739 aramv 1077 free(current_variable->value);
740 aramv 1211 current_variable->value = NULL;
741 aramv 1085
742 aramv 1127 /* Move to next variable */
743 aramv 1085 variables_list_last = current_variable;
744 aramv 1077 current_variable = current_variable->next;
745 aramv 1085
746 aramv 1127 /* Clean last variable struct */
747 aramv 1085 free(variables_list_last);
748 aramv 1211 variables_list_last = NULL;
749 aramv 890 }
750     return EES_SUCCESS;
751     }
752    
753 aramv 1219 /*! Iterates the tree of rule_t structures starting with the passed rule and tries to free them and their true/false branches */
754     rule_t* clean_rules_tree(rule_t* top_rule){
755 aramv 1127 rule_t* temp_rule = top_rule;
756 aramv 1202 if(temp_rule){
757 aramv 1219 clean_rules_tree(temp_rule->true_branch);
758 aramv 1202
759 aramv 1219 clean_rules_tree(temp_rule->false_branch);
760 aramv 1085
761 aramv 1215 free(temp_rule->state);
762 aramv 1202 free(temp_rule);
763 aramv 1211 temp_rule = NULL;
764 aramv 1085 }
765 aramv 1219 return NULL;
766 aramv 1085 }
767    
768 aramv 1219 /*! Iterates the list of rule_t structures starting with the passed rule and tries to free them and their true/false branches */
769     rule_t* clean_rules_list(rule_t* top_rule){
770     rule_t *temp_rule = top_rule, *next_rule = NULL;
771     while(temp_rule){
772     next_rule = temp_rule->next;
773 aramv 1222 clean_rules_tree(temp_rule);
774 aramv 1219 temp_rule = next_rule;
775     }
776     return NULL;
777     }
778    
779 aramv 1147 void free_args(int argc, char** argv){
780     for(; argc > 0; argc--){
781     free(argv[argc-1]);
782 aramv 1211 argv[argc-1] = NULL;
783 aramv 1147 }
784     free(argv);
785 aramv 1211 argv = NULL;
786 aramv 1147 }
787    
788 aramv 1127 /*! Iterates the list of policy_t structures and tries to free them and their rules */
789 aramv 1212 EES_RC clean_policies_list(policy_t* policies){
790     policy_t *temp_policy = policies, *last_policy = NULL;
791 aramv 1127 while(temp_policy){
792     /* Clean policy fields */
793 aramv 1219 if(temp_policy->rules_list_transformed_to_tree){
794     clean_rules_tree(temp_policy->rules);
795     } else {
796     clean_rules_list(temp_policy->rules);
797     }
798 aramv 1127 free(temp_policy->name);
799 aramv 1211 temp_policy->name = NULL;
800 aramv 1127
801     /* Move to next policy */
802     last_policy = temp_policy;
803     temp_policy = temp_policy->next;
804     free(last_policy);
805 aramv 1211 last_policy = NULL;
806 aramv 1127 }
807     return EES_SUCCESS;
808     }
809    
810 aramv 1070 /*! Terminates the parser and tries to free all used memory */
811 aramv 1257 EES_RC pdl_term(){
812 aramv 1077 clean_variables_list();
813 aramv 1259 clean_policies_list(policies_list);
814 aramv 592 free(_pdl_path);
815 aramv 1211 _pdl_path = NULL;
816 aramv 1077
817     if(config_file_fp != NULL){
818 aramv 1069 /* This is the preferred way of cleaning up various flex versions - See: http://flex.sourceforge.net/manual/Memory-leak-_002d-16386-bytes-allocated-by-malloc_002e.html#Memory-leak-_002d-16386-bytes-allocated-by-malloc_002e */
819 aramv 1127 #if HAVE_YYLEX_DESTROY /* macro set by configure script */
820 aramv 586 yylex_destroy();
821 aramv 1069 #else
822 aramv 1127 /*eef_log(LOG_WARNING, "Lex function yylex_destroy() not available - possibly unable to free allocated memory for evaluation manager\n");*/
823 aramv 1069 #if HAVE_FLEX
824 aramv 1127 delete_lex_buffer(); /* this function is defined in pdl_lex.l */
825     /*eef_log(LOG_INFO, "Managed to free allocated memory for evaluation manager\n"); */
826     #else
827     eef_log(LOG_WARNING, "Lex functions yylex_destroy() and yy_delete_buffer() are both not available - unable to free allocated memory for evaluation manager\n");
828 aramv 1069 #endif
829 aramv 586 #endif
830 aramv 1127
831 aramv 1077 if((fclose(config_file_fp)==0) ){
832 aramv 781 return EES_SUCCESS;
833 aramv 586 }
834 aramv 526 }
835 aramv 781 return EES_FAILURE;
836 aramv 526 }
837    
838 aramv 1070 /*! TODO */
839 aramv 781 EES_RC allow_rules(int val){
840 aramv 1208 /*eef_log(LOG_DEBUG, "Allowed rule: %i\n", val);*/
841 aramv 781 return EES_SUCCESS;
842 aramv 526 }
843    
844 aramv 1070 /*! TODO */
845 aramv 781 EES_RC allowed_policy_rule(const char* label){
846 aramv 1208 /*eef_log(LOG_DEBUG, "Allowed policy rule: %s\n", label);*/
847 aramv 781 return EES_SUCCESS;
848 aramv 526 }

grid.support@nikhef.nl
ViewVC Help
Powered by ViewVC 1.1.28