]> git.ipfire.org Git - thirdparty/freeswitch.git/commitdiff
freetdm: ss7 - bug fix for call-resume and call-suspend handling, added isup interfac...
authorKonrad Hammel <konrad@sangoma.com>
Wed, 20 Oct 2010 14:14:35 +0000 (10:14 -0400)
committerKonrad Hammel <konrad@sangoma.com>
Wed, 20 Oct 2010 17:58:29 +0000 (13:58 -0400)
libs/freetdm/src/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_handle.c
libs/freetdm/src/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_in.c
libs/freetdm/src/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_main.c
libs/freetdm/src/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_main.h
libs/freetdm/src/ftmod/ftmod_sangoma_ss7/ftmod_sangoma_ss7_xml.c

index ac58abd412f24b3712e76b0d30d43a92da116f5a..807b3b62c786f2906727462b95541340f89de302 100644 (file)
@@ -51,6 +51,8 @@ ftdm_status_t handle_dat_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
 ftdm_status_t handle_fac_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 ftdm_status_t handle_fac_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 ftdm_status_t handle_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit);
+ftdm_status_t handle_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt);
+ftdm_status_t handle_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt);
 ftdm_status_t handle_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt);
 
 ftdm_status_t handle_reattempt(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt);
@@ -298,8 +300,21 @@ ftdm_status_t handle_con_sta(uint32_t suInstId, uint32_t spInstId, uint32_t circ
                        /* need to grab the sp instance id */ 
                        sngss7_info->spInstId = spInstId;
 
-                       /* go to PROGRESS */
-                       ftdm_set_state_locked(ftdmchan, FTDM_CHANNEL_STATE_PROGRESS);
+                       if ((siCnStEvnt->optBckCalInd.eh.pres) && 
+                               (siCnStEvnt->optBckCalInd.inbndInfoInd.pres)) {
+
+                               if (siCnStEvnt->optBckCalInd.inbndInfoInd.val) {
+                                       /* go to PROGRESS_MEDIA */
+                                       ftdm_set_state_locked(ftdmchan, FTDM_CHANNEL_STATE_PROGRESS_MEDIA);
+                               } else {
+                                       /* go to PROGRESS */
+                                       ftdm_set_state_locked(ftdmchan, FTDM_CHANNEL_STATE_PROGRESS);
+                               } /* if (inband) */
+                       } else {
+                               /* go to PROGRESS_MEDIA */
+                               ftdm_set_state_locked(ftdmchan, FTDM_CHANNEL_STATE_PROGRESS_MEDIA);
+                       }
+                       
                break;
                /**********************************************************************/
                default:        /* incorrect state...reset the CIC */
@@ -733,6 +748,60 @@ ftdm_status_t handle_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t cir
        return FTDM_SUCCESS;
 }
 
+/******************************************************************************/
+ftdm_status_t handle_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt)
+{
+       SS7_FUNC_TRACE_ENTER(__FUNCTION__);
+       
+       sngss7_chan_data_t  *sngss7_info ;
+       ftdm_channel_t    *ftdmchan;
+
+       /* get the ftdmchan and ss7_chan_data from the circuit */
+       if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
+               SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return FTDM_FAIL;
+       }
+
+       /* lock the channel */
+       ftdm_mutex_lock(ftdmchan->mutex);
+
+       SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Rx Call-Suspend msg\n", sngss7_info->circuit->cic);
+
+       /* unlock the channel */
+       ftdm_mutex_unlock(ftdmchan->mutex);
+
+       SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+       return FTDM_SUCCESS;
+}
+
+/******************************************************************************/
+ftdm_status_t handle_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt)
+{
+       SS7_FUNC_TRACE_ENTER(__FUNCTION__);
+       
+       sngss7_chan_data_t  *sngss7_info ;
+       ftdm_channel_t    *ftdmchan;
+
+       /* get the ftdmchan and ss7_chan_data from the circuit */
+       if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
+               SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return FTDM_FAIL;
+       }
+
+       /* lock the channel */
+       ftdm_mutex_lock(ftdmchan->mutex);
+
+       SS7_INFO_CHAN(ftdmchan,"[CIC:%d]Rx Call-Resume msg\n", sngss7_info->circuit->cic);
+
+       /* unlock the channel */
+       ftdm_mutex_unlock(ftdmchan->mutex);
+
+       SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+       return FTDM_SUCCESS;
+}
+
 /******************************************************************************/
 ftdm_status_t handle_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt)
 {
index 34893cf5aaff3cd40eba285ef2ac5c6888ec5f33..06fae0cd3796b400413f9356b2a1841fc4576833 100644 (file)
@@ -52,7 +52,9 @@ void sngss7_dat_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiIn
 void sngss7_fac_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 void sngss7_fac_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 void sngss7_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit);
