comparison g23m-gsm/cc/cc_rel.c @ 0:75a11d740a02

initial import of gsm-fw from freecalypso-sw rev 1033:5ab737ac3ad7
author Mychaela Falconia <falcon@freecalypso.org>
date Thu, 09 Jun 2016 00:02:41 +0000
parents
children
comparison
equal deleted inserted replaced
-1:000000000000 0:75a11d740a02
1 /*
2 +-----------------------------------------------------------------------------
3 | Project : GSM-PS (6147)
4 | Modul : CC_REL
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 : This Modul defines the functions for call release
18 | of the component CC of the mobile station.
19 +-----------------------------------------------------------------------------
20 */
21
22 #ifndef CC_REL_C
23 #define CC_REL_C
24
25 #include "config.h"
26 #include "fixedconf.h"
27 #include "condat-features.h"
28
29 #define ENTITY_CC
30 /*==== INCLUDES ===================================================*/
31
32 #include <string.h>
33 #include "typedefs.h"
34 #include "pcm.h"
35 #include "vsi.h"
36 #include "custom.h"
37 #include "gsm.h"
38 #include "message.h"
39 #include "ccdapi.h"
40 #include "prim.h"
41 #include "cnf_cc.h"
42 #include "mon_cc.h"
43 #include "pei.h"
44 #include "tok.h"
45 #include "cc.h"
46 #include "cc_em.h"
47
48 /*==== EXPORT =====================================================*/
49
50 /*==== PROTOTYPES =================================================*/
51 /* Implements Measure# 8 */
52 LOCAL void cc_mncc_release_ind (T_PRIM * prim);
53 /* Implements Measure# 9 */
54 LOCAL void cc_mncc_release_cnf (T_PRIM * prim);
55 /* Implements Measure# 41 */
56 LOCAL void cc_mncc_sync_ind ( UBYTE ti,
57 UBYTE new_state);
58 /*==== PRIVAT =====================================================*/
59
60 /*==== VARIABLES ==================================================*/
61
62 /*==== FUNCTIONS ==================================================*/
63
64 /*
65 +--------------------------------------------------------------------+
66 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
67 | STATE : code ROUTINE : cc_check_setup_reattempt |
68 +--------------------------------------------------------------------+
69
70 PURPOSE : This function checks whether a the mobile originated setup
71 may be reattempted. This will be done for some certain
72 reasons which may indicate network failure.
73 This function is considered as a hack only
74 for networks which tend to deliver a poor quality
75 of service only (e.g. typically in China).
76 This behaviour or the algorithm is not specified / implied
77 by GSM but driven by customer requests and the desire
78 to have a good, working product.
79 */
80
81 LOCAL void cc_check_setup_reattempt ( const T_M_CC_cc_cause *cc_cause)
82 {
83 GET_INSTANCE_DATA;
84 EXTERN BOOL poor_quality_network;
85
86 TRACE_FUNCTION ("cc_check_setup_reattempt()");
87
88 #ifdef WIN32
89 /*
90 * Set poor_quality_network for test, pei_config() is the appropriate place,
91 * but this seems not to be working for some strange reasons
92 */
93 poor_quality_network = TRUE;
94 #endif
95
96 /* reattempt already "running", see cc_setup_reattempt for further reasoning */
97 if (cc_data->setup_reattempt_ti NEQ NOT_PRESENT_8BIT)
98 return;
99
100 switch (cc_data->state[cc_data->index_ti])
101 {
102 case M_CC_CS_1: /* call initiated */
103 case M_CC_CS_3: /* mobile originating call proceeding */
104 cc_data->setup_attempts++;
105 if (poor_quality_network AND
106 (cc_data->setup_attempts < MAX_SETUP_ATTEMPTS) AND
107 (cc_cause->v_cause))
108 {
109 /*
110 * Mobile originated call got disconnect,
111 * max. number of setup attempts not reached.
112 * New dial attempt for certain disconnect reasons
113 */
114 switch (cc_cause->cause)
115 {
116 case M_CC_CAUSE_NO_CHAN_AVAIL: /* #34 */
117 case M_CC_CAUSE_NETWORK_ORDER: /* #38 */
118 case M_CC_CAUSE_TEMP_FAIL: /* #41 */
119 case M_CC_CAUSE_SWITCH_CONGEST: /* #42 */
120 case M_CC_CAUSE_INFO_DISCARD: /* #43 */
121 case M_CC_CAUSE_REQ_CHAN_UNAVAIL: /* #44 */
122 case M_CC_CAUSE_RESOURCE_UNAVAIL: /* #47 */
123 case M_CC_CAUSE_QOS_UNAVAIL: /* #49 */
124 case M_CC_CAUSE_BEARER_CAP_UNAVAIL: /* #58 */
125 case M_CC_CAUSE_TIMER: /* #102 */
126 case M_CC_CAUSE_INTERWORKING: /* #127 */
127 /*
128 * Maybe some more causes to added here
129 * which indicate network failure
130 */
131
132 /* try setup reattempt, remember this by setting setup_reattempt_ti */
133 cc_data->setup_reattempt_ti = cc_data->ti;
134 break;
135
136 default: /* Don't try setup reattempt, no appropriate cause */
137 srv_free_stored_setup ();
138 break;
139 }
140 }
141 break;
142
143 default: /* Don't try setup reattempt in other states */
144 break;
145 }
146 }
147
148 /*
149 +--------------------------------------------------------------------+
150 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
151 | STATE : code ROUTINE : cc_setup_reattempt |
152 +--------------------------------------------------------------------+
153
154 PURPOSE : This function reattempts the mobile originated setup
155 for some certain reasons which may indicate network
156 failure. This function is considered as a hack only
157 for networks which tend to deliver a poor quality
158 of service only.
159
160 */
161
162 LOCAL void cc_setup_reattempt (void)
163 {
164 GET_INSTANCE_DATA;
165 TRACE_FUNCTION ("cc_setup_reattempt()");
166
167 if (cc_data->ti EQ cc_data->setup_reattempt_ti)
168 {
169 PALLOC (est, MMCM_ESTABLISH_REQ); /* T_MMCM_ESTABLISH_REQ */
170 est->ti = cc_data->ti;
171 est->estcs = cc_data->estcs;
172 for_est_req (est);
173
174 cc_data->setup_reattempt_ti = NOT_PRESENT_8BIT;
175 cc_data->progress_desc[cc_data->index_ti] = NOT_PRESENT_8BIT;
176 cc_set_state (M_CC_CS_01);
177 TIMERSTART (T303, T303_VALUE);
178 }
179 }
180
181 /*==== VARIABLES ==================================================*/
182
183 /*==== FUNCTIONS ==================================================*/
184 /*
185 +--------------------------------------------------------------------+
186 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
187 | STATE : code ROUTINE : cc_mncc_disconnect_req |
188 +--------------------------------------------------------------------+
189
190 PURPOSE : Disconnection of call by the mobile side.
191
192 */
193
194 GLOBAL void cc_mncc_disconnect_req (T_MNCC_DISCONNECT_REQ * disc)
195 {
196 GET_INSTANCE_DATA;
197 TRACE_FUNCTION ("cc_mncc_disconnect_req()");
198
199 if ((cc_data->index_ti = srv_convert_ti (disc->ti))
200 EQ NOT_PRESENT_8BIT)
201 {
202 PFREE (disc);
203 return;
204 }
205 if (cc_data->ti EQ cc_data->setup_reattempt_ti)
206 {
207 srv_free_stored_setup ();
208 }
209 switch (cc_data->state[cc_data->index_ti])
210 {
211 case M_CC_CS_03: /* WAIT FOR NW. INFO */
212 case M_CC_CS_05: /* CC ESTABLISHMENT CONFIRMED */
213 case M_CC_CS_06: /* RECALL PRESENT */
214 /* Forget stored CCBS setup */
215 if (cc_data->stored_ccbs_setup NEQ NULL)
216 {
217 PFREE (cc_data->stored_ccbs_setup);
218 cc_data->stored_ccbs_setup = NULL;
219 }
220
221 /* Send a (faked) MNCC_RELEASE_IND to MMI */
222 {
223 PALLOC (rel, MNCC_RELEASE_IND);
224 rel->ti = disc->ti;
225 rel->cause = disc->cause;
226 rel->c_raw_cause = 0;
227 PSENDX (MMI, rel);
228 }
229
230 /* Send RELEASE COMPLETE to network */
231 CCD_START;
232 {
233 MCAST (rel_com, U_RELEASE_COMP);
234 cc_build_release_complete (rel_com, disc->cause);
235 for_release_complete (rel_com);
236 }
237 CCD_END;
238
239 /* Release MM connection */
240 for_rel_req ();
241
242 PFREE (disc);
243
244 /* Stop all running timers */
245 TIMERSTOP (TIMER_CC);
246
247 /* Next state is NULL */
248 cc_set_state (M_CC_CS_0);
249 break;
250
251 case M_CC_CS_01:
252 case CS_101:
253 case CS_261:
254 {
255 TIMERSTOP (TIMER_CC);
256
257 cc_reset_dtmf ();
258
259 {
260 PALLOC (rel, MNCC_RELEASE_IND);
261 rel->ti = disc->ti;
262 rel->cause = disc->cause;
263 rel->c_raw_cause = 0;
264 PSENDX (MMI, rel);
265 }
266
267 for_rel_req ();
268 cc_set_state (M_CC_CS_0);
269 srv_use_stored_prim ();
270 PFREE (disc);
271 }
272 break;
273
274 case M_CC_CS_1:
275 case M_CC_CS_3:
276 case M_CC_CS_4:
277 case M_CC_CS_7:
278 case M_CC_CS_8:
279 case M_CC_CS_9:
280 case M_CC_CS_10:
281 case M_CC_CS_26:
282 TIMERSTOP (TIMER_CC);
283
284 CCD_START;
285 {
286 MCAST (disconnect, U_DISCONNECT);
287
288 cc_build_disconnect (disconnect, disc->cause,
289 &disc->fac_inf, disc->ss_version);
290 cc_set_state (M_CC_CS_11);
291 for_disconnect (disconnect);
292 }
293 CCD_END;
294 TIMERSTART (T305, T305_VALUE);
295 PFREE (disc);
296 break;
297
298 case M_CC_CS_12: /* DISCONNECT INDICATION, this is clear collision here */
299 CCD_START;
300 {
301 MCAST (release, U_RELEASE);
302
303 cc_build_release (release, disc->cause,
304 NULL, MNCC_SS_VER_NOT_PRES);
305 cc_set_state (M_CC_CS_19);
306 for_release (release);
307
308 }
309 CCD_END;
310 TIMERSTART (T308, T308_VALUE);
311 PFREE (disc);
312 break;
313
314 default:
315 PFREE (disc);
316 break;
317
318 }
319 }
320 /*
321 +--------------------------------------------------------------------+
322 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
323 | STATE : code ROUTINE : cc_mncc_reject_req |
324 +--------------------------------------------------------------------+
325
326 PURPOSE : Release of call by the mobile side by sending
327 a RELEASE COMPLETE message.
328
329 */
330
331 GLOBAL void cc_mncc_reject_req (T_MNCC_REJECT_REQ * rej)
332 {
333 GET_INSTANCE_DATA;
334
335 TRACE_FUNCTION ("cc_mncc_reject_req");
336
337 if ((cc_data->index_ti = srv_convert_ti (rej->ti))
338 EQ NOT_PRESENT_8BIT)
339 {
340 PFREE (rej);
341 return;
342 }
343
344 if (cc_data->ti EQ cc_data->setup_reattempt_ti)
345 {
346 srv_free_stored_setup ();
347 }
348
349 switch (cc_data->state[cc_data->index_ti])
350 {
351 case M_CC_CS_03: /* WAIT FOR NW. INFO */
352 case M_CC_CS_05: /* CC ESTABLISHMENT CONFIRMED */
353 case M_CC_CS_06: /* RECALL PRESENT */
354 /* Forget stored CCBS setup */
355 if (cc_data->stored_ccbs_setup NEQ NULL)
356 {
357 PFREE (cc_data->stored_ccbs_setup);
358 cc_data->stored_ccbs_setup = NULL;
359 }
360
361 /* Send RELEASE COMPLETE */
362 CCD_START;
363 {
364 MCAST (rel_com, U_RELEASE_COMP);
365 cc_build_release_complete (rel_com, rej->cause);
366 for_release_complete (rel_com);
367 }
368 CCD_END;
369
370 /* Release MM connection */
371 for_rel_req ();
372
373 PFREE (rej);
374
375 /* Stop all running timers */
376 TIMERSTOP (TIMER_CC);
377
378 /* Next state is NULL */
379 cc_set_state (M_CC_CS_0);
380 break;
381 default:
382 PFREE (rej);
383 break;
384 }
385 }
386
387
388 /*
389 +--------------------------------------------------------------------+
390 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
391 | STATE : code ROUTINE : cc_mncc_release_req |
392 +--------------------------------------------------------------------+
393
394 PURPOSE : Release of call by the mobile side.
395
396 */
397 GLOBAL void cc_mncc_release_req (T_MNCC_RELEASE_REQ * rel)
398 {
399 GET_INSTANCE_DATA;
400
401 TRACE_FUNCTION ("cc_mncc_release_req()");
402
403 if ((cc_data->index_ti = srv_convert_ti (rel->ti))
404 EQ NOT_PRESENT_8BIT)
405 {
406 PFREE (rel);
407 return;
408 }
409
410 if (cc_data->ti EQ cc_data->setup_reattempt_ti)
411 {
412 srv_free_stored_setup ();
413 }
414
415 switch (cc_data->state[cc_data->index_ti])
416 {
417 case M_CC_CS_12: /* DISCONNECT INDICATION */
418
419 CCD_START;
420 {
421 MCAST (release, U_RELEASE);
422
423 cc_build_release (release, rel->cause,
424 &rel->fac_inf, rel->ss_version);
425 cc_set_state (M_CC_CS_19);
426 for_release (release);
427
428 }
429 CCD_END;
430 TIMERSTART (T308, T308_VALUE);
431 PFREE (rel);
432 break;
433
434 default:
435 PFREE (rel);
436 break;
437
438 }
439 }
440
441 /*
442 +--------------------------------------------------------------------+
443 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
444 | STATE : code ROUTINE : cc_disconnect |
445 +--------------------------------------------------------------------+
446
447 PURPOSE : Processing an incoming disconnect message.
448
449 */
450
451 GLOBAL void cc_disconnect (T_D_DISCONNECT * disconnect)
452 {
453 GET_INSTANCE_DATA;
454
455 TRACE_FUNCTION ("cc_disconnect()");
456
457 /* The cause is in DISCONNECT a mandatory IE (given intact message) */
458 TRACE_EVENT_P1 ("DISCONNECT cause: %02x", disconnect->cc_cause.cause);
459
460 EM_CC_DISCONNECT_RECEIVED;
461
462 switch (cc_data->state[cc_data->index_ti])
463 {
464 case M_CC_CS_11: /* DISCONNECT REQUEST, this is clear collision here */
465 CCD_END;
466 CCD_START;
467 {
468 MCAST (release, U_RELEASE);
469
470 TIMERSTOP (TIMER_CC);
471 /* PATCH LE 10.04.00
472 * set disconnect collision flag
473 */
474 cc_data->disc_coll [cc_data->index_ti] = TRUE;
475 /* END PATCH LE 10.04.00 */
476
477 switch (cc_data->error)
478 {
479 case M_CC_CAUSE_INVALID_MAND_INFO:
480 case M_CC_CAUSE_COND_INFO_ELEM:
481 cc_build_release (release, CAUSE_MAKE(DEFBY_STD,
482 ORIGSIDE_MS,
483 MNCC_CC_ORIGINATING_ENTITY,
484 cc_data->error),
485 NULL, MNCC_SS_VER_NOT_PRES);
486 cc_set_state (M_CC_CS_19);
487 for_release (release);
488 TIMERSTART (T308, T308_VALUE);
489 break;
490
491 default:
492 if (disconnect->v_progress)
493 {
494 cc_data->progress_desc[cc_data->index_ti] =
495 disconnect->progress.progress_desc;
496 }
497 cc_build_release (release, CAUSE_MAKE(DEFBY_CONDAT,
498 ORIGSIDE_MS,
499 MNCC_CC_ORIGINATING_ENTITY,
500 NOT_PRESENT_8BIT),
501 NULL, MNCC_SS_VER_NOT_PRES);
502 cc_set_state (M_CC_CS_19);
503 for_release (release);
504 TIMERSTART (T308, T308_VALUE);
505 break;
506 }
507 }
508 CCD_END;
509 break;
510
511 case M_CC_CS_12: /* DISCONNECT INDICATION */
512 case M_CC_CS_19: /* RELEASE REQUEST */
513 /* NULL (M_CC_CS_0) is handled by the formatter */
514 CCD_END;
515 /* Implements Measure# 3 and streamline encoding */
516 cc_send_status (M_CC_CAUSE_MESSAGE_TYPE_INCOMPAT);
517 break;
518
519 default:
520 /* any "normal" state */
521 TIMERSTOP (TIMER_CC);
522
523 switch (cc_data->error)
524 {
525 case M_CC_CAUSE_INVALID_MAND_INFO:
526 case M_CC_CAUSE_COND_INFO_ELEM:
527 CCD_END;
528 CCD_START;
529 {
530 USHORT curr_cause; /* local variable to avoid repeated CAUSE_MAKEs for the same cause */
531
532 MCAST (release, U_RELEASE);
533 PALLOC (disc_ind, MNCC_DISCONNECT_IND);
534
535 disc_ind->ti = cc_data->ti;
536 curr_cause = CAUSE_MAKE(DEFBY_STD,
537 ORIGSIDE_MS,
538 MNCC_CC_ORIGINATING_ENTITY,
539 cc_data->error);
540 disc_ind->cause = curr_cause;
541 /* Setting raw_cause to empty as this is a local release
542 * of MM connection,CC is not receiving any cause value
543 * from Network
544 */
545 disc_ind->c_raw_cause = 0;
546
547 disc_ind->diagnostic = NOT_PRESENT_8BIT;
548 disc_ind->progress_desc = MNCC_PROG_NOT_PRES;
549 /* CQ 23619: get the ss diagnostic >> */
550 disc_ind->ss_diag = MNCC_SS_DIAG_NOT_PROVIDED;
551 /* CQ 23619 << */
552 PSENDX (MMI, disc_ind);
553
554 /* Patch HM 29-Jan-02 >>> */
555 cc_build_facility_ind (MNCC_FAC_IN_DISCONNECT,
556 disconnect->v_facility, &disconnect->facility);
557 /* Patch HM 29-Jan-02 <<< */
558 cc_build_release (release, cc_data->error,
559 NULL, MNCC_SS_VER_NOT_PRES);
560 cc_set_state (M_CC_CS_19);
561 for_release (release);
562 TIMERSTART (T308, T308_VALUE);
563 }
564 CCD_END;
565 break;
566
567 default:
568 if (disconnect->v_progress)
569 {
570 cc_data->progress_desc[cc_data->index_ti] =
571 disconnect->progress.progress_desc;
572 }
573 cc_check_setup_reattempt (&disconnect->cc_cause);
574
575 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
576 {
577 /*
578 * We don't perform setup reattempt, so send disconnect to MMI
579 */
580 USHORT curr_cause; /* local variable to avoid repeated CAUSE_MAKEs for the same cause */
581 PALLOC (disc_ind, MNCC_DISCONNECT_IND); /* T_MNCC_DISCONNECT_IND */
582 disc_ind->ti = cc_data->ti;
583 disc_ind->cause = curr_cause = CAUSE_MAKE(DEFBY_STD,
584 ORIGSIDE_NET,
585 MNCC_CC_ORIGINATING_ENTITY,
586 disconnect->cc_cause.cause);
587 disc_ind->c_raw_cause = cc_build_cause (&disconnect->cc_cause,
588 disc_ind->raw_cause);
589 disc_ind->diagnostic = NOT_PRESENT_8BIT;
590
591 if (disconnect->v_progress)
592 disc_ind->progress_desc = disconnect->progress.progress_desc;
593 else
594 disc_ind->progress_desc = MNCC_PROG_NOT_PRES;
595
596 /* Handle CCBS possible flag */
597 if ((cc_data->call_ctrl_cap.pcp NEQ 0) AND
598 (disconnect->v_allowed_actions NEQ 0) AND
599 (disconnect->allowed_actions.ccbs_act EQ M_CC_CCBS_YES))
600 {
601 /* CCBS indicated as possible by the network */
602 disc_ind->diagnostic = MNCC_DIAG_CCBS_POSSIBLE;
603 }
604 /* CQ 23619: get the ss diagnostic */
605 disc_ind->ss_diag = cc_get_ss_diag(curr_cause, disconnect);
606 /* CQ 23619 << */
607 PSENDX (MMI, disc_ind);
608 /* Patch HM 29-Jan-02 >>> */
609 cc_build_facility_ind (MNCC_FAC_IN_DISCONNECT,
610 disconnect->v_facility, &disconnect->facility);
611 /* Patch HM 29-Jan-02 <<< */
612 }
613 if ((cc_data->ti NEQ cc_data->setup_reattempt_ti) AND
614 (((disconnect->v_progress AND
615 (disconnect->progress.progress_desc EQ M_CC_PROG_INBAND_AVAIL) AND
616 (cc_data->channel_mode != NAS_CHM_SIG_ONLY)))
617 OR
618 ((cc_data->call_ctrl_cap.pcp NEQ 0) AND
619 (disconnect->v_allowed_actions NEQ 0) AND
620 (disconnect->allowed_actions.ccbs_act EQ M_CC_CCBS_YES))))
621 {
622 /*
623 * Hook on tone is generated by the
624 * infrastructure and signalled via TCH OR CCBS is possible
625 */
626 CCD_END;
627 cc_set_state (M_CC_CS_12);
628 }
629 else
630 {
631 CCD_END;
632 CCD_START;
633 {
634 MCAST (release, U_RELEASE);
635
636 /*
637 * Hook on tone is generated internally by the mobile station
638 * and no CCBS possible, the connection is released
639 */
640 cc_build_release (release, CAUSE_MAKE(DEFBY_CONDAT,
641 ORIGSIDE_MS,
642 MNCC_CC_ORIGINATING_ENTITY,
643 NOT_PRESENT_8BIT),
644 NULL, MNCC_SS_VER_NOT_PRES);
645 cc_set_state (M_CC_CS_19);
646 for_release (release);
647 TIMERSTART (T308, T308_VALUE);
648 }
649 CCD_END;
650 }
651 break;
652 }
653 break;
654 }
655 }
656
657 /*
658 +--------------------------------------------------------------------+
659 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
660 | STATE : code ROUTINE : cc_release |
661 +--------------------------------------------------------------------+
662
663 PURPOSE : Processing an incoming release message.
664
665 */
666
667 GLOBAL void cc_release (T_D_RELEASE * release)
668 {
669 GET_INSTANCE_DATA;
670
671 TRACE_FUNCTION ("cc_release()");
672
673 if (release->cc_cause.v_cause)
674 {
675 /* The cause is in RELEASE an optional IE */
676 TRACE_EVENT_P1 ("RELEASE cause: %02x", release->cc_cause.cause);
677 }
678 else
679 {
680 TRACE_EVENT ("RELEASE cause: --");
681 }
682
683 switch (cc_data->state[cc_data->index_ti])
684 {
685 /*
686 * M_CC_CS_0 is handled by the formatter
687 */
688 case M_CC_CS_19: /* Release Request */
689 {
690 cc_reset_dtmf ();
691 /* PATCH LE 10.04.00
692 * in disconnect collision case send
693 * MNCC_RELEASE_IND instead of MNCC_RELEASE_CNF
694 .... */
695 TIMERSTOP (TIMER_CC);
696 if (cc_data->disc_coll [cc_data->index_ti])
697 {
698 /* Implements Measure# 8 */
699 cc_mncc_release_ind ((T_PRIM *)D2P(release));
700 }
701 else
702 {
703 /* Implements Measure# 9 */
704 cc_mncc_release_cnf ((T_PRIM *)D2P(release));
705 }
706 // END PATCH LE 10.04.00
707
708 for_rel_req ();
709 cc_set_state (M_CC_CS_0);
710 /* END PATCH LE 10.04.00 */
711 CCD_END;
712 break;
713 }
714
715 case M_CC_CS_1: /* call initiated */
716 case M_CC_CS_3: /* mobile originating call proceeding */
717 cc_check_setup_reattempt (&release->cc_cause);
718 /*FALLTHROUGH*/ /*lint -fallthrough*/
719 default:
720 cc_reset_dtmf (); /* China change HM 11.07.00 */
721 CCD_END;
722 CCD_START;
723 {
724 MCAST (rel_com, U_RELEASE_COMP);
725
726 TIMERSTOP (TIMER_CC);
727 switch (cc_data->error)
728 {
729 case M_CC_CAUSE_INVALID_MAND_INFO:
730 case M_CC_CAUSE_COND_INFO_ELEM:
731 {
732 /* local variable to avoid repeated CAUSE_MAKEs
733 for the same cause */
734 USHORT curr_cause;
735 curr_cause = CAUSE_MAKE(DEFBY_STD,
736 ORIGSIDE_MS,
737 MNCC_CC_ORIGINATING_ENTITY,
738 cc_data->error);
739
740 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
741 {
742 PALLOC (rel_ind, MNCC_RELEASE_IND);
743 rel_ind->ti = cc_data->ti;
744 rel_ind->cause = curr_cause;
745 rel_ind->c_raw_cause = 0;
746 PSENDX (MMI, rel_ind);
747 }
748 cc_build_release_complete (rel_com, curr_cause);
749 }
750 break;
751
752 default:
753 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
754 {
755 /* Implements Measure# 8 */
756 cc_mncc_release_ind ((T_PRIM *)D2P(release));
757 }
758 cc_build_release_complete (rel_com, CAUSE_MAKE(DEFBY_CONDAT,
759 ORIGSIDE_MS,
760 MNCC_CC_ORIGINATING_ENTITY,
761 NOT_PRESENT_8BIT));
762 break;
763 }
764
765 for_release_complete (rel_com);
766 }
767 CCD_END;
768 for_rel_req ();
769 cc_set_state (M_CC_CS_0);
770 cc_setup_reattempt ();
771 break;
772 }
773 }
774
775 /*
776 +--------------------------------------------------------------------+
777 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
778 | STATE : code ROUTINE : cc_release_complete |
779 +--------------------------------------------------------------------+
780
781 PURPOSE : Processing an incoming release complete message.
782
783 */
784
785 GLOBAL void cc_release_complete (T_D_RELEASE_COMP * rel_com)
786 {
787 GET_INSTANCE_DATA;
788
789 TRACE_FUNCTION ("cc_release_complete()");
790
791 if (rel_com->cc_cause.v_cause)
792 {
793 /* The cause is in RELEASE COMPLETE an optional IE */
794 TRACE_EVENT_P1 ("RELEASE COMPLETE cause: %02x", rel_com->cc_cause.cause);
795 }
796 else
797 {
798 TRACE_EVENT ("RELEASE COMPLETE cause: --");
799 }
800
801 EM_CC_RELEASE_COMPLETE_RECEIVED;
802
803 switch (cc_data->state[cc_data->index_ti])
804 {
805 case M_CC_CS_0: /* NULL */
806 CCD_END;
807 for_rel_req ();
808 break;
809
810 case M_CC_CS_03: /* WAIT FOR NETWORK INFO*/
811 /* Stop all running CC timers */
812 TIMERSTOP (TIMER_CC);
813
814 /* Inform MMI */
815 {
816 PALLOC (release, MNCC_RELEASE_IND);
817 release->ti = cc_data->ti;
818 if (rel_com->v_cc_cause AND rel_com->cc_cause.v_cause)
819 {
820 release->cause = CAUSE_MAKE(DEFBY_STD,
821 ORIGSIDE_NET,
822 MNCC_CC_ORIGINATING_ENTITY,
823 rel_com->cc_cause.cause);
824 release->c_raw_cause = cc_build_cause (&rel_com->cc_cause,
825 release->raw_cause);
826 }
827 else
828 {
829 release->cause = CAUSE_MAKE(DEFBY_CONDAT,
830 ORIGSIDE_NET,
831 MNCC_CC_ORIGINATING_ENTITY,
832 NOT_PRESENT_8BIT);
833 release->c_raw_cause = 0;
834 }
835 PSENDX (MMI, release);
836 }
837
838 CCD_END;
839
840 /* Release MM connection */
841 for_rel_req ();
842
843 /* Next state is NULL */
844 cc_set_state (M_CC_CS_0);
845 break;
846
847 case M_CC_CS_05: /* CC ESTABLISHMENT CONFIRMED */
848 case M_CC_CS_06: /* RECALL PRESENT */
849 /* Forget stored CCBS setup */
850 PFREE (cc_data->stored_ccbs_setup);
851 cc_data->stored_ccbs_setup = NULL;
852
853 /* Stop all running CC timers */
854 TIMERSTOP (TIMER_CC);
855
856 /* Inform MMI */
857 {
858 PALLOC (release, MNCC_RELEASE_IND);
859 release->ti = cc_data->ti;
860 if (rel_com->v_cc_cause AND rel_com->cc_cause.v_cause)
861 {
862 release->cause = CAUSE_MAKE(DEFBY_STD,
863 ORIGSIDE_NET,
864 MNCC_CC_ORIGINATING_ENTITY,
865 rel_com->cc_cause.cause);
866 release->c_raw_cause = cc_build_cause (&rel_com->cc_cause,
867 release->raw_cause);
868 }
869 else
870 {
871 release->cause = CAUSE_MAKE(DEFBY_CONDAT,
872 ORIGSIDE_NET,
873 MNCC_CC_ORIGINATING_ENTITY,
874 NOT_PRESENT_8BIT);
875 release->c_raw_cause = 0;
876 }
877 PSENDX (MMI, release);
878 }
879
880 CCD_END;
881
882 /* Release MM connection */
883 for_rel_req ();
884
885 /* Next state is NULL */
886 cc_set_state (M_CC_CS_0);
887 break;
888
889 case M_CC_CS_19: /* RELEASE REQUEST */
890 cc_reset_dtmf ();
891 /* PATCH LE 10.04.00
892 * in disconnect collision case send
893 * MNCC_RELEASE_IND instead of MNCC_RELEASE_CNF
894 */
895 TIMERSTOP (TIMER_CC);
896
897 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
898 {
899 /* Inform MMI only if no setup reattempt for this ti */
900 if (cc_data->disc_coll [cc_data->index_ti])
901 {
902 /* Implements Measure# 9 */
903 cc_mncc_release_ind ((T_PRIM *)D2P(rel_com));
904 }
905 else
906 {
907 /* Implements Measure# 9 */
908 cc_mncc_release_cnf ((T_PRIM *)D2P(rel_com));
909 }
910 /* END PATCH LE 10.04.00 */
911
912 }
913
914 for_rel_req ();
915 cc_set_state (M_CC_CS_0);
916 CCD_END;
917 cc_setup_reattempt ();
918 break;
919
920 case M_CC_CS_1: /* call initiated */
921 case M_CC_CS_3: /* mobile originating call proceeding */
922 cc_check_setup_reattempt (&rel_com->cc_cause);
923 /*FALLTHROUGH*/ /*lint -fallthrough*/
924 default:
925 cc_reset_dtmf (); /* China change HM 11.07.00 */
926 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
927 {
928 /* Implements Measure# 10 */
929 cc_mncc_release_ind ((T_PRIM *)D2P(rel_com));
930 }
931 for_rel_req ();
932 CCD_END;
933 cc_set_state (M_CC_CS_0);
934 cc_setup_reattempt ();
935 break;
936 }
937 }
938
939 /*
940 +--------------------------------------------------------------------+
941 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
942 | STATE : code ROUTINE : cc_rel_ind |
943 +--------------------------------------------------------------------+
944
945 PURPOSE : Processing of an incoming release indication from
946 mobility management.
947
948 */
949
950 GLOBAL void cc_rel_ind (USHORT cause)
951 {
952 GET_INSTANCE_DATA;
953
954 TRACE_FUNCTION ("cc_rel_ind()");
955
956 switch (cc_data->state[cc_data->index_ti])
957 {
958 case M_CC_CS_0:
959 break;
960
961 case M_CC_CS_05: /* CC ESTABLISHMENT CONFIRMED */
962 case M_CC_CS_06: /* RECALL PRESENT */
963 /* Stop all timers */
964 TIMERSTOP (TIMER_CC);
965
966 /* Forget stored CCBS setup message */
967 PFREE (cc_data->stored_ccbs_setup);
968 cc_data->stored_ccbs_setup = NULL;
969
970 /* Inform MMI */
971 {
972 PALLOC (release, MNCC_RELEASE_IND);
973 release->ti = cc_data->ti;
974 release->cause = cause; /* provide cause from lower layers transparently to higher layers */
975 release->c_raw_cause = 0;
976 PSENDX (MMI, release);
977 }
978
979 cc_set_state (M_CC_CS_0);
980 srv_use_stored_prim ();
981 break;
982
983 case CS_101: /* Re-establishment request in state M_CC_CS_10 */\
984 case CS_261: /* Re-establishment request in state CS_26 */\
985 EM_CC_REESTABLISHED_FAILED;
986 /*FALLTHROUGH*/ /*lint -fallthrough*/
987
988 default:
989 cc_reset_dtmf (); /* China change HM 11.07.00 */
990 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
991 {
992 PALLOC (rej_ind, MNCC_REJECT_IND);
993 rej_ind->ti = cc_data->ti;
994 rej_ind->cause = cause;
995 PSENDX (MMI, rej_ind);
996 }
997
998 cc_set_state (M_CC_CS_0);
999 if (cc_data->ti EQ cc_data->setup_reattempt_ti)
1000 {
1001 cc_setup_reattempt();
1002 }
1003 else
1004 {
1005 srv_use_stored_prim ();
1006 }
1007 break;
1008 }
1009 }
1010
1011 /*
1012 +--------------------------------------------------------------------+
1013 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
1014 | STATE : code ROUTINE : cc_err_ind |
1015 +--------------------------------------------------------------------+
1016
1017 PURPOSE : Processing of an incoming error indication from
1018 mobility management.
1019
1020 */
1021
1022 GLOBAL void cc_err_ind (T_MMCM_ERROR_IND * err_ind)
1023 {
1024 GET_INSTANCE_DATA;
1025
1026 TRACE_FUNCTION ("cc_err_ind()");
1027
1028 switch (cc_data->state[cc_data->index_ti])
1029 {
1030 case M_CC_CS_0:
1031 break;
1032
1033 case M_CC_CS_10:
1034 {
1035 /* Implements Measure# 41 */
1036 cc_mncc_sync_ind(err_ind->ti, CS_101);
1037
1038 EM_CC_REESTABLISHED_STARTED;
1039
1040 }
1041 break;
1042
1043 case M_CC_CS_26:
1044 {
1045 /* Implements Measure# 41 */
1046 cc_mncc_sync_ind(err_ind->ti, CS_261);
1047
1048 EM_CC_REESTABLISHED_STARTED;
1049
1050 }
1051 break;
1052
1053 default:
1054 cc_reset_dtmf ();
1055 if (cc_data->ti NEQ cc_data->setup_reattempt_ti)
1056 {
1057 PALLOC (rel_ind, MNCC_RELEASE_IND);
1058 rel_ind->cause = err_ind->cause;
1059 rel_ind->ti = cc_data->ti;
1060 rel_ind->c_raw_cause = 0;
1061 PSENDX (MMI, rel_ind);
1062 }
1063 cc_set_state (M_CC_CS_0);
1064 for_rel_req ();
1065 cc_setup_reattempt ();
1066 break;
1067 }
1068 PFREE (err_ind);
1069 }
1070 /* Implements Measure# 8 */
1071 /*
1072 +--------------------------------------------------------------------+
1073 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
1074 | STATE : code ROUTINE : cc_mncc_release_ind |
1075 +--------------------------------------------------------------------+
1076
1077 PURPOSE : send mncc_release_ind
1078
1079 */
1080
1081 LOCAL void cc_mncc_release_ind (T_PRIM * prim)
1082 {
1083 GET_INSTANCE_DATA;
1084 UBYTE v_cc_cause;
1085 T_M_CC_cc_cause *cc_cause;
1086
1087 TRACE_FUNCTION ("cc_mncc_release_ind()");
1088
1089 if (prim->custom.opc EQ D_RELEASE)
1090 {
1091 v_cc_cause = ((T_D_RELEASE *)P2D(prim))->v_cc_cause;
1092 cc_cause = &((T_D_RELEASE *)P2D(prim))->cc_cause;
1093 cc_build_facility_ind (MNCC_FAC_IN_RELEASE,
1094 ((T_D_RELEASE *)P2D(prim))->v_facility,
1095 &((T_D_RELEASE *)P2D(prim))->facility);
1096 }
1097 else
1098 {
1099 v_cc_cause = ((T_D_RELEASE_COMP *)P2D(prim))->v_cc_cause;
1100 cc_cause = &((T_D_RELEASE_COMP *)P2D(prim))->cc_cause;
1101 cc_build_facility_ind (MNCC_FAC_IN_RELEASE_COMP,
1102 ((T_D_RELEASE_COMP *)P2D(prim))->v_facility,
1103 &((T_D_RELEASE_COMP *)P2D(prim))->facility);
1104 }
1105
1106 /* Patch HM 29-Jan-02 <<< */
1107 {
1108 PALLOC (rel_ind, MNCC_RELEASE_IND);
1109 rel_ind->ti = cc_data->ti;
1110 if (v_cc_cause)
1111 {
1112 rel_ind->cause = CAUSE_MAKE(DEFBY_STD,
1113 ORIGSIDE_NET,
1114 MNCC_CC_ORIGINATING_ENTITY,
1115 cc_cause->cause);
1116 rel_ind->c_raw_cause = cc_build_cause (cc_cause,
1117 rel_ind->raw_cause);
1118 }
1119 else
1120 {
1121 rel_ind->cause = CAUSE_MAKE(DEFBY_CONDAT,
1122 ORIGSIDE_NET,
1123 MNCC_CC_ORIGINATING_ENTITY,
1124 NOT_PRESENT_8BIT);
1125 /* Setting raw_cause to empty as this is a local release
1126 * of MM connection,CC is not receiving any cause value
1127 * from Network
1128 */
1129 rel_ind->c_raw_cause = 0;
1130 }
1131 PSENDX (MMI, rel_ind);
1132 }
1133 }
1134
1135 /* Implements Measure# 9 */
1136 /*
1137 +--------------------------------------------------------------------+
1138 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
1139 | STATE : code ROUTINE : cc_mncc_release_cnf |
1140 +--------------------------------------------------------------------+
1141
1142 PURPOSE : send mncc_release_cnf
1143
1144 */
1145
1146 LOCAL void cc_mncc_release_cnf (T_PRIM * prim)
1147 {
1148 GET_INSTANCE_DATA;
1149 UBYTE v_cc_cause;
1150 T_M_CC_cc_cause *cc_cause;
1151
1152 TRACE_FUNCTION ("cc_mncc_release_cnf()");
1153
1154 if (prim->custom.opc EQ D_RELEASE)
1155 {
1156 v_cc_cause = ((T_D_RELEASE *)P2D(prim))->v_cc_cause;
1157 cc_cause = &((T_D_RELEASE *)P2D(prim))->cc_cause;
1158 cc_build_facility_ind (MNCC_FAC_IN_RELEASE_COMP, /* A little bit dirty */
1159 ((T_D_RELEASE *)P2D(prim))->v_facility,
1160 &((T_D_RELEASE *)P2D(prim))->facility);
1161 }
1162 else
1163 {
1164 v_cc_cause = ((T_D_RELEASE_COMP *)P2D(prim))->v_cc_cause;
1165 cc_cause = &((T_D_RELEASE_COMP *)P2D(prim))->cc_cause;
1166 cc_build_facility_ind (MNCC_FAC_IN_RELEASE_COMP,
1167 ((T_D_RELEASE_COMP *)P2D(prim))->v_facility,
1168 &((T_D_RELEASE_COMP *)P2D(prim))->facility);
1169 }
1170
1171 /* Patch HM 29-Jan-02 <<< */
1172 {
1173 PALLOC (rel_cnf, MNCC_RELEASE_CNF);
1174 rel_cnf->ti = cc_data->ti;
1175 if (v_cc_cause)
1176 {
1177 rel_cnf->cause = CAUSE_MAKE(DEFBY_STD,
1178 ORIGSIDE_NET,
1179 MNCC_CC_ORIGINATING_ENTITY,
1180 cc_cause->cause);
1181 rel_cnf->c_raw_cause = cc_build_cause (cc_cause,
1182 rel_cnf->raw_cause);
1183 }
1184 else
1185 {
1186 rel_cnf->cause = CAUSE_MAKE(DEFBY_CONDAT,
1187 ORIGSIDE_NET,
1188 MNCC_CC_ORIGINATING_ENTITY,
1189 NOT_PRESENT_8BIT);
1190 /* Setting raw_cause to empty as this is a local release
1191 * of MM connection,CC is not receiving any cause value
1192 * from Network
1193 */
1194 rel_cnf->c_raw_cause = 0;
1195 }
1196 PSENDX (MMI, rel_cnf);
1197 }
1198 }
1199
1200
1201 /* Implements Measure# 41 */
1202 /*
1203 +--------------------------------------------------------------------+
1204 | PROJECT : GSM-PS (6147) MODULE : CC_REL |
1205 | STATE : code ROUTINE : cc_mncc_sync_ind |
1206 +--------------------------------------------------------------------+
1207
1208 PURPOSE : send cc_mncc_sync_ind
1209
1210 */
1211
1212 LOCAL void cc_mncc_sync_ind (UBYTE ti, UBYTE new_state)
1213 {
1214 TRACE_FUNCTION ("cc_mncc_sync_ind()");
1215 {
1216 PALLOC (sync_ind, MNCC_SYNC_IND); /* T_MNCC_SYNC_IND */
1217
1218 sync_ind->ti = ti;
1219 sync_ind->cause = MNCC_CAUSE_REEST_STARTED;
1220 sync_ind->ch_info.ch_mode=NOT_PRESENT_8BIT;
1221 sync_ind->ch_info.ch_type=NOT_PRESENT_8BIT;
1222
1223 PSENDX (MMI, sync_ind);
1224
1225 for_reest_req ();
1226 cc_set_state (new_state);
1227 }
1228
1229 }
1230 #endif