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

Contents of /trunk/grid-mw-security/ees/src/aos/aos.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1748 - (show annotations) (download) (as text)
Wed Jun 9 13:46:31 2010 UTC (11 years, 7 months ago) by aramv
File MIME type: text/x-chdr
File size: 14170 byte(s)
Working on AOS cleanup functions
1 #include "plugin_manager.h"
2 #include "_aos.h"
3 #include "eef_aos.h"
4
5 static pthread_key_t _aos_key;
6 static pthread_once_t _aos_key_once = PTHREAD_ONCE_INIT; /* Normally not okay to do initialisation outside of a function, but this way it (hopefully) will only be set one - during compile time */
7 static struct aos_state_s * _global_state;
8
9 /* internal methods */
10
11 /**
12 * returns _is_initialized
13 */
14 int aos_is_initialized(){
15 return _is_initialized;
16 }
17
18 /**
19 * sets threading flag
20 */
21 void aos_start_threading(){
22 _is_threading = 1;
23 }
24
25 /**
26 * returns a pointer to an aos_storage_t struct that corresponds to the current thread context. If the current context is not threaded, a pointer to a global storage struct is returned.
27 */
28 aos_state_t * aos_get_state(void){
29 pid_t tid;
30 aos_state_t * state = NULL;
31
32 tid = syscall(SYS_gettid);
33 /*tid = gettid();*/
34
35 if(!_is_threading){
36 return _global_state;
37 }
38
39 /* Try to get TLS */
40 state = pthread_getspecific(_aos_key);
41 if(state == 0) {
42 /* Create new TLS */
43 if((state = calloc(1, sizeof(aos_state_t)))){
44 state->last_context = NULL;
45 if((state->current_storage = calloc(1, sizeof(aos_storage_t)))){
46 state->current_storage->list_contexts = NULL;
47 _is_initialized = 1;
48 pthread_setspecific(_aos_key, state);
49 state->saved_storage = state->current_storage;
50 return state;
51 }
52 }
53 } else {
54 return state;
55 }
56 return NULL;
57 }
58
59 aos_storage_t* aos_get_storage(){
60 aos_state_t* iterator = aos_get_state();
61 return iterator->current_storage;
62 }
63
64 EES_RC aos_free_state(aos_state_t* state){
65 printf("Freeing state at %p\n", state);
66 if(state == _global_state){
67 printf("Trying to free global state!\n");
68 }
69 aos_free_storage(state->saved_storage);
70 state->saved_storage = NULL;
71 state->last_context = NULL;
72 }
73
74 /**
75 * Frees storage struct pointed to by storage pointer
76 */
77 EES_RC aos_free_storage(aos_storage_t* storage){
78 aos_context_t *context = NULL, *next_context = NULL;
79 aos_attribute_t *attribute = NULL, *next_attribute = NULL;
80 int attribute_count = 0;
81
82 if(!storage){
83 return EES_FAILURE;
84 }
85
86 EEF_log(LOG_DEBUG, "Cleaning aos storage at %p\n", storage);
87
88 context = storage->list_contexts;
89
90 while(context){
91 next_context = context->next;
92 attribute = context->list_attributes;
93 while(attribute){
94 next_attribute = attribute->next;
95 /*free(attribute->id);*/
96 free(attribute->issuer);
97 /*free(attribute->type);*/
98 if(attribute->needs_free){
99 EEF_log(LOG_DEBUG, "Freeing arg data %i at %p\n",attribute_count, attribute->data);
100 free(attribute->data);
101 }
102 free(attribute);
103 attribute = next_attribute;
104 attribute_count++;
105 }
106 /* free here */
107 EEF_log(LOG_DEBUG, "Freeing context at %p\n", context);
108 context->next = NULL;
109 context->list_attributes = NULL;
110 free(context);
111 context = next_context;
112 }
113 storage->list_contexts = NULL;
114 free(storage);
115 storage = NULL;
116 return EES_SUCCESS;
117 }
118
119 /* base functions */
120
121 /**
122 * Returns a pointer to a freshly allocated aos_context_t struct
123 */
124 aos_context_t * createContext(aos_context_class_t context_class){
125 aos_context_t * context;
126 if((context = calloc(1, sizeof(aos_context_t)))){
127 context->context_class = context_class;
128 context->list_attributes = NULL;
129 context->last_attribute = NULL;
130 context->next = NULL;
131 }
132 /*printf("Context of type %i created at %p\n", context_class, context);*/
133 return context;
134 }
135
136 /**
137 * Adds supplied context to storage attained through aos_get_storage()
138 */
139 EES_RC addContext(aos_context_t* context){
140 aos_state_t* iterator = aos_get_state();
141 aos_storage_t* storage = iterator->saved_storage;
142 aos_context_t* tmp_context = NULL;
143
144 EEF_log(LOG_DEBUG, "Adding context at %p to storage at %p\n", context, iterator->current_storage);
145 if(!storage){
146 EEF_log(LOG_ERR, "No storage available at %p", storage);
147 return EES_FAILURE;
148 }
149 if(storage->list_contexts != NULL){
150 if((tmp_context = storage->list_contexts)!=NULL){
151 while(tmp_context->next){
152 if(tmp_context == context){
153 EEF_log(LOG_ERR, "The context you're trying to add was already added!\n");
154 return EES_FAILURE;
155 }
156 tmp_context = tmp_context->next;
157 }
158 }
159 tmp_context->next = context;
160 EEF_log(LOG_DEBUG, "Inserted at %p\n", tmp_context);
161 /*printf("Inserted at %p\n", tmp_context);*/
162 } else {
163 storage->list_contexts = context;
164 EEF_log(LOG_DEBUG, "Created at %p\n", context);
165 /*printf("List created at %p\n", context);*/
166 }
167 aos_set_iterator(context);
168
169 /*eef_log(LOG_DEBUG, "Copied context to %p\n", storage->last_context);*/
170 return EES_SUCCESS;
171 }
172
173 EES_RC rewindContexts(aos_storage_t* storage){
174 aos_state_t* state = aos_get_state();
175 /* not using storage parameter anymore */
176
177 if(state){
178 state->current_storage = state->saved_storage;
179
180 if(state->current_storage){
181 aos_set_iterator(state->current_storage->list_contexts);
182 return EES_SUCCESS;
183 } else {
184 EEF_log(LOG_ERR, "Unable to aquire AOS handle in rewindContexts()\n");
185 }
186 }
187 return EES_FAILURE;
188 }
189
190 EES_RC aos_set_iterator(aos_context_t* context){
191 aos_state_t* state = aos_get_state();
192 if(state->current_storage){
193 /*printf("Setting iterator for %p to %p\n", state->current_storage, context);*/
194 state->last_context = context;
195 return EES_SUCCESS;
196 } else {
197 EEF_log(LOG_ERR, "Invalid storage passed to aos_set_iterator(): %p\n", state->current_storage);
198 }
199 return EES_FAILURE;
200 }
201
202 aos_context_t* aos_get_iterator(void){
203 aos_state_t* state = aos_get_state();
204 if(state->current_storage){
205 /*printf("Getting iterator for %p as %p\n", state->current_storage, state->last_context);*/
206 if(state->last_context){
207 return state->last_context;
208 }
209 } else {
210 EEF_log(LOG_ERR, "Invalid storage passed to aos_set_iterator(): %p\n", state->current_storage);
211 }
212 return NULL;
213 }
214
215 /**
216 * returns the next aos_context_t pointer with the supplied context_class from the list of contexts in the supplied storage.
217 * will fall through and try to use global storage in case nothing was found
218 */
219 aos_context_t * getNextContext(aos_context_class_t context_class, aos_storage_t* storage){
220 aos_state_t* state = aos_get_state();
221 aos_context_t* current_context = aos_get_iterator();
222
223 /* find context type */
224 if(context_class != ANY){
225 while(current_context != NULL){
226 if((current_context->context_class == context_class)){
227 /* Found context */
228 break;
229 }
230 current_context = current_context->next;
231 }
232 }
233
234 /* save state */
235 if((current_context == NULL) && (storage != _global_state->current_storage) && (state->current_storage != _global_state->current_storage)){
236 /* Retry with global storage */
237 state->current_storage = _global_state->current_storage;
238 aos_set_iterator(_global_state->current_storage->list_contexts);
239 current_context = getNextContext(context_class, _global_state->current_storage);
240 }
241
242 /* save iterator */
243 if(current_context){
244 aos_set_iterator(current_context->next);
245 } else {
246 aos_set_iterator(NULL);
247 }
248
249 return current_context;
250 }
251
252 /**
253 * Sets the obligation name in the struct pointed to by the supplied pointer context to supplied obligation
254 */
255 void setContextObligationId(aos_context_t* context, char * obligation){
256 if(context->context_class == OBLIGATION){
257 context->obligation_name = obligation;
258 }
259 }
260
261 /**
262 * Returns the obligation name from the supplied context
263 */
264 char* getContextObligationId(aos_context_t* context){
265 return context->obligation_name;
266 }
267
268 /**
269 * Returns a pointer to a freshly allocated aos_attribute_t struct
270 */
271 aos_attribute_t* createAttribute(void){
272 aos_attribute_t* attribute = NULL;
273 if((attribute = calloc(1, sizeof(aos_attribute_t)))){
274 attribute->next = NULL;
275 attribute->setting_plugin = get_running_plugin();
276 }
277 return attribute;
278 }
279
280 /**
281 * Adds supplied attribute to supplied context
282 */
283 EES_RC addAttribute(aos_context_t * context, aos_attribute_t* attribute){
284 if(context->last_attribute){
285 context->last_attribute->next = attribute;
286 } else {
287 context->list_attributes = attribute;
288 context->last_attribute = NULL;
289 }
290 context->last_attribute = attribute;
291 return EES_SUCCESS;
292 }
293
294 EES_RC rewindAttributes(aos_context_t* context){
295 context->last_attribute = NULL;
296 return EES_SUCCESS;
297 }
298
299 /**
300 * returns the next aos_attribute_t pointer from list of attributes in the supplied context
301 */
302 aos_attribute_t* getNextAttribute(aos_context_t* context){
303 aos_attribute_t* attribute = NULL;
304 if(context->last_attribute){
305 attribute = context->last_attribute->next;
306 } else {
307 attribute = context->list_attributes;
308 }
309 context->last_attribute = attribute;
310 return attribute;
311 }
312
313 /**
314 * removes a supplied attribute from the supplied context
315 */
316 EES_RC destroyAttribute(aos_context_t* context, aos_attribute_t* attribute){
317 aos_attribute_t *last_attribute = NULL, *current_attribute = NULL;
318 for(current_attribute = context->list_attributes; current_attribute != NULL; last_attribute = current_attribute, current_attribute = current_attribute->next){
319 if(current_attribute == attribute){
320 if(current_attribute->setting_plugin != get_running_plugin()){
321 EEF_log(LOG_ERR, "Argument %s is not owned by running plugin %s", current_attribute->id, get_running_plugin()->name);
322 return EES_FAILURE;
323 }
324 free(attribute->data);
325 free(attribute);
326 attribute = NULL;
327 if(last_attribute == NULL){
328 context->list_attributes = current_attribute->next;
329 } else {
330 last_attribute->next = current_attribute->next;
331 }
332 break;
333 }
334 }
335
336 if(current_attribute){
337 free(current_attribute->data);
338 free(current_attribute);
339 current_attribute = NULL;
340 return EES_SUCCESS;
341 }
342 return EES_FAILURE;
343 }
344
345 /**
346 * sets attribute id in supplied attribute
347 */
348 EES_RC setAttributeId(aos_attribute_t* attribute, char* id){
349 attribute->id = id;
350 return EES_SUCCESS;
351 }
352
353 /**
354 * sets attribute issuer in supplied attribute
355 */
356 EES_RC setAttributeIssuer(aos_attribute_t* attribute, char* issuer){
357 attribute->issuer = issuer;
358 return EES_SUCCESS;
359 }
360
361 /**
362 * sets attribute value in supplied attribute
363 */
364 EES_RC setAttributeValue(aos_attribute_t* attribute, const void* value, size_t size){
365 if(value != NULL){
366 if(size == 0) {
367 attribute->data = value;
368 attribute->needs_free = 0;
369 } else {
370 attribute->data = calloc(1, size+1);
371 memcpy(attribute->data, value, size);
372 attribute->needs_free = 1;
373 }
374 } else {
375 return EES_FAILURE;
376 }
377 return EES_SUCCESS;
378 }
379
380 /**
381 * sets attribute type in supplied attribute
382 */
383 EES_RC setAttributeType(aos_attribute_t * attribute, char* type){
384 attribute->type = type;
385 return EES_SUCCESS;
386 }
387
388 /**
389 * returns id from supplied attribute
390 */
391 char* getAttributeId(aos_attribute_t* attribute){
392 return attribute->id;
393 }
394
395 /**
396 * returns issuer from supplied attribute
397 */
398 char* getAttributeIssuer(aos_attribute_t* attribute){
399 return attribute->issuer;
400 }
401
402 /**
403 * returns data from supplied attribute casted to a char*
404 */
405 char* getAttributeValueAsString(aos_attribute_t* attribute){
406 return (char*) attribute->data;
407 }
408
409 /**
410 * returns data from supplied attribute casted to a int
411 */
412 int getAttributeValueAsInt(aos_attribute_t* attribute){
413 char* string = getAttributeValueAsString(attribute);
414 return strtol(string, NULL, 10);
415 }
416
417 /* AOS control functions */
418
419 /**
420 * Initializes the AOS and creates thread-local storage key
421 */
422 EES_RC AOS_Init (void){
423 _is_threading = 0;
424 pthread_once(&_aos_key_once, aos_make_key);
425
426 if((_global_state = calloc(1, sizeof(aos_state_t)))){
427 _global_state->last_context = NULL;
428 if((_global_state->current_storage = calloc(1, sizeof(aos_storage_t)))){
429 _global_state->current_storage->list_contexts = NULL;
430 _is_initialized = 1;
431 _global_state->saved_storage = _global_state->current_storage;
432 return EES_SUCCESS;
433 }
434 }
435
436 return EES_FAILURE;
437 }
438
439 /**
440 * Creates thread-local storage key
441 */
442 void aos_make_key(void){
443 pthread_key_create(&_aos_key, aos_free_key);
444 }
445
446 /**
447 * Frees thread-local storage key
448 */
449 void aos_free_key(void* state){
450 pid_t tid;
451 aos_storage_t* storage;
452 aos_state_t* tmp_state = (aos_state_t*) state;
453 /*tid = gettid();*/
454 tid = syscall(SYS_gettid);
455 EEF_log(LOG_DEBUG, "Killing thread %i\n", tid);
456 aos_free_state(tmp_state);
457 }
458
459 /**
460 * Frees thread-local storage for this thread
461 */
462 EES_RC AOS_Clean(void){
463 pid_t tid;
464 /*tid = gettid();*/
465 tid = syscall(SYS_gettid);
466 EEF_log(LOG_DEBUG, "Killing thread %i\n", tid);
467 if(!_is_threading){
468 return EES_FAILURE;
469 }
470 aos_free_state(aos_get_state());
471 return EES_SUCCESS;
472 }
473
474 /**
475 * Terminates AOS, deleting the thread-local storage key
476 */
477 EES_RC AOS_Term (void){
478 _is_threading = 0;
479 /*aos_free_storage(_global_storage);*/
480 aos_free_state(_global_state);
481 pthread_setspecific(_aos_key, NULL);
482 pthread_key_delete(_aos_key);
483 _is_initialized = 0;
484 return EES_SUCCESS;
485 }
486
487 /**
488 * Dumps out all the data present in the AOS, as seen from the current thread's perspective
489 */
490 EES_RC aos_dump_argslist (void) {
491 char *log_str = "aos_dump";
492 aos_context_t *context = NULL;
493 aos_attribute_t *attribute = NULL;
494 char *attribute_name = NULL;
495 char *attribute_value = NULL;
496
497 EEF_log(LOG_DEBUG, "Dumping aos");
498
499 rewindContexts(NULL);
500
501 while((context = getNextContext(ANY, NULL)) != NULL){
502 EEF_log(LOG_DEBUG, "Context %p class: %i\n", context, context->context_class);
503 rewindAttributes(context);
504 while((attribute = getNextAttribute(context)) != NULL){
505 attribute_name = getAttributeId(attribute);
506 attribute_value = getAttributeValueAsString(attribute);
507 if(attribute_name && attribute_value){
508 EEF_log(LOG_DEBUG, "\t%s=%s\n", attribute_name, attribute_value);
509 }
510 }
511 }
512
513 return EES_SUCCESS;
514 }
515

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