-
+void sngss7_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt);
+void sngss7_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt);
+void sngss7_ssp_sta_cfm(uint32_t infId);
 /******************************************************************************/
 
 /* FUNCTIONS ******************************************************************/
@@ -442,7 +444,127 @@ void sngss7_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint
 }
 
 /******************************************************************************/
+void sngss7_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt)
+{
+       SS7_FUNC_TRACE_ENTER(__FUNCTION__);
+
+       sngss7_chan_data_t      *sngss7_info = NULL;
+       ftdm_channel_t          *ftdmchan = NULL;
+       sngss7_event_data_t     *sngss7_event = NULL;
+
+       /* get the ftdmchan and ss7_chan_data from the circuit */
+       if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
+               SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+
+       /* initalize the sngss7_event */
+       sngss7_event = ftdm_malloc(sizeof(*sngss7_event));
+       if (sngss7_event == NULL) {
+               SS7_ERROR("Failed to allocate memory for sngss7_event!\n");
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+       memset(sngss7_event, 0x0, sizeof(*sngss7_event));
+
+       /* fill in the sngss7_event struct */
+       sngss7_event->spInstId  = spInstId;
+       sngss7_event->suInstId  = suInstId;
+       sngss7_event->circuit   = circuit;
+       sngss7_event->event_id  = SNGSS7_SUSP_IND_EVENT;
+       if (siSuspEvnt != NULL) {
+               memcpy(&sngss7_event->event.siSuspEvnt, siSuspEvnt, sizeof(*siSuspEvnt));
+       }
+
+       /* enqueue this event */
+       ftdm_queue_enqueue(((sngss7_span_data_t*)sngss7_info->ftdmchan->span->mod_data)->event_queue, sngss7_event);
+
+       SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+
+}
+
+/******************************************************************************/
+void sngss7_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt)
+{
+       SS7_FUNC_TRACE_ENTER(__FUNCTION__);
 
+       sngss7_chan_data_t      *sngss7_info = NULL;
+       ftdm_channel_t          *ftdmchan = NULL;
+       sngss7_event_data_t     *sngss7_event = NULL;
+
+       /* get the ftdmchan and ss7_chan_data from the circuit */
+       if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
+               SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+
+       /* initalize the sngss7_event */
+       sngss7_event = ftdm_malloc(sizeof(*sngss7_event));
+       if (sngss7_event == NULL) {
+               SS7_ERROR("Failed to allocate memory for sngss7_event!\n");
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+       memset(sngss7_event, 0x0, sizeof(*sngss7_event));
+
+       /* fill in the sngss7_event struct */
+       sngss7_event->spInstId  = spInstId;
+       sngss7_event->suInstId  = suInstId;
+       sngss7_event->circuit   = circuit;
+       sngss7_event->event_id  = SNGSS7_RESM_IND_EVENT;
+       if (siResmEvnt != NULL) {
+               memcpy(&sngss7_event->event.siResmEvnt, siResmEvnt, sizeof(*siResmEvnt));
+       }
+
+       /* enqueue this event */
+       ftdm_queue_enqueue(((sngss7_span_data_t*)sngss7_info->ftdmchan->span->mod_data)->event_queue, sngss7_event);
+
+       SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+
+}
+
+/******************************************************************************/
+void sngss7_ssp_sta_cfm(uint32_t infId)
+{
+       SS7_FUNC_TRACE_ENTER(__FUNCTION__);
+#if 0
+       sngss7_chan_data_t      *sngss7_info = NULL;
+       ftdm_channel_t          *ftdmchan = NULL;
+       sngss7_event_data_t     *sngss7_event = NULL;
+
+       /* get the ftdmchan and ss7_chan_data from the circuit */
+       if (extract_chan_data(circuit, &sngss7_info, &ftdmchan)) {
+               SS7_ERROR("Failed to extract channel data for circuit = %d!\n", circuit);
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+
+       /* initalize the sngss7_event */
+       sngss7_event = ftdm_malloc(sizeof(*sngss7_event));
+       if (sngss7_event == NULL) {
+               SS7_ERROR("Failed to allocate memory for sngss7_event!\n");
+               SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+               return;
+       }
+       memset(sngss7_event, 0x0, sizeof(*sngss7_event));
+
+       /* fill in the sngss7_event struct */
+       sngss7_event->spInstId  = spInstId;
+       sngss7_event->suInstId  = suInstId;
+       sngss7_event->circuit   = circuit;
+       sngss7_event->event_id  = SNGSS7_RESM_IND_EVENT;
+       if (siSuspEvnt != NULL) {
+               memcpy(&sngss7_event->event.siResmEvnt, siResmEvnt, sizeof(*siResmEvnt));
+       }
+
+       /* enqueue this event */
+       ftdm_queue_enqueue(((sngss7_span_data_t*)sngss7_info->ftdmchan->span->mod_data)->event_queue, sngss7_event);
+#endif
+       SS7_FUNC_TRACE_EXIT(__FUNCTION__);
+
+}
 /******************************************************************************/
 /* For Emacs:
  * Local Variables:
index 2b267e716cb480492e5f73bddaa992f52dffbf13..587242d94e285b72e84972a017927324618fcb2b 100644 (file)
@@ -208,7 +208,7 @@ ftdm_state_map_t sangoma_ss7_state_map = {
        {FTDM_CHANNEL_STATE_SUSPENDED, FTDM_CHANNEL_STATE_RESTART,
         FTDM_CHANNEL_STATE_CANCEL, FTDM_CHANNEL_STATE_TERMINATING,
         FTDM_CHANNEL_STATE_HANGUP, FTDM_CHANNEL_STATE_PROGRESS,
-        FTDM_CHANNEL_STATE_UP, FTDM_END}
+        FTDM_CHANNEL_STATE_PROGRESS_MEDIA ,FTDM_CHANNEL_STATE_UP, FTDM_END}
        },
    {
        ZSD_OUTBOUND,
@@ -448,6 +448,17 @@ static void ftdm_sangoma_ss7_process_stack_event (sngss7_event_data_t *sngss7_ev
                handle_sta_ind(sngss7_event->suInstId, sngss7_event->spInstId, sngss7_event->circuit, sngss7_event->globalFlg, sngss7_event->evntType,  &sngss7_event->event.siStaEvnt);
                break;
        /**************************************************************************/
+       case (SNGSS7_SUSP_IND_EVENT):
+               handle_susp_ind(sngss7_event->suInstId, sngss7_event->spInstId, sngss7_event->circuit,  &sngss7_event->event.siSuspEvnt);
+               break;
+       /**************************************************************************/
+       case (SNGSS7_RESM_IND_EVENT):
+               handle_resm_ind(sngss7_event->suInstId, sngss7_event->spInstId, sngss7_event->circuit,  &sngss7_event->event.siResmEvnt);
+               break;
+       /**************************************************************************/
+       case (SNGSS7_SSP_STA_CFM_EVENT):
+               break;
+       /**************************************************************************/
        default:
                SS7_ERROR("Unknown Event Id!\n");
                break;
@@ -469,6 +480,7 @@ static void ftdm_sangoma_ss7_process_stack_event (sngss7_event_data_t *sngss7_ev
 void ftdm_sangoma_ss7_process_state_change (ftdm_channel_t * ftdmchan)
 {
        sngss7_chan_data_t      *sngss7_info = ftdmchan->call_data;
+       sng_isup_inf_t          *isup_intf = NULL; 
        int                             i = 0;
        ftdm_sigmsg_t           sigev;
 
@@ -589,17 +601,16 @@ void ftdm_sangoma_ss7_process_state_change (ftdm_channel_t * ftdmchan)
                }
 
                /*check if the channel is inbound or outbound */
-               if (ftdm_test_flag (ftdmchan, FTDM_CHANNEL_OUTBOUND))   {
+               if (ftdm_test_flag (ftdmchan, FTDM_CHANNEL_OUTBOUND)) {
                        /*OUTBOUND...so we were told by the line of this so noifiy the user */
                        sigev.event_id = FTDM_SIGEVENT_PROGRESS;
                        ftdm_span_send_signal (ftdmchan->span, &sigev);
 
+                       /* move to progress media  */
                        ftdm_set_state_locked (ftdmchan, FTDM_CHANNEL_STATE_PROGRESS_MEDIA);
                } else {
                        /* inbound call so we need to send out ACM */
-                       ft_to_sngss7_acm (ftdmchan);
-
-                       ftdm_set_state_locked (ftdmchan, FTDM_CHANNEL_STATE_PROGRESS_MEDIA);
+                       ft_to_sngss7_acm(ftdmchan);
                }
 
                break;
@@ -611,6 +622,13 @@ void ftdm_sangoma_ss7_process_state_change (ftdm_channel_t * ftdmchan)
                        break;
                }
 
+               if (ftdm_test_flag (ftdmchan, FTDM_CHANNEL_OUTBOUND)) {
+                       /* inform the user there is media avai */
+                       sigev.event_id = FTDM_SIGEVENT_PROGRESS_MEDIA;
+                       ftdm_span_send_signal (ftdmchan->span, &sigev);
+               }
+                       
+
                /* nothing to do at this time */
                break;
        /**************************************************************************/
@@ -1155,11 +1173,15 @@ suspend_goto_restart:
                ftdm_set_state_locked (ftdmchan, FTDM_CHANNEL_STATE_RESTART);
                break;
 
-/**************************************************************************/
+       /**************************************************************************/
        case FTDM_CHANNEL_STATE_IN_LOOP:        /* COT test */
 
-               /* send the lpa */
-               ft_to_sngss7_lpa (ftdmchan);
+               isup_intf = &g_ftdm_sngss7_data.cfg.isupIntf[sngss7_info->circuit->infId];
+
+               if (sngss7_test_options(isup_intf, SNGSS7_LPA_FOR_COT)) {
+                       /* send the lpa */
+                       ft_to_sngss7_lpa (ftdmchan);
+               } 
 
                break;
        /**************************************************************************/
@@ -1507,9 +1529,9 @@ static FIO_SIG_LOAD_FUNCTION(ftdm_sangoma_ss7_init)
        sng_event.cc.sng_fac_cfm = sngss7_fac_cfm;
        sng_event.cc.sng_sta_ind = sngss7_sta_ind;
        sng_event.cc.sng_umsg_ind = sngss7_umsg_ind;
-       sng_event.cc.sng_susp_ind = NULL;
-       sng_event.cc.sng_resm_ind = NULL;
-       sng_event.cc.sng_ssp_sta_cfm = NULL;
+       sng_event.cc.sng_susp_ind = sngss7_susp_ind;
+       sng_event.cc.sng_resm_ind = sngss7_resm_ind;
+       sng_event.cc.sng_ssp_sta_cfm = sngss7_ssp_sta_cfm;
 
        sng_event.sm.sng_log = handle_sng_log;
        sng_event.sm.sng_mtp1_alarm = handle_sng_mtp1_alarm;
index f41664a5b6756e39a97f4a20ecd04a15798dc9f2..27833cb2a210c5c3e8b33d8668fde069fc2ec31a 100644 (file)
@@ -70,7 +70,10 @@ typedef enum {
        SNGSS7_FAC_IND_EVENT,
        SNGSS7_FAC_CFM_EVENT,
        SNGSS7_UMSG_IND_EVENT,
-       SNGSS7_STA_IND_EVENT
+       SNGSS7_STA_IND_EVENT,
+       SNGSS7_SUSP_IND_EVENT,
+       SNGSS7_RESM_IND_EVENT,
+       SNGSS7_SSP_STA_CFM_EVENT
 } sng_event_type_t;
 
 typedef enum {
@@ -86,7 +89,8 @@ typedef enum {
 } sng_flag_t;
 
 typedef enum {
-       SNGSS7_ACM_OBCI_BITA    = (1 << 0)      /* in-band indication */
+       SNGSS7_LPA_FOR_COT              = (1 << 0),     /* send LPA when COT arrives */
+       SNGSS7_ACM_OBCI_BITA    = (1 << 10)     /* in-band indication */
 } sng_intf_options_t;
 
 typedef enum {
@@ -397,6 +401,8 @@ typedef struct sngss7_event_data
                SiInfoEvnt      siInfoEvnt;
                SiFacEvnt       siFacEvnt;
                SiStaEvnt       siStaEvnt;
+               SiSuspEvnt      siSuspEvnt;
+               SiResmEvnt      siResmEvnt;
        } event;
 } sngss7_event_data_t;
 
@@ -526,6 +532,9 @@ void sngss7_fac_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint
 void sngss7_fac_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 void sngss7_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt);
 void sngss7_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit);
+void sngss7_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt);
+void sngss7_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt);
+void sngss7_ssp_sta_cfm(uint32_t infId);
 
 /* in ftmod_sangoma_ss7_handle.c */
 ftdm_status_t handle_con_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiConEvnt *siConEvnt);
