FreeCalypso > hg > fc-magnetite
comparison src/aci2/aci_dti_mng/dti_conn_mng.c @ 3:93999a60b835
src/aci2, src/condat2: import of g23m/condat source pieces from TCS211
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Mon, 26 Sep 2016 00:29:36 +0000 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
2:c41a534f33c6 | 3:93999a60b835 |
---|---|
1 /* | |
2 +----------------------------------------------------------------------------- | |
3 | Project : ... | |
4 | Modul : dti_conn_mng.c | |
5 +----------------------------------------------------------------------------- | |
6 | Copyright 2002 Texas Instruments Berlin, AG | |
7 | All rights reserved. | |
8 | | |
9 | This file is confidential and a trade secret of Texas | |
10 | Instruments Berlin, AG | |
11 | The receipt of or possession of this file does not convey | |
12 | any rights to reproduce or disclose its contents or to | |
13 | manufacture, use, or sell anything it may describe, in | |
14 | whole, or in part, without the specific written consent of | |
15 | Texas Instruments Berlin, AG. | |
16 +----------------------------------------------------------------------------- | |
17 | Purpose : Implementation of DTI Connection Manager | |
18 +----------------------------------------------------------------------------- | |
19 */ | |
20 | |
21 | |
22 #ifndef DTI_CONN_MNG_C | |
23 #define DTI_CONN_MNG_C | |
24 #endif | |
25 | |
26 | |
27 /*===== INCLUDES ===================================================*/ | |
28 | |
29 #include "aci_all.h" | |
30 | |
31 #include "pconst.cdg" | |
32 #include "mconst.cdg" | |
33 #include "cnf_aci.h" | |
34 #include "mon_aci.h" | |
35 #include "pei.h" | |
36 #include "aci_cmh.h" | |
37 #include "ati_cmd.h" | |
38 #include "aci_io.h" | |
39 | |
40 #include "aci_cmh.h" | |
41 #include "aci_lst.h" | |
42 #include "aci_mem.h" | |
43 | |
44 #include "dti.h" | |
45 #include "dti_conn_mng.h" | |
46 #include "dti_cntrl_mng.h" | |
47 | |
48 | |
49 | |
50 LOCAL ULONG used_dti_channels = 0; | |
51 LOCAL T_ACI_LIST *dti_channel_list = NULL; /* list_begin */ | |
52 | |
53 LOCAL T_DTI_CONN_PARAMS glob_params; | |
54 | |
55 | |
56 /********************** LOCAL FUNCTIONS *****************************/ | |
57 | |
58 | |
59 LOCAL UBYTE dti_conn_get_new_dti_id (void) | |
60 { | |
61 ULONG tst_id; | |
62 UBYTE i; | |
63 | |
64 TRACE_FUNCTION("dti_conn_get_new_dti_id()"); | |
65 | |
66 /* create a new DTI ID */ | |
67 for (i = 0; i <= MAX_DTI_CONN_CHANNELS; i++) | |
68 { | |
69 tst_id = (0x01 << i) & used_dti_channels; | |
70 if (!tst_id) | |
71 { | |
72 break; | |
73 } | |
74 } | |
75 if (tst_id) | |
76 { | |
77 TRACE_EVENT("No DTI ID available"); | |
78 return (DTI_DTI_ID_NOTPRESENT); | |
79 } | |
80 used_dti_channels |= (0x01 << i); | |
81 | |
82 TRACE_EVENT_P1("DTI ID %d created", i); | |
83 | |
84 return (i); | |
85 } | |
86 | |
87 | |
88 LOCAL void dti_conn_remove_dti_id (UBYTE dti_id) | |
89 { | |
90 ULONG tst_id; | |
91 | |
92 TRACE_FUNCTION("dti_conn_remove_id()"); | |
93 | |
94 if (dti_id >= MAX_DTI_CONN_CHANNELS) | |
95 return; | |
96 | |
97 tst_id = 0x01 << (dti_id); | |
98 used_dti_channels &= ~tst_id; | |
99 | |
100 TRACE_EVENT_P1("DTI ID %d removed", dti_id); | |
101 | |
102 } | |
103 | |
104 | |
105 LOCAL BOOL dti_conn_error_cb(UBYTE dti_id, T_DTI_CONN_STATE result_type) | |
106 { | |
107 /* theorically should not be called... Yet helpfull for testing */ | |
108 TRACE_FUNCTION("dti_conn_error_cb()"); | |
109 | |
110 TRACE_EVENT("ERROR: DTI connection callback has not been initialized !"); | |
111 | |
112 return FALSE; | |
113 } | |
114 | |
115 | |
116 LOCAL void dti_conn_reset_conn_parms( T_DTI_CONN_CHANNEL *dti_channel ) | |
117 { | |
118 | |
119 UBYTE i,j; | |
120 | |
121 TRACE_FUNCTION("dti_conn_reset_conn_parms()"); | |
122 | |
123 dti_channel->erase_channel = FALSE; | |
124 dti_channel->num_of_conns = 0; | |
125 dti_channel->conn_cb = dti_conn_error_cb; | |
126 dti_channel->state = DTI_CONN_STATE_DISCONNECTED; | |
127 | |
128 for (i=0; i<MAX_DTI_CONN_TUPLES; i++) | |
129 { | |
130 dti_channel->tuple_list[i].state = DTI_CONN_STATE_DISCONNECTED; | |
131 for (j=0; j<NUM_OF_PEERS; j++) | |
132 { | |
133 dti_channel->tuple_list[i].peers[j].state = DTI_CONN_STATE_DISCONNECTED; | |
134 dti_channel->tuple_list[i].peers[j].ent_id = DTI_ENTITY_INVALID; | |
135 } | |
136 } | |
137 } | |
138 | |
139 | |
140 LOCAL BOOL DTItest_dti_id( UBYTE dti_id, void *elem) | |
141 { | |
142 T_DTI_CONN_CHANNEL *dti_channel = (T_DTI_CONN_CHANNEL *)elem; | |
143 | |
144 if (dti_channel EQ NULL) | |
145 return FALSE; | |
146 if (dti_channel -> dti_id EQ dti_id ) | |
147 return TRUE; | |
148 else | |
149 return FALSE; | |
150 } | |
151 | |
152 LOCAL T_DTI_CONN_TUPLE *dti_conn_find_dti_tuple( T_DTI_CONN_CHANNEL *dti_channel, UBYTE tuple_no) | |
153 { | |
154 return &(dti_channel->tuple_list[tuple_no]); | |
155 } | |
156 | |
157 | |
158 LOCAL T_DTI_CONN_CHANNEL *dti_conn_find_dti_conn( UBYTE dti_id ) | |
159 { | |
160 T_DTI_CONN_CHANNEL *dti_channel; | |
161 | |
162 TRACE_FUNCTION("dti_conn_find_dti_conn()"); | |
163 | |
164 /*find channel in list */ | |
165 dti_channel = find_element (dti_channel_list, dti_id, DTItest_dti_id); | |
166 | |
167 return dti_channel; | |
168 } | |
169 | |
170 | |
171 LOCAL BOOL dti_conn_connect( T_DTI_CONN_CHANNEL* dti_channel, | |
172 T_DTI_ENTITY_ID* entity_list, | |
173 UBYTE num_entities, | |
174 T_DTI_CONN_MODE mode ) | |
175 { | |
176 ULONG link_id; | |
177 UBYTE tuple_no; | |
178 UBYTE i; | |
179 | |
180 TRACE_FUNCTION("dti_conn_connect()"); | |
181 | |
182 dti_channel->state = DTI_CONN_STATE_CONNECTING; | |
183 | |
184 if (dti_channel->conn_cb) | |
185 { | |
186 dti_channel->conn_cb(dti_channel->dti_id, DTI_CONN_STATE_CONNECTING); | |
187 } | |
188 else | |
189 { | |
190 TRACE_EVENT("conn_cb is NULL"); | |
191 } | |
192 | |
193 | |
194 if (mode EQ APPEND) | |
195 { | |
196 tuple_no = dti_channel->num_of_conns; | |
197 } | |
198 else /* SPLIT */ | |
199 { | |
200 tuple_no = 0; | |
201 dti_channel->num_of_conns = 0; | |
202 } | |
203 | |
204 for (i=0; i<num_entities-1; i++) | |
205 { | |
206 dti_channel->tuple_list[tuple_no].peers[0].ent_id = entity_list[i]; | |
207 dti_channel->tuple_list[tuple_no].peers[1].ent_id = entity_list[i+1]; | |
208 | |
209 if ( (dti_channel->tuple_list[tuple_no].state NEQ DTI_CONN_STATE_DISCONNECTING) AND | |
210 (dti_channel->tuple_list[tuple_no].state NEQ DTI_CONN_STATE_CONNECTING) ) | |
211 { | |
212 dti_channel->tuple_list[tuple_no].state = DTI_CONN_STATE_CONNECTING; | |
213 dti_channel->tuple_list[tuple_no].tuple_no = tuple_no; | |
214 dti_channel->state = DTI_CONN_STATE_CONNECTING; | |
215 | |
216 link_id = dti_conn_compose_link_id(0, 0, dti_channel->dti_id, tuple_no); | |
217 | |
218 dti_channel->tuple_list[tuple_no].peers[0].state = DTI_CONN_STATE_CONNECTING; | |
219 dti_channel->tuple_list[tuple_no].peers[1].state = DTI_CONN_STATE_CONNECTING; | |
220 | |
221 /* connect a tuple */ | |
222 glob_params.mng_ent_cb(link_id, entity_list[i], entity_list[i+1], DTI_CONNECT); | |
223 glob_params.mng_ent_cb(link_id, entity_list[i+1], entity_list[i], DTI_CONNECT); | |
224 } | |
225 | |
226 tuple_no++; | |
227 } | |
228 | |
229 dti_channel->num_of_conns = tuple_no; | |
230 | |
231 return TRUE; | |
232 } | |
233 | |
234 | |
235 LOCAL BOOL dti_conn_disconnect( T_DTI_CONN_CHANNEL* dti_channel ) | |
236 { | |
237 ULONG link_id; | |
238 UBYTE i; | |
239 | |
240 TRACE_FUNCTION("dti_conn_disconnect()"); | |
241 | |
242 dti_channel->state = DTI_CONN_STATE_DISCONNECTING; | |
243 | |
244 if (dti_channel->conn_cb) | |
245 { | |
246 dti_channel->conn_cb(dti_channel->dti_id, DTI_CONN_STATE_DISCONNECTING); | |
247 } | |
248 else | |
249 { | |
250 TRACE_EVENT("conn_cb is NULL"); | |
251 } | |
252 | |
253 for (i=0; i < dti_channel->num_of_conns; i++) | |
254 { | |
255 | |
256 /* set tuple state only if it is not already DISCONNECTED */ | |
257 if (dti_channel->tuple_list[i].state NEQ DTI_CONN_STATE_DISCONNECTED) | |
258 { | |
259 dti_channel->tuple_list[i].state = DTI_CONN_STATE_DISCONNECTING; | |
260 } | |
261 | |
262 link_id = dti_conn_compose_link_id(0, 0, dti_channel->dti_id, i); | |
263 | |
264 /* disconnect only a connected entity */ | |
265 if (dti_channel->tuple_list[i].peers[0].state EQ DTI_CONN_STATE_CONNECTED OR | |
266 dti_channel->tuple_list[i].peers[0].state EQ DTI_CONN_STATE_CONNECTING ) | |
267 { | |
268 dti_channel->tuple_list[i].peers[0].state = DTI_CONN_STATE_DISCONNECTING; | |
269 glob_params.mng_ent_cb(link_id, dti_channel->tuple_list[i].peers[0].ent_id, | |
270 dti_channel->tuple_list[i].peers[1].ent_id, DTI_DISCONNECT); | |
271 } | |
272 | |
273 /* disconnect only a connected entity */ | |
274 if (dti_channel->tuple_list[i].peers[1].state EQ DTI_CONN_STATE_CONNECTED OR | |
275 dti_channel->tuple_list[i].peers[1].state EQ DTI_CONN_STATE_CONNECTING ) | |
276 { | |
277 dti_channel->tuple_list[i].peers[1].state = DTI_CONN_STATE_DISCONNECTING; | |
278 glob_params.mng_ent_cb(link_id, dti_channel->tuple_list[i].peers[1].ent_id, | |
279 dti_channel->tuple_list[i].peers[0].ent_id, DTI_DISCONNECT); | |
280 } | |
281 } | |
282 | |
283 return TRUE; | |
284 } | |
285 | |
286 | |
287 | |
288 | |
289 | |
290 | |
291 | |
292 /********************** GLOBAL FUNCTIONS *****************************/ | |
293 | |
294 | |
295 GLOBAL T_DTI_CONN_LINK_ID dti_conn_compose_link_id(UBYTE dummy, UBYTE assoc, UBYTE dti_id, UBYTE tuple_no) | |
296 { | |
297 T_DTI_CONN_LINK_ID link_id = 0; | |
298 | |
299 link_id += dummy; | |
300 link_id <<= 8; | |
301 link_id += assoc; | |
302 link_id <<= 8; | |
303 link_id += dti_id; | |
304 link_id <<= 8; | |
305 link_id += tuple_no; | |
306 | |
307 return link_id; | |
308 } | |
309 | |
310 | |
311 /* | |
312 +--------------------------------------------------------------------+ | |
313 | PROJECT : MODULE : DTI_CONN | | |
314 | STATE : code ROUTINE : dti_conn_init | | |
315 +--------------------------------------------------------------------+ | |
316 | |
317 PURPOSE : initialise the DTI Connection Manager | |
318 | |
319 */ | |
320 GLOBAL void dti_conn_init( T_DTI_CONN_MNG_ENT_CB* mng_ent_cb ) | |
321 { | |
322 TRACE_FUNCTION("dti_conn_init()"); | |
323 | |
324 dti_channel_list = new_list (); | |
325 | |
326 glob_params.conn_cb = NULL; | |
327 glob_params.mng_ent_cb = mng_ent_cb; | |
328 glob_params.num_entities = 0; | |
329 | |
330 } | |
331 | |
332 | |
333 /* | |
334 +--------------------------------------------------------------------+ | |
335 | PROJECT : MODULE : DTI_CONN | | |
336 | STATE : code ROUTINE : dti_conn_new | | |
337 +--------------------------------------------------------------------+ | |
338 | |
339 PURPOSE : register new DTI channel | |
340 | |
341 */ | |
342 GLOBAL UBYTE dti_conn_new(UBYTE dti_id ) | |
343 { | |
344 T_DTI_CONN_CHANNEL *dti_channel; | |
345 | |
346 TRACE_FUNCTION("dti_conn_new()"); | |
347 | |
348 | |
349 if (dti_id EQ DTI_DTI_ID_NOTPRESENT) | |
350 { | |
351 dti_id = dti_conn_get_new_dti_id (); | |
352 } | |
353 | |
354 if (dti_id EQ DTI_DTI_ID_NOTPRESENT) | |
355 { | |
356 return (DTI_DTI_ID_NOTPRESENT); | |
357 } | |
358 | |
359 /* search for an existing entry with correspondant dti_id */ | |
360 dti_channel = dti_conn_find_dti_conn (dti_id); | |
361 | |
362 if( dti_channel ) | |
363 { | |
364 return (DTI_DTI_ID_NOTPRESENT); /* couldn't create a new entry */ | |
365 } | |
366 | |
367 ACI_MALLOC(dti_channel, sizeof(T_DTI_CONN_CHANNEL)); | |
368 | |
369 dti_conn_reset_conn_parms (dti_channel); | |
370 dti_channel->dti_id = dti_id; | |
371 insert_list(dti_channel_list, dti_channel); | |
372 | |
373 return (dti_channel->dti_id); | |
374 } | |
375 | |
376 | |
377 /* | |
378 +---------------------------------------------------------------------+ | |
379 | PROJECT : MODULE : DTI_CONN | | |
380 | STATE : code ROUTINE : dti_conn_erase_entry | | |
381 +---------------------------------------------------------------------+ | |
382 | |
383 PURPOSE : /* erase entry from DTI channel list | |
384 | |
385 */ | |
386 GLOBAL void dti_conn_erase_entry(UBYTE dti_id) | |
387 { | |
388 T_DTI_CONN_CHANNEL *dti_channel; | |
389 | |
390 TRACE_FUNCTION("dti_conn_erase_entry"); | |
391 | |
392 /* find element to be erased */ | |
393 dti_channel = remove_element (dti_channel_list, dti_id, DTItest_dti_id); | |
394 | |
395 if( dti_channel NEQ NULL ) /* entry not erased yet */ | |
396 ACI_MFREE (dti_channel); | |
397 | |
398 dti_conn_remove_dti_id(dti_id); | |
399 } | |
400 | |
401 | |
402 /* | |
403 +-----------------------------------------------------------------------+ | |
404 | PROJECT : MODULE : DTI_CONN | | |
405 | STATE : code ROUTINE : dti_conn_is_dti_channel_connected | | |
406 +-----------------------------------------------------------------------+ | |
407 | |
408 PURPOSE : returns TRUE if end-to-end DTI connection is connected and | |
409 the given entity is in this connection | |
410 | |
411 */ | |
412 GLOBAL BOOL dti_conn_is_dti_channel_connected( T_DTI_ENTITY_ID ent_id, UBYTE dti_id ) | |
413 { | |
414 UBYTE count = 0; | |
415 UBYTE i; | |
416 UBYTE entity_found = FALSE; | |
417 T_DTI_CONN_CHANNEL *dti_channel = dti_conn_find_dti_conn( dti_id ); | |
418 | |
419 TRACE_FUNCTION("dti_conn_is_dti_channel_connected()"); | |
420 | |
421 if (dti_channel EQ NULL) | |
422 { | |
423 TRACE_EVENT_P1("dti_channel for dti_id %d not found", dti_id); | |
424 return FALSE; | |
425 } | |
426 | |
427 for (i=0; i<dti_channel->num_of_conns; i++) | |
428 { | |
429 if ((dti_channel->tuple_list[i].peers[0].ent_id EQ ent_id) OR | |
430 (dti_channel->tuple_list[i].peers[1].ent_id EQ ent_id)) | |
431 { | |
432 entity_found = TRUE; | |
433 break; | |
434 } | |
435 } | |
436 | |
437 if (entity_found EQ FALSE) | |
438 return FALSE; | |
439 | |
440 if (dti_channel->state EQ DTI_CONN_STATE_CONNECTED) | |
441 { | |
442 return TRUE; | |
443 } | |
444 else | |
445 { | |
446 for (i=0; i<dti_channel->num_of_conns; i++) | |
447 { | |
448 if (dti_channel->tuple_list[i].state EQ DTI_CONN_STATE_CONNECTED) | |
449 { | |
450 count++; | |
451 } | |
452 } | |
453 | |
454 if (count EQ dti_channel->num_of_conns) | |
455 { | |
456 return TRUE; | |
457 } | |
458 } | |
459 | |
460 return FALSE; | |
461 } | |
462 | |
463 | |
464 /* | |
465 +--------------------------------------------------------------------------+ | |
466 | PROJECT : MODULE : DTI_CONN | | |
467 | STATE : code ROUTINE : dti_conn_is_dti_channel_disconnected | | |
468 +--------------------------------------------------------------------------+ | |
469 | |
470 PURPOSE : returns TRUE if end-to-end DTI connection is disconnected | |
471 | |
472 */ | |
473 GLOBAL BOOL dti_conn_is_dti_channel_disconnected( UBYTE dti_id ) | |
474 { | |
475 UBYTE count = 0; | |
476 UBYTE i; | |
477 T_DTI_CONN_CHANNEL *dti_channel = dti_conn_find_dti_conn( dti_id ); | |
478 | |
479 TRACE_FUNCTION("dti_conn_is_dti_channel_disconnected()"); | |
480 | |
481 | |
482 if (dti_channel EQ NULL) | |
483 { | |
484 return TRUE; | |
485 } | |
486 | |
487 if (dti_channel->state EQ DTI_CONN_STATE_DISCONNECTED) | |
488 { | |
489 return TRUE; | |
490 } | |
491 else | |
492 { | |
493 for (i=0; i<dti_channel->num_of_conns; i++) | |
494 { | |
495 if (dti_channel->tuple_list[i].state EQ DTI_CONN_STATE_DISCONNECTED) | |
496 { | |
497 count++; | |
498 } | |
499 } | |
500 | |
501 if (count EQ dti_channel->num_of_conns) | |
502 { | |
503 return TRUE; | |
504 } | |
505 } | |
506 | |
507 return FALSE; | |
508 } | |
509 | |
510 | |
511 /* | |
512 +---------------------------------------------------------------------+ | |
513 | PROJECT : MODULE : DTI_CONN | | |
514 | STATE : code ROUTINE : dti_conn_est_dpath | | |
515 +---------------------------------------------------------------------+ | |
516 | |
517 PURPOSE : establishes data path. | |
518 | |
519 */ | |
520 GLOBAL BOOL dti_conn_est_dpath( UBYTE dti_id, | |
521 T_DTI_ENTITY_ID* entity_list, | |
522 UBYTE num_entities, | |
523 T_DTI_CONN_MODE mode, | |
524 T_DTI_CONN_CB* cb) | |
525 { | |
526 T_DTI_CONN_CHANNEL *dti_channel; | |
527 | |
528 TRACE_FUNCTION("dti_conn_est_dpath()"); | |
529 | |
530 | |
531 /*find channel in list */ | |
532 dti_channel = dti_conn_find_dti_conn (dti_id); | |
533 | |
534 if (dti_channel EQ NULL) | |
535 { | |
536 TRACE_EVENT_P1("[ERR] dti_conn_est_dpath: dti_channel dti_id=%x not found", | |
537 dti_id); | |
538 /* DTI ID not found */ | |
539 return FALSE; | |
540 } | |
541 | |
542 if ( entity_list[0] EQ DTI_ENTITY_INVALID OR entity_list[1] EQ DTI_ENTITY_INVALID) | |
543 { | |
544 /* improper entity list */ | |
545 TRACE_EVENT("[ERR] improper entity list "); | |
546 return FALSE; | |
547 } | |
548 | |
549 /* if 'SPLIT' then the whole DTI channel must be disconnected before a | |
550 * new connection is established | |
551 */ | |
552 if ((mode EQ SPLIT) AND (dti_channel->state NEQ DTI_CONN_STATE_DISCONNECTED)) | |
553 { | |
554 dti_conn_disconnect (dti_channel); | |
555 | |
556 /* save new entity list to entity list buffer */ | |
557 memcpy(glob_params.entity_list_buf, entity_list, sizeof(T_DTI_ENTITY_ID)*num_entities); | |
558 glob_params.num_entities = num_entities; | |
559 glob_params.conn_cb = cb; | |
560 } | |
561 else | |
562 { | |
563 dti_channel->conn_cb = cb; | |
564 dti_conn_connect (dti_channel, entity_list, num_entities, mode); | |
565 } | |
566 | |
567 return TRUE; | |
568 } | |
569 | |
570 | |
571 /* | |
572 +---------------------------------------------------------------------+ | |
573 | PROJECT : MODULE : DTI_CONN | | |
574 | STATE : code ROUTINE : dti_conn_close_dpath | | |
575 +---------------------------------------------------------------------+ | |
576 | |
577 PURPOSE : closes a DTI connection | |
578 | |
579 */ | |
580 GLOBAL BOOL dti_conn_close_dpath( UBYTE dti_id ) | |
581 { | |
582 T_DTI_CONN_CHANNEL *dti_channel; | |
583 UBYTE i=0; | |
584 | |
585 TRACE_FUNCTION("dti_conn_close_dpath()"); | |
586 | |
587 | |
588 dti_channel = dti_conn_find_dti_conn( dti_id ); | |
589 if (dti_channel EQ NULL) | |
590 { | |
591 TRACE_EVENT_P1("[ERR] dti_conn_close_dpath: dti_channel dti_id=%x not found", | |
592 dti_id); | |
593 return FALSE; | |
594 } | |
595 | |
596 if (dti_channel->state NEQ DTI_CONN_STATE_DISCONNECTED) | |
597 { | |
598 dti_channel->state = DTI_CONN_STATE_DISCONNECTING; | |
599 | |
600 dti_conn_disconnect (dti_channel); | |
601 } | |
602 else | |
603 { | |
604 TRACE_EVENT("[ERR] dti_conn_close_dpath: try to close dpath which was DISCONNECTED"); | |
605 return FALSE; | |
606 } | |
607 | |
608 return TRUE; | |
609 } | |
610 | |
611 | |
612 /* | |
613 +-----------------------------------------------------------------------+ | |
614 | PROJECT : MODULE : DTI_CONN | | |
615 | STATE : code ROUTINE : dti_conn_entity_connected | | |
616 +-----------------------------------------------------------------------+ | |
617 | |
618 PURPOSE : response after a DTI connect request. This function is called | |
619 to inform the DTI Connection Manager that a connection is | |
620 established. | |
621 | |
622 */ | |
623 GLOBAL void dti_conn_entity_connected( T_DTI_CONN_LINK_ID link_id, | |
624 T_DTI_ENTITY_ID ent_id, | |
625 T_DTI_CONN_RESULT result ) | |
626 { | |
627 T_DTI_CONN_CHANNEL *dti_channel; | |
628 T_DTI_CONN_TUPLE *tuple; | |
629 UBYTE i; | |
630 UBYTE dti_id = EXTRACT_DTI_ID(link_id); | |
631 BOOL both_entities_connected = FALSE; | |
632 UBYTE count = 0; | |
633 | |
634 TRACE_FUNCTION("dti_conn_entity_connected()"); | |
635 | |
636 | |
637 dti_channel = dti_conn_find_dti_conn( dti_id ); | |
638 if (dti_channel EQ NULL) | |
639 { | |
640 TRACE_EVENT_P1("[ERR] dti_conn_entity_connected: dti_channel link_id=%x not found", | |
641 link_id); | |
642 return; | |
643 } | |
644 | |
645 if (result EQ DTI_ERROR) | |
646 { | |
647 /* mark entity as disconnected */ | |
648 dti_conn_entity_disconnected( link_id, ent_id ); | |
649 | |
650 /* close the whole DTI channel */ | |
651 dti_conn_close_dpath( dti_id ); | |
652 return; | |
653 } | |
654 | |
655 if (dti_channel->state EQ DTI_CONN_STATE_CONNECTED) | |
656 { | |
657 TRACE_EVENT_P1("dti channel with dti_id=%x already connected", dti_id); | |
658 return; | |
659 } | |
660 | |
661 tuple = dti_conn_find_dti_tuple( dti_channel, EXTRACT_TUPLE_NO(link_id ) ); | |
662 | |
663 for (i=0; i<NUM_OF_PEERS; i++) | |
664 { | |
665 if (tuple->peers[i].state EQ DTI_CONN_STATE_CONNECTED) | |
666 { | |
667 count++; | |
668 } | |
669 | |
670 if (tuple->peers[i].ent_id EQ ent_id) | |
671 { | |
672 if (tuple->peers[i].state EQ DTI_CONN_STATE_CONNECTING) | |
673 { | |
674 tuple->peers[i].state = DTI_CONN_STATE_CONNECTED; | |
675 count++; | |
676 } | |
677 } | |
678 if (count EQ NUM_OF_PEERS) | |
679 { | |
680 both_entities_connected = TRUE; | |
681 } | |
682 } | |
683 | |
684 /* if both entities are CONNECTED */ | |
685 if (both_entities_connected) | |
686 { | |
687 tuple->state = DTI_CONN_STATE_CONNECTED; | |
688 | |
689 /* if all other tuples CONNECTED */ | |
690 if (dti_conn_is_dti_channel_connected(ent_id, dti_id)) | |
691 { | |
692 dti_channel->state = DTI_CONN_STATE_CONNECTED; | |
693 | |
694 TRACE_EVENT_P1("DTI ID %d connected", dti_id); | |
695 | |
696 /* call connect_cb here */ | |
697 if (dti_channel->conn_cb) | |
698 { | |
699 dti_channel->conn_cb(dti_id, DTI_CONN_STATE_CONNECTED); | |
700 } | |
701 else | |
702 { | |
703 TRACE_EVENT("conn_cb is NULL"); | |
704 } | |
705 } | |
706 } | |
707 } | |
708 | |
709 | |
710 /* | |
711 +-----------------------------------------------------------------------+ | |
712 | PROJECT : MODULE : DTI_CONN | | |
713 | STATE : code ROUTINE : dti_conn_entity_disconnected | | |
714 +-----------------------------------------------------------------------+ | |
715 | |
716 PURPOSE : response after a DTI connect request. This function is called | |
717 to inform the DTI Connection Manager that a connection is | |
718 closed. | |
719 | |
720 */ | |
721 GLOBAL void dti_conn_entity_disconnected( T_DTI_CONN_LINK_ID link_id, T_DTI_ENTITY_ID ent_id ) | |
722 { | |
723 T_DTI_CONN_CHANNEL *dti_channel; | |
724 T_DTI_CONN_TUPLE *tuple; | |
725 UBYTE i; | |
726 UBYTE dti_id = EXTRACT_DTI_ID(link_id); | |
727 UBYTE count = 0; | |
728 | |
729 TRACE_FUNCTION("dti_conn_entity_disconnected()"); | |
730 | |
731 | |
732 dti_channel = dti_conn_find_dti_conn( dti_id ); | |
733 if (dti_channel EQ NULL) | |
734 { | |
735 TRACE_EVENT_P1("[ERR] dti_conn_entity_disconnected: dti_channel link_id=%x not found", | |
736 link_id); | |
737 return; | |
738 } | |
739 | |
740 if (dti_channel->state EQ DTI_CONN_STATE_DISCONNECTED) | |
741 { | |
742 TRACE_EVENT_P1("dti channel with dti_id=%x already diconnected", dti_id); | |
743 return; | |
744 } | |
745 | |
746 | |
747 tuple = dti_conn_find_dti_tuple( dti_channel, EXTRACT_TUPLE_NO(link_id) ); | |
748 | |
749 for (i=0; i<NUM_OF_PEERS; i++) | |
750 { | |
751 if (tuple->peers[i].state EQ DTI_CONN_STATE_DISCONNECTED) | |
752 { | |
753 count++; | |
754 } | |
755 | |
756 /* find disconnected entity */ | |
757 if (tuple->peers[i].ent_id EQ ent_id) | |
758 { | |
759 tuple->peers[i].state = DTI_CONN_STATE_DISCONNECTED; | |
760 tuple->peers[i].ent_id = DTI_ENTITY_INVALID; | |
761 count++; | |
762 | |
763 tuple->state = DTI_CONN_STATE_DISCONNECTING; | |
764 | |
765 if (dti_channel->state EQ DTI_CONN_STATE_CONNECTED) | |
766 { | |
767 /* set DTI channel state */ | |
768 dti_channel->state = DTI_CONN_STATE_DISCONNECTING; | |
769 } | |
770 } | |
771 } | |
772 | |
773 /* if both entities are DISCONNECTED */ | |
774 if (count EQ NUM_OF_PEERS) | |
775 { | |
776 /* set tuple state */ | |
777 tuple->state = DTI_CONN_STATE_DISCONNECTED; | |
778 | |
779 /* if all other tuples DISCONNECTED */ | |
780 if (dti_conn_is_dti_channel_disconnected(dti_id)) | |
781 { | |
782 dti_channel->state = DTI_CONN_STATE_DISCONNECTED; | |
783 | |
784 TRACE_EVENT_P1("DTI ID %d disconnected", dti_id); | |
785 | |
786 /* reset number of conns */ | |
787 dti_channel->num_of_conns = 0; | |
788 | |
789 /* call disconnect_cb here */ | |
790 if (dti_channel->conn_cb) | |
791 { | |
792 dti_channel->conn_cb(dti_id, DTI_CONN_STATE_DISCONNECTED); | |
793 } | |
794 else | |
795 { | |
796 TRACE_EVENT("conn_cb is NULL"); | |
797 } | |
798 | |
799 if (glob_params.num_entities NEQ 0) | |
800 { | |
801 dti_channel->conn_cb = glob_params.conn_cb; | |
802 dti_conn_connect( dti_channel, glob_params.entity_list_buf, glob_params.num_entities, SPLIT ); | |
803 glob_params.num_entities = 0; | |
804 } | |
805 else | |
806 { | |
807 if (dti_channel->erase_channel EQ TRUE) | |
808 { | |
809 /* erase entry in DTI Conn Mng */ | |
810 dti_conn_erase_entry(dti_id); | |
811 } | |
812 } | |
813 } | |
814 } | |
815 } | |
816 | |
817 | |
818 /* | |
819 +-----------------------------------------------------------------------+ | |
820 | PROJECT : MODULE : DTI_CONN | | |
821 | STATE : code ROUTINE : dti_conn_close_all_connections| | |
822 +-----------------------------------------------------------------------+ | |
823 | |
824 PURPOSE : This function is called to close all established DTI | |
825 connections. | |
826 | |
827 */ | |
828 GLOBAL void dti_conn_close_all_connections() | |
829 { | |
830 T_DTI_CONN_CHANNEL *dti_channel; | |
831 | |
832 TRACE_FUNCTION("dti_conn_close_all_connections()"); | |
833 | |
834 while(TRUE) | |
835 { | |
836 dti_channel = get_next_element (dti_channel_list, dti_channel); | |
837 if (dti_channel EQ NULL) | |
838 { | |
839 return; | |
840 } | |
841 | |
842 if (dti_channel->state EQ DTI_CONN_STATE_CONNECTED) | |
843 { | |
844 dti_conn_close_dpath(dti_channel->dti_id); | |
845 dti_channel->erase_channel = TRUE; | |
846 } | |
847 else | |
848 { | |
849 dti_conn_erase_entry(dti_channel->dti_id); | |
850 } | |
851 } | |
852 } |