1 /*
2 * Portions of this file Copyright 1999-2005 University of Chicago
3 * Portions of this file Copyright 1999-2005 The University of Southern California.
4 *
5 * This file or a portion of this file is licensed under the
6 * terms of the Globus Toolkit Public License, found at
7 * http://www.globus.org/toolkit/download/license.html.
8 * If you redistribute this file, with or without
9 * modifications, you must include this notice in the file.
10 */
11
12 #include "globus_common.h"
13 #include "globus_i_handler_chain.h"
14 #include "globus_extension.h"
15 #include "globus_soap_message.h"
16
17 globus_extension_registry_t globus_handler_registry =
18 {
19 NULL,
20 GLOBUS_FALSE,
21 GLOBUS_FALSE
22 };
23
24 0 GlobusDebugDefine(GLOBUS_HANDLER);
25
26 static globus_list_t * globus_l_handler_extensions = NULL;
27 static globus_mutex_t globus_l_handler_extensions_mutex;
28
29 enum globus_l_handler_debug_levels
30 {
31 GLOBUS_L_HANDLER_DEBUG_TRACE = 1,
32 GLOBUS_L_HANDLER_DEBUG_ERROR = 2
33 };
34
35 #define GlobusHandlerDebugPrintf(level, message) \
36 GlobusDebugPrintf(GLOBUS_HANDLER, level, message)
37
38 #define GlobusHandlerDebugEnter() \
39 GlobusHandlerDebugPrintf( \
40 GLOBUS_L_HANDLER_DEBUG_TRACE, \
41 ("[%s] Entering\n", _globus_func_name))
42
43 #define GlobusHandlerDebugExit() \
44 GlobusHandlerDebugPrintf( \
45 GLOBUS_L_HANDLER_DEBUG_TRACE, \
46 ("[%s] Exiting\n", _globus_func_name))
47
48 #define GlobusHandlerErrorHeaderElementNotFound() \
49 globus_error_put( \
50 globus_error_construct_error( \
51 GLOBUS_HANDLER_MODULE, \
52 NULL, \
53 GLOBUS_HANDLER_ERROR_HEADER_ELEMENT_NOT_FOUND, \
54 __FILE__, \
55 _globus_func_name, \
56 __LINE__, \
57 "No Header element found"))
58
59 #define GlobusHandlerErrorRegistryLookupFailed(CAUSE, ENDPOINT) \
60 globus_error_put( \
61 globus_error_construct_error( \
62 GLOBUS_HANDLER_MODULE, \
63 (CAUSE ? globus_error_get(CAUSE) : NULL), \
64 GLOBUS_HANDLER_ERROR_REGISTRY_LOOKUP_FAILED, \
65 __FILE__, \
66 _globus_func_name, \
67 __LINE__, \
68 "No handler found at endpoint: %s", ENDPOINT))
69
70 #define GlobusHandlerErrorDefaultTriggerAlreadyDefined() \
71 globus_error_put( \
72 globus_error_construct_error( \
73 GLOBUS_HANDLER_MODULE, \
74 NULL, \
75 GLOBUS_HANDLER_ERROR_DEFAULT_TRIGGER_ALREADY_DEFINED, \
76 __FILE__, \
77 _globus_func_name, \
78 __LINE__, \
79 "A default trigger handler has already been defined"))
80
81 #define GlobusHandlerErrorNoTriggersDefined() \
82 globus_error_put( \
83 globus_error_construct_error( \
84 GLOBUS_HANDLER_MODULE, \
85 NULL, \
86 GLOBUS_HANDLER_ERROR_NO_TRIGGERS_DEFINED, \
87 __FILE__, \
88 _globus_func_name, \
89 __LINE__, \
90 "No triggers defined"))
91
92 static int
93 globus_l_handler_activate(void);
94
95 static int
96 globus_l_handler_deactivate(void);
97
98 #include "version.h"
99
100 globus_module_descriptor_t globus_i_handler_module =
101 {
102 "globus_handler",
103 globus_l_handler_activate,
104 globus_l_handler_deactivate,
105 GLOBUS_NULL,
106 GLOBUS_NULL,
107 &local_version
108 };
109
110 static int
111 globus_l_handler_activate(void)
112 0 {
113 int rc;
114
115 0 rc = globus_module_activate(GLOBUS_COMMON_MODULE);
116 0 if(rc != GLOBUS_SUCCESS)
117 {
118 0 return rc;
119 }
120
121 0 GlobusHandlerDebugEnter();
122
123 0 rc = globus_module_activate(GLOBUS_SOAP_MESSAGE_MODULE);
124 0 if(rc != GLOBUS_SUCCESS)
125 {
126 0 globus_module_deactivate(GLOBUS_COMMON_MODULE);
127 0 return rc;
128 }
129
130 0 globus_mutex_init(&globus_l_handler_extensions_mutex, NULL);
131
132 0 GlobusHandlerDebugExit();
133 0 return GLOBUS_SUCCESS;
134 }
135
136 static
137 void
138 globus_l_handler_extension_destroy(
139 void * ep)
140 0 {
141 0 char * symbol = (char *) ep;
142
143 0 globus_extension_deactivate(symbol);
144 0 globus_free(symbol);
145 }
146
147 static int
148 globus_l_handler_deactivate(void)
149 0 {
150 GlobusFuncName(globus_l_handler_deactivate);
151 0 GlobusHandlerDebugEnter();
152
153 0 globus_mutex_lock(&globus_l_handler_extensions_mutex);
154 0 if(globus_l_handler_extensions)
155 {
156 0 globus_list_destroy_all(globus_l_handler_extensions,
157 globus_l_handler_extension_destroy);
158 0 globus_l_handler_extensions = NULL;
159 }
160 0 globus_mutex_unlock(&globus_l_handler_extensions_mutex);
161 0 globus_mutex_destroy(&globus_l_handler_extensions_mutex);
162
163 0 globus_module_deactivate(GLOBUS_SOAP_MESSAGE_MODULE);
164
165 0 GlobusHandlerDebugExit();
166 0 GlobusDebugDestroy(GLOBUS_HANDLER);
167
168 0 globus_module_deactivate(GLOBUS_COMMON_MODULE);
169
170 0 return GLOBUS_SUCCESS;
171 }
172
173 typedef struct globus_l_handler_s
174 {
175 globus_extension_handle_t extension_handle;
176 globus_handler_invoke_func_t invoke;
177 globus_handler_trigger_t * trigger;
178 } globus_l_handler_t;
179
180 globus_result_t
181 globus_handler_chain_init(
182 globus_handler_chain_t * chain)
183 6330 {
184 globus_handler_chain_t new_chain;
185 6330 globus_result_t result = GLOBUS_SUCCESS;
186
187 GlobusFuncName(globus_handler_chain_init);
188 6330 GlobusHandlerDebugEnter();
189
190 6330 new_chain = globus_malloc(sizeof(globus_i_handler_chain_t));
191 6330 if(!new_chain)
192 {
193 0 result = GlobusSoapMessageErrorOutOfMemory;
194 0 GlobusHandlerDebugExit();
195 0 return result;
196 }
197 6330 memset(new_chain, 0, sizeof(globus_i_handler_chain_t));
198
199 6330 *chain = new_chain;
200
201 6330 GlobusHandlerDebugExit();
202 6330 return result;
203 }
204
205 void
206 globus_l_handler_destroy(
207 void * h)
208 22090 {
209 globus_l_handler_t * entry;
210
211 22090 entry = (globus_l_handler_t *) h;
212
213 22090 if(entry)
214 {
215 22090 free(entry);
216 }
217 }
218
219 void
220 globus_handler_chain_destroy(
221 globus_handler_chain_t chain)
222 9395 {
223 globus_extension_handle_t ext;
224 globus_list_t * extensions;
225 GlobusFuncName(globus_handler_chain_init);
226 9395 GlobusHandlerDebugEnter();
227
228 9395 globus_list_destroy_all(chain->request_handlers,
229 globus_l_handler_destroy);
230 9395 globus_list_destroy_all(chain->response_handlers,
231 globus_l_handler_destroy);
232 9395 globus_list_destroy_all(chain->request_init_handlers,
233 globus_l_handler_destroy);
234 9395 globus_list_destroy_all(chain->request_destroy_handlers,
235 globus_l_handler_destroy);
236 9395 globus_list_destroy_all(chain->response_init_handlers,
237 globus_l_handler_destroy);
238 9395 globus_list_destroy_all(chain->response_destroy_handlers,
239 globus_l_handler_destroy);
240 9395 if(chain->triggers)
241 {
242 3160 globus_hashtable_destroy_all(
243 &chain->triggers,
244 globus_l_handler_destroy);
245 }
246
247 9395 extensions = chain->extensions;
248 25110 while(extensions)
249 {
250 6320 ext = globus_list_first(extensions);
251 6320 globus_extension_release(ext);
252 6320 extensions = globus_list_rest(extensions);
253 }
254
255 9395 globus_list_free(chain->extensions);
256
257 9395 globus_free(chain);
258
259 9395 GlobusHandlerDebugExit();
260 }
261
262 static
263 void
264 globus_l_handler_hash_entry_copy(
265 void ** dest_key,
266 void ** dest_datum,
267 void * src_key,
268 void * src_datum)
269 15325 {
270 globus_l_handler_t * dest_handler;
271 globus_l_handler_t * src_handler;
272
273 15325 src_handler = (globus_l_handler_t *)src_datum;
274 15325 dest_handler = globus_malloc(sizeof(globus_l_handler_t));
275 15325 if(!dest_handler)
276 {
277 0 *dest_key = NULL;
278 0 *dest_datum = NULL;
279 }
280
281 15325 memset(dest_handler, 0, sizeof(globus_l_handler_t));
282
283 15325 dest_handler->invoke = src_handler->invoke;
284 15325 dest_handler->trigger = src_handler->trigger;
285
286 15325 *dest_datum = (void *)dest_handler;
287 15325 *dest_key = (void *)dest_handler->trigger->element;
288 }
289
290 static
291 globus_result_t
292 globus_l_handle_chain_copy(
293 globus_list_t ** dest,
294 globus_list_t * src)
295 18390 {
296 18390 globus_result_t result = GLOBUS_SUCCESS;
297 globus_l_handler_t * src_handler;
298 globus_l_handler_t * new_handler;
299 GlobusFuncName(globus_l_handler_chain_copy);
300 18390 GlobusHandlerDebugEnter();
301
302 6130 for(; !globus_list_empty(src); src = globus_list_rest(src))
303 {
304 6130 src_handler = globus_list_first(src);
305
306 6130 new_handler = globus_malloc(sizeof(globus_l_handler_t));
307 6130 if(!new_handler)
308 {
309 0 result = GlobusSoapMessageErrorOutOfMemory;
310 0 GlobusHandlerDebugExit();
311 0 return result;
312 }
313
314 6130 memset(new_handler, 0, sizeof(globus_l_handler_t));
315
316 6130 new_handler->invoke = src_handler->invoke;
317 6130 globus_list_insert(dest, new_handler);
318 6130 dest = globus_list_rest_ref(*dest);
319 }
320
321 18390 GlobusHandlerDebugExit();
322 18390 return result;
323 }
324
325 globus_result_t
326 globus_handler_chain_copy(
327 globus_handler_chain_t * dest,
328 globus_handler_chain_t src)
329 3065 {
330 globus_extension_handle_t ext;
331 globus_list_t * extensions;
332 globus_handler_chain_t new_chain;
333 3065 globus_result_t result = GLOBUS_SUCCESS;
334
335 GlobusFuncName(globus_handler_chain_copy);
336 3065 GlobusHandlerDebugEnter();
337
338 3065 new_chain = globus_malloc(sizeof(globus_i_handler_chain_t));
339 3065 if(!new_chain)
340 {
341 0 result = GlobusSoapMessageErrorOutOfMemory;
342 0 goto exit;
343 }
344
345 3065 memset(new_chain, 0, sizeof(globus_i_handler_chain_t));
346
347 3065 result = globus_l_handle_chain_copy(
348 &new_chain->request_handlers, src->request_handlers);
349 3065 if(result != GLOBUS_SUCCESS)
350 {
351 3065 goto error;
352 }
353
354 3065 result = globus_l_handle_chain_copy(
355 &new_chain->response_handlers, src->response_handlers);
356 3065 if(result != GLOBUS_SUCCESS)
357 {
358 3065 goto destroy_request_handlers;
359 }
360
361 3065 result = globus_l_handle_chain_copy(
362 &new_chain->request_init_handlers, src->request_init_handlers);
363 3065 if(result != GLOBUS_SUCCESS)
364 {
365 3065 goto destroy_response_handlers;
366 }
367
368 3065 result = globus_l_handle_chain_copy(
369 &new_chain->request_destroy_handlers, src->request_destroy_handlers);
370 3065 if(result != GLOBUS_SUCCESS)
371 {
372 3065 goto destroy_request_init_handlers;
373 }
374
375 3065 result = globus_l_handle_chain_copy(
376 &new_chain->response_init_handlers, src->response_init_handlers);
377 3065 if(result != GLOBUS_SUCCESS)
378 {
379 3065 goto destroy_request_destroy_handlers;
380 }
381
382 3065 result = globus_l_handle_chain_copy(
383 &new_chain->response_destroy_handlers, src->response_destroy_handlers);
384 3065 if(result != GLOBUS_SUCCESS)
385 {
386 3065 goto destroy_response_init_handlers;
387 }
388
389 3065 if(src->triggers)
390 {
391 3065 globus_hashtable_copy(
392 &new_chain->triggers,
393 &src->triggers,
394 globus_l_handler_hash_entry_copy);
395 }
396
397 3065 new_chain->default_trigger = src->default_trigger;
398
399 3065 extensions = src->extensions;
400 12260 while(extensions)
401 {
402 6130 ext = globus_list_first(extensions);
403 6130 globus_extension_reference(ext);
404 6130 globus_list_insert(&new_chain->extensions, (void *)ext);
405 6130 extensions = globus_list_rest(extensions);
406 }
407
408 3065 *dest = new_chain;
409
410 3065 GlobusHandlerDebugExit();
411 3065 return result;
412
413 0 destroy_response_init_handlers:
414 0 globus_list_destroy_all(
415 new_chain->response_init_handlers, globus_l_handler_destroy);
416
417 0 destroy_request_destroy_handlers:
418 0 globus_list_destroy_all(
419 new_chain->request_destroy_handlers, globus_l_handler_destroy);
420
421 0 destroy_request_init_handlers:
422 0 globus_list_destroy_all(
423 new_chain->request_init_handlers, globus_l_handler_destroy);
424
425 0 destroy_response_handlers:
426 0 globus_list_destroy_all(
427 new_chain->response_handlers, globus_l_handler_destroy);
428
429 0 destroy_request_handlers:
430 0 globus_list_destroy_all(
431 new_chain->request_handlers, globus_l_handler_destroy);
432
433 0 error:
434 0 globus_free(new_chain);
435
436 0 exit:
437 0 GlobusHandlerDebugExit();
438 0 return result;
439 }
440
441 static
442 int
443 globus_l_handler_chain_list_insert_last(
444 globus_list_t * volatile * headp,
445 void * datum)
446 95 {
447 95 globus_list_t * entry = NULL;
448 globus_list_t * tmp_list;
449
450 95 if(!*headp)
451 {
452 95 globus_list_insert(headp, datum);
453 }
454 else
455 {
456 0 tmp_list = *headp;
457
458 0 while(tmp_list->next)
459 {
460 0 tmp_list = globus_list_rest(tmp_list);
461 }
462 0 globus_list_insert(&entry, datum);
463 0 tmp_list->next = entry;
464 }
465
466 95 return 0;
467 }
468
469 static
470 globus_result_t
471 globus_l_handler_chain_push(
472 globus_list_t ** chain,
473 globus_extension_handle_t extension_handle,
474 globus_handler_invoke_func_t invoke,
475 globus_bool_t last)
476 190 {
477 190 globus_result_t result = GLOBUS_SUCCESS;
478 globus_l_handler_t * handler;
479 GlobusFuncName(globus_handler_chain_push);
480 190 GlobusHandlerDebugEnter();
481
482 190 handler = globus_malloc(sizeof(globus_l_handler_t));
483 190 if(!handler)
484 {
485 0 result = GlobusSoapMessageErrorOutOfMemory;
486 0 goto exit;
487 }
488
489 190 memset(handler, 0, sizeof(globus_l_handler_t));
490 190 handler->invoke = invoke;
491
492 190 if(last)
493 {
494 95 globus_l_handler_chain_list_insert_last(chain, handler);
495 }
496 else
497 {
498 95 globus_list_insert(chain, handler);
499 }
500
501 190 exit:
502 190 GlobusHandlerDebugExit();
503 190 return result;
504 }
505
506 globus_result_t
507 globus_l_handler_triggers_insert(
508 globus_hashtable_t * triggers,
509 globus_extension_handle_t ext,
510 globus_list_t * trigger_list)
511 190 {
512 190 globus_result_t result = GLOBUS_SUCCESS;
513 globus_list_t * trigger_iter;
514 globus_handler_trigger_t * trigger;
515 globus_l_handler_t * handler;
516 GlobusFuncName(globus_handler_chain_push);
517 190 GlobusHandlerDebugEnter();
518
519 190 if(!*triggers)
520 {
521 95 globus_hashtable_init(
522 triggers, 20, xsd_QName_hash, xsd_QName_keyeq);
523 }
524
525 190 trigger_iter = trigger_list;
526 1270 while(trigger_iter)
527 {
528 890 trigger = globus_list_first(trigger_iter);
529
530 890 handler = globus_malloc(sizeof(globus_l_handler_t));
531 890 if(!handler)
532 {
533 0 result = GlobusSoapMessageErrorOutOfMemory;
534 0 goto exit;
535 }
536
537 890 memset(handler, 0, sizeof(globus_l_handler_t));
538 890 handler->trigger = trigger;
539
540 890 globus_hashtable_insert(
541 triggers,
542 handler->trigger->element,
543 handler);
544 890 trigger_iter = globus_list_rest(trigger_iter);
545 }
546
547 190 exit:
548 190 GlobusHandlerDebugExit();
549 190 return result;
550 }
551
552 globus_result_t
553 globus_handler_chain_push(
554 globus_handler_chain_t chain,
555 globus_handler_type_t type,
556 const char * endpoint)
557 190 {
558 globus_handler_descriptor_t * handler_desc;
559 190 globus_result_t result = GLOBUS_SUCCESS;
560 globus_extension_handle_t extension_handle;
561 GlobusFuncName(globus_handler_chain_push);
562 190 GlobusHandlerDebugEnter();
563
564 190 handler_desc = globus_extension_lookup(
565 &extension_handle, GLOBUS_HANDLER_REGISTRY, (void *)endpoint);
566 190 if(!handler_desc)
567 {
568 globus_result_t tmp_result;
569
570 0 tmp_result = globus_extension_activate(endpoint);
571 0 if(tmp_result != GLOBUS_SUCCESS)
572 {
573 0 result = GlobusHandlerErrorRegistryLookupFailed(
574 tmp_result, endpoint);
575 0 goto exit;
576 }
577
578 0 globus_mutex_lock(&globus_l_handler_extensions_mutex);
579 0 globus_list_insert(
580 &globus_l_handler_extensions, strdup(endpoint));
581 0 globus_mutex_unlock(&globus_l_handler_extensions_mutex);
582
583 0 handler_desc = globus_extension_lookup(
584 &extension_handle, GLOBUS_HANDLER_REGISTRY, (void *)endpoint);
585 0 if(!handler_desc)
586 {
587 0 result = GlobusHandlerErrorRegistryLookupFailed(
588 GLOBUS_FAILURE, endpoint);
589 0 goto exit;
590 }
591 }
592
593 190 globus_list_insert(&chain->extensions, (void *)extension_handle);
594
595 190 if((type & GLOBUS_HANDLER_TYPE_REQUEST) && handler_desc->request)
596 {
597 95 globus_l_handler_chain_push(&chain->request_handlers,
598 extension_handle, handler_desc->request, GLOBUS_FALSE);
599 }
600
601 190 if((type & GLOBUS_HANDLER_TYPE_RESPONSE) && handler_desc->response)
602 {
603 95 globus_l_handler_chain_push(&chain->response_handlers,
604 extension_handle, handler_desc->response, GLOBUS_TRUE);
605 }
606
607 190 if((type & GLOBUS_HANDLER_TYPE_REQUEST_INIT) && handler_desc->request_init)
608 {
609 0 globus_l_handler_chain_push(
610 &chain->request_init_handlers,
611 extension_handle, handler_desc->request_init, GLOBUS_FALSE);
612 }
613
614 190 if((type & GLOBUS_HANDLER_TYPE_RESPONSE_INIT) && handler_desc->response_init)
615 {
616 0 globus_l_handler_chain_push(
617 &chain->response_init_handlers,
618 extension_handle, handler_desc->response_init, GLOBUS_FALSE);
619 }
620
621 190 if((type & GLOBUS_HANDLER_TYPE_REQUEST_DESTROY) && handler_desc->request_destroy)
622 {
623 0 globus_l_handler_chain_push(
624 &chain->request_destroy_handlers,
625 extension_handle, handler_desc->request_destroy, GLOBUS_FALSE);
626 }
627
628 190 if((type & GLOBUS_HANDLER_TYPE_RESPONSE_DESTROY) &&
629 handler_desc->response_destroy)
630 {
631 0 globus_l_handler_chain_push(
632 &chain->response_destroy_handlers,
633 extension_handle, handler_desc->response_destroy, GLOBUS_FALSE);
634 }
635
636
637 190 if(handler_desc->default_trigger)
638 {
639 60 if(chain->default_trigger &&
640 (chain->default_trigger != handler_desc->default_trigger))
641 {
642 0 result = GlobusHandlerErrorDefaultTriggerAlreadyDefined();
643 0 goto exit;
644 }
645
646 60 chain->default_trigger = handler_desc->default_trigger;
647 }
648
649 190 if(handler_desc->trigger_list)
650 {
651 190 globus_l_handler_triggers_insert(
652 &chain->triggers, extension_handle,
653 handler_desc->trigger_list);
654 }
655
656 190 exit:
657
658 190 GlobusHandlerDebugExit();
659 190 return result;
660 }
661
662 static
663 void
664 globus_l_handler_callback_call_next(
665 void * args)
666 82873 {
667 globus_l_handler_t * next_handler;
668 globus_handler_session_descriptor_t session;
669 globus_handler_invoke_func_t trigger;
670 82873 globus_assert(args);
671 82873 session = (globus_handler_session_descriptor_t) args;
672
673 82873 if(session->trigger)
674 {
675 23804 trigger = session->trigger;
676 23804 session->trigger = NULL;
677 23804 trigger(session, session->message, session->result);
678 23804 return;
679 }
680
681 59069 if(globus_list_empty(session->remaining_handlers))
682 {
683 48758 session->callback_func(session->result, session->callback_args);
684 48758 globus_free(session);
685 48758 return;
686 }
687
688 10311 next_handler = globus_list_first(session->remaining_handlers);
689 10311 session->remaining_handlers = globus_list_rest(
690 session->remaining_handlers);
691 10311 next_handler->invoke(session, session->message, session->result);
692 }
693
694 void
695 globus_handler_finished(
696 globus_handler_session_descriptor_t session,
697 globus_result_t result)
698 82873 {
699 82873 globus_result_t local_result = GLOBUS_SUCCESS;
700 GlobusFuncName(globus_handler_finished);
701 82873 GlobusHandlerDebugEnter();
702
703 82873 session->result = result;
704
705 82873 local_result = globus_callback_register_oneshot(
706 NULL, NULL,
707 globus_l_handler_callback_call_next,
708 session);
709 82873 if(local_result != GLOBUS_SUCCESS)
710 {
711 0 globus_panic(GLOBUS_HANDLER_MODULE,
712 local_result,
713 "[%s:%d] Couldn't register callback",
714 _globus_func_name,
715 __LINE__);
716 }
717
718 82873 GlobusHandlerDebugExit();
719 }
720
721 globus_bool_t
722 globus_handler_chain_has_trigger(
723 globus_handler_chain_t chain,
724 const xsd_QName * element)
725 0 {
726 0 if(chain->triggers && globus_hashtable_lookup(
727 &chain->triggers,
728 (void *)element))
729 {
730 0 return GLOBUS_TRUE;
731 }
732 0 return GLOBUS_FALSE;
733 }
734
735 globus_result_t
736 globus_handler_chain_register_trigger(
737 globus_handler_chain_t chain,
738 globus_soap_message_handle_t message,
739 const xsd_QName * element,
740 globus_handler_callback_func_t callback,
741 void * user_args)
742 23804 {
743 globus_handler_session_descriptor_t desc;
744 globus_l_handler_t * handler;
745 23804 globus_result_t result = GLOBUS_SUCCESS;
746 GlobusFuncName(globus_handler_chain_register_trigger);
747 23804 GlobusHandlerDebugEnter();
748
749 23804 if(!chain->triggers)
750 {
751 0 result = GlobusHandlerErrorNoTriggersDefined();
752 0 goto exit;
753 }
754
755 23804 desc = (globus_handler_session_descriptor_t) globus_malloc(
756 sizeof(globus_i_handler_session_descriptor_t));
757 23804 if(!desc)
758 {
759 0 result = GlobusSoapMessageErrorOutOfMemory;
760 0 goto exit;
761 }
762 23804 memset(desc, 0, sizeof(globus_i_handler_session_descriptor_t));
763
764 23804 desc->message = message;
765 23804 desc->callback_func = callback;
766 23804 desc->callback_args = user_args;
767
768 23804 handler = globus_hashtable_lookup(
769 &chain->triggers,
770 (void *)element);
771 23804 if(handler)
772 {
773 21720 desc->trigger = handler->trigger->invoke;
774 }
775 2084 else if(chain->default_trigger)
776 {
777 2084 desc->trigger = chain->default_trigger;
778 }
779 else
780 {
781 0 result = GLOBUS_HANDLER_STATUS_NOT_TRIGGERED;
782 0 goto exit;
783 }
784
785 23804 globus_handler_finished(desc, GLOBUS_SUCCESS);
786
787 23804 exit:
788
789 23804 GlobusHandlerDebugExit();
790 23804 return result;
791 }
792
793 void
794 globus_handler_chain_register_invoke(
795 globus_handler_chain_t chain,
796 globus_handler_type_t type,
797 globus_soap_message_handle_t message,
798 globus_handler_callback_func_t callback,
799 void * user_args)
800 24954 {
801 globus_handler_session_descriptor_t desc;
802 GlobusFuncName(globus_handler_chain_register_invoke);
803 24954 GlobusHandlerDebugEnter();
804
805 24954 desc = (globus_handler_session_descriptor_t) globus_malloc(
806 sizeof(globus_i_handler_session_descriptor_t));
807 24954 if(!desc)
808 {
809 0 globus_handler_finished(NULL, GlobusSoapMessageErrorOutOfMemory);
810 }
811
812 24954 memset(desc, 0, sizeof(globus_i_handler_session_descriptor_t));
813
814 24954 desc->message = message;
815 24954 desc->callback_func = callback;
816 24954 desc->callback_args = user_args;
817
818 24954 switch(type)
819 {
820 case GLOBUS_HANDLER_TYPE_REQUEST_INIT:
821 5196 desc->remaining_handlers = chain->request_init_handlers;
822 5196 break;
823 case GLOBUS_HANDLER_TYPE_REQUEST_DESTROY:
824 5195 desc->remaining_handlers = chain->request_destroy_handlers;
825 5195 break;
826 case GLOBUS_HANDLER_TYPE_REQUEST:
827 5195 desc->remaining_handlers = chain->request_handlers;
828 5195 break;
829 case GLOBUS_HANDLER_TYPE_RESPONSE_INIT:
830 2130 desc->remaining_handlers = chain->response_init_handlers;
831 2130 break;
832 case GLOBUS_HANDLER_TYPE_RESPONSE_DESTROY:
833 2122 desc->remaining_handlers = chain->response_destroy_handlers;
834 2122 break;
835 case GLOBUS_HANDLER_TYPE_RESPONSE:
836 5116 desc->remaining_handlers = chain->response_handlers;
837 5116 break;
838 default:
839 0 desc->remaining_handlers = NULL;
840 }
841
842 24954 globus_handler_finished(desc, GLOBUS_SUCCESS);
843
844 24954 GlobusHandlerDebugExit();