@@ -537,6 +546,8 @@ ftdm_status_t handle_dat_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circ
 ftdm_status_t handle_fac_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 ftdm_status_t handle_fac_cfm(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t evntType, SiFacEvnt *siFacEvnt);
 ftdm_status_t handle_umsg_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit);
+ftdm_status_t handle_susp_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiSuspEvnt *siSuspEvnt);
+ftdm_status_t handle_resm_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, SiResmEvnt *siResmEvnt);
 ftdm_status_t handle_sta_ind(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt);
 
 ftdm_status_t handle_reattempt(uint32_t suInstId, uint32_t spInstId, uint32_t circuit, uint8_t globalFlg, uint8_t evntType, SiStaEvnt *siStaEvnt);
index 52295426c06de27e9360aabee9f2b77e81f96161..0f81d61f2523b5a6cfc3b2bb568db762232d9f81 100644 (file)
@@ -1261,6 +1261,18 @@ static int ftmod_ss7_parse_isup_interface(ftdm_conf_node_t *isup_interface)
                                SS7_DEBUG("\tInvalid value for \"obci_bita\" option\n");
                        }
                /**********************************************************************/
+               } else if (!strcasecmp(parm->var, "lpa_on_cot")) {
+               /**********************************************************************/
+                       if (*parm->val == '1') {
+                               sngss7_set_options(&sng_isup, SNGSS7_LPA_FOR_COT);
+                               SS7_DEBUG("\tFound Tx LPA on COT enable option\n");
+                       } else if (*parm->val == '0') {
+                               sngss7_clear_options(&sng_isup, SNGSS7_LPA_FOR_COT);
+                               SS7_DEBUG("\tFound Tx LPA on COT disable option\n");
+                       } else {
+                               SS7_DEBUG("\tInvalid value for \"lpa_on_cot\" option\n");
+                       }
+               /**********************************************************************/
                } else {
                        SS7_ERROR("\tFound an invalid parameter \"%s\"!\n", parm->val);
                        return FTDM_FAIL;