[Freeswitch-trunk] [commit] r14015 - in freeswitch/trunk/contrib: jmesquita/mod_khomp mod/endpoints/mod_khomp mod/endpoints/mod_khomp/include mod/endpoints/mod_khomp/src

FreeSWITCH SVN raulfragoso at freeswitch.org
Sat Jun 27 17:18:43 PDT 2009


Author: raulfragoso
Date: Sat Jun 27 19:18:43 2009
New Revision: 14015

Log:
- No more dynamic allocation of pvt objects;
- Initial implementation of a function to find the first available channel;

Modified:
   freeswitch/trunk/contrib/jmesquita/mod_khomp/mod_khomp.cpp
   freeswitch/trunk/contrib/mod/endpoints/mod_khomp/include/khomp_pvt.h
   freeswitch/trunk/contrib/mod/endpoints/mod_khomp/mod_khomp.cpp
   freeswitch/trunk/contrib/mod/endpoints/mod_khomp/src/khomp_pvt.cpp

Modified: freeswitch/trunk/contrib/jmesquita/mod_khomp/mod_khomp.cpp
==============================================================================
--- freeswitch/trunk/contrib/jmesquita/mod_khomp/mod_khomp.cpp	(original)
+++ freeswitch/trunk/contrib/jmesquita/mod_khomp/mod_khomp.cpp	Sat Jun 27 19:18:43 2009
@@ -247,6 +247,8 @@
 
 static switch_status_t channel_on_hangup(switch_core_session_t *session)
 {
+    switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "CHANNEL ON HANGUP\n");
+    
 	switch_channel_t *channel = NULL;
 	private_t *tech_pvt = NULL;
 
@@ -291,6 +293,8 @@
 
 static switch_status_t channel_kill_channel(switch_core_session_t *session, int sig)
 {
+    switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "CHANNEL KILL, sig = %d\n", sig);
+    
 	switch_channel_t *channel = NULL;
 	private_t *tech_pvt = NULL;
 
@@ -1282,7 +1286,7 @@
 
 static void Kstdcall khomp_audio_listener (int32 deviceid, int32 mixer, byte * read_buffer, int32 read_size)
 {
-    switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "New audio buffer for deviceid %d, mixer %d, with size %d\n", deviceid, mixer, read_size);
+    //switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_NOTICE, "New audio buffer for deviceid %d, mixer %d, with size %d\n", deviceid, mixer, read_size);
 }
 
 /* For Emacs:

Modified: freeswitch/trunk/contrib/mod/endpoints/mod_khomp/include/khomp_pvt.h
==============================================================================
--- freeswitch/trunk/contrib/mod/endpoints/mod_khomp/include/khomp_pvt.h	(original)
+++ freeswitch/trunk/contrib/mod/endpoints/mod_khomp/include/khomp_pvt.h	Sat Jun 27 19:18:43 2009
@@ -46,24 +46,34 @@
         return _pvts[target.device][target.object];
     }
 
+    static KhompPvt * find_channel(char* allocation_string, switch_core_session_t * new_session, switch_call_cause_t * cause);
+
     static void initialize(void)
     {
+        switch_mutex_init(&_pvts_mutex, SWITCH_MUTEX_NESTED, Globals::_module_pool);
+        
         for (unsigned dev = 0; dev < Globals::_k3lapi.device_count(); dev++)
         {
-           // KhompPvt * tech_pvt;
-            //tech= (KhompPvt *) switch_core_session_alloc(*new_session, sizeof(KhompPvt));
             _pvts.push_back(std::vector<KhompPvt*>());
 
             for (unsigned obj = 0; obj < Globals::_k3lapi.channel_count(dev); obj++)
             {
                 K3LAPI::target tgt(Globals::_k3lapi, K3LAPI::target::CHANNEL, dev, obj);
                 KhompPvt * pvt = new KhompPvt(tgt);
+                pvt->_KDeviceId = dev;
+                pvt->_KChannelId = obj;
+                pvt->_session = NULL;
                 _pvts.back().push_back(pvt);
                 Globals::_k3lapi.command(dev, obj, CM_DISCONNECT, NULL); 
             }
         }
     }
 
+    static void terminate()
+    {
+        
+    }
+
     K3LAPI::target          _target;
     switch_core_session_t * _session;
 
@@ -74,6 +84,8 @@
 
     switch_frame_t _read_frame;
 
+    switch_buffer_t * _audio_buffer;
+    
     unsigned char _databuf[SWITCH_RECOMMENDED_BUFFER_SIZE];
 
     switch_caller_profile_t *_caller_profile;
@@ -82,9 +94,11 @@
     switch_mutex_t *flag_mutex; //TODO: Alterar o nome depois
 
     unsigned int _KDeviceId;    // Represent de board we are making the call from
-    unsigned int _KChannel;   // Represent the channel we are making the call from
+    unsigned int _KChannelId;   // Represent the channel we are making the call from
+    
+    /* static stuff */
+    static switch_mutex_t *_pvts_mutex;
     
-    /* static stuff */    
     static KhompPvtVector _pvts;
 };
 

Modified: freeswitch/trunk/contrib/mod/endpoints/mod_khomp/mod_khomp.cpp
==============================================================================
--- freeswitch/trunk/contrib/mod/endpoints/mod_khomp/mod_khomp.cpp	(original)
+++ freeswitch/trunk/contrib/mod/endpoints/mod_khomp/mod_khomp.cpp	Sat Jun 27 19:18:43 2009
@@ -53,7 +53,7 @@
 
     switch_mutex_init(&tech_pvt->_mutex, SWITCH_MUTEX_NESTED, switch_core_session_get_pool(session));
     switch_mutex_init(&tech_pvt->flag_mutex, SWITCH_MUTEX_NESTED, switch_core_session_get_pool(session));
-
+    
     switch_core_session_set_private(session, tech_pvt);
 
     tech_pvt->_session = session;
@@ -183,7 +183,7 @@
 
     try 
     {
-        Globals::_k3lapi.command(tech_pvt->_KDeviceId, tech_pvt->_KChannel, CM_DISCONNECT, NULL);
+        Globals::_k3lapi.command(tech_pvt->_KDeviceId, tech_pvt->_KChannelId, CM_DISCONNECT, NULL);
     }
     catch(K3LAPI::failed_command & e)
     {
@@ -267,7 +267,6 @@
     tech_pvt->_read_frame.flags = SFF_NONE;
     *frame = NULL;
 
-
     while (switch_test_flag(tech_pvt, TFLAG_IO)) {
 
         if (switch_test_flag(tech_pvt, TFLAG_BREAK)) {
@@ -385,79 +384,68 @@
 
     char *argv[3] = { 0 };
     int argc = 0;
+    KhompPvt *tech_pvt;
+    switch_call_cause_t cause = SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
 
+    /* We first need to find an available KhompPvt object to serve the session */
+    
     if ((*new_session = switch_core_session_request(Globals::_khomp_endpoint_interface, SWITCH_CALL_DIRECTION_OUTBOUND, pool)) != 0) {
-        KhompPvt *tech_pvt;
         switch_channel_t *channel;
         switch_caller_profile_t *caller_profile;
+        char name[128];
 
-        switch_core_session_add_stream(*new_session, NULL);
-        if ((tech_pvt = (KhompPvt *) switch_core_session_alloc(*new_session, sizeof(KhompPvt))) != 0) {
-            channel = switch_core_session_get_channel(*new_session);
-            tech_init(tech_pvt, *new_session);
-        } else {
-            switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CRIT, "Hey where is my memory pool?\n");
-            switch_core_session_destroy(new_session);
-            return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
-        }
-
-        if (outbound_profile) {
-            char name[128];
-
-            snprintf(name, sizeof(name), "Khomp/%s", outbound_profile->destination_number);
-            switch_channel_set_name(channel, name);
+        if (outbound_profile) 
+        {
+            tech_pvt = KhompPvt::find_channel(outbound_profile->destination_number, *new_session, &cause);
 
-            /* Let's setup our own vars on tech_pvt */
-            if ((argc = switch_separate_string(outbound_profile->destination_number, '/', argv, (sizeof(argv) / sizeof(argv[0])))) < 3)
+            if(tech_pvt == NULL || cause != SWITCH_CAUSE_SUCCESS)
             {
-                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid dial string. Should be on the format:[Khomp/BOARD/CHANNEL]\n");
-                return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
+                switch_core_session_destroy(new_session);
+                return cause;
             }
-            else
-            {
-                // usar algoritmo de busca de canais (spec.*).
-                tech_pvt->_KDeviceId = atoi(argv[0]);
-                tech_pvt->_KChannel = atoi(argv[1]);
-                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "Dialing to %s out from Board:%u, Channel:%u.\n",
-                                                                    argv[2],
-                                                                    tech_pvt->_KDeviceId,
-                                                                    tech_pvt->_KChannel);
-
-            }
-
-            caller_profile = switch_caller_profile_clone(*new_session, outbound_profile);
-            switch_channel_set_caller_profile(channel, caller_profile);
-            tech_pvt->_caller_profile = caller_profile;
-        } else {
+                    
+            switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "Dialing to %s out from Board:%u, Channel:%u.\n",
+                                                                argv[2],
+                                                                tech_pvt->_KDeviceId,
+                                                                tech_pvt->_KChannelId);
+        }
+        else
+        {
             switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Doh! no caller profile\n");
             switch_core_session_destroy(new_session);
-            /* Destroy the channel session */
-            KhompPvt::khompPvt(tech_pvt->_KDeviceId, tech_pvt->_KChannel)->session(NULL);
             return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
         }
+        
+        switch_core_session_add_stream(*new_session, NULL);
+        channel = switch_core_session_get_channel(*new_session);
+        tech_init(tech_pvt, *new_session);
 
-
+        snprintf(name, sizeof(name), "Khomp/%s", outbound_profile->destination_number);
+        switch_channel_set_name(channel, name);
+        
+        caller_profile = switch_caller_profile_clone(*new_session, outbound_profile);
+        switch_channel_set_caller_profile(channel, caller_profile);
+        tech_pvt->_caller_profile = caller_profile;
 
         switch_channel_set_flag(channel, CF_OUTBOUND);
         switch_set_flag_locked(tech_pvt, TFLAG_OUTBOUND);
         switch_channel_set_state(channel, CS_INIT);
 
-        try {
+        try 
+        {
             /* Lets make the call! */
             char params[ 255 ];
             snprintf(params, sizeof(params), "dest_addr=\"%s\" orig_addr=\"%s\"", argv[2], outbound_profile->caller_id_number);
             switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "We are calling with params: %s.\n", params);
-            Globals::_k3lapi.command(tech_pvt->_KDeviceId,tech_pvt->_KChannel, CM_MAKE_CALL, params); 
+            Globals::_k3lapi.command(tech_pvt->_KDeviceId,tech_pvt->_KChannelId, CM_MAKE_CALL, params); 
         }
         catch(K3LAPI::failed_command & e)
         {
             switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Could not place call! Cause: code%x and rc%d.\n", e.code, e.rc);
+            switch_core_session_destroy(new_session);
             return SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
         }
 
-        /* Add the new session the the channel's info */
-        KhompPvt::khompPvt(tech_pvt->_KDeviceId, tech_pvt->_KChannel)->session(*new_session);
-
         return SWITCH_CAUSE_SUCCESS;
     }
 
@@ -1113,8 +1101,11 @@
     return ksSuccess;
 }
 
-static void Kstdcall khomp_audio_listener (int32 deviceid, int32 mixer, byte * read_buffer, int32 read_size)
+static void Kstdcall khomp_audio_listener (int32 deviceid, int32 objectid, byte * read_buffer, int32 read_size)
 {
+    KhompPvt * pvt = KhompPvt::khompPvt(deviceid, objectid);
+    /*TODO: write to the switch_buffer_t member, which will be read by channel_read_frame */
+        
 }
 
 /* For Emacs:

Modified: freeswitch/trunk/contrib/mod/endpoints/mod_khomp/src/khomp_pvt.cpp
==============================================================================
--- freeswitch/trunk/contrib/mod/endpoints/mod_khomp/src/khomp_pvt.cpp	(original)
+++ freeswitch/trunk/contrib/mod/endpoints/mod_khomp/src/khomp_pvt.cpp	Sat Jun 27 19:18:43 2009
@@ -1,3 +1,132 @@
 #include "khomp_pvt.h"
 
 KhompPvt::KhompPvtVector KhompPvt::_pvts;
+switch_mutex_t * KhompPvt::_pvts_mutex;
+
+KhompPvt * KhompPvt::find_channel(char* allocation_string, switch_core_session_t * new_session, switch_call_cause_t * cause)
+{
+    /* For now we support only the 'first-free' mode */
+
+    char *argv[3] = { 0 };
+    int argc = 0;
+    
+    int board_low = 0;
+    int board_high = 0;
+
+    int channel_low = 0;
+    int channel_high = 0;
+    
+    bool first_channel_available = true;
+
+    *cause = SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER;
+
+    KhompPvt * pvt = NULL;
+    
+    /* Let's setup our own vars on tech_pvt */
+    if ((argc = switch_separate_string(allocation_string, '/', argv, (sizeof(argv) / sizeof(argv[0])))) < 3)
+    {
+        switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid dial string (%s). Should be on the format:[Khomp/BoardID (or A for first free board)/CHANNEL (or A for first free channel)]\n", allocation_string);
+        return NULL;
+    }
+
+    if(*argv[0] == 'A' || *argv[0] == 'a')
+    {
+        board_low = 0;
+        board_high = Globals::_k3lapi.device_count();
+    }
+    else
+    {
+        board_low = atoi(argv[0]);
+        board_high = board_low;
+    }
+
+    if(*argv[1] == 'A' || *argv[1] == 'a')
+    {
+        first_channel_available = true;
+    }
+    else
+    {
+        first_channel_available = false;
+        channel_low = atoi(argv[0]);
+        channel_high = board_low;
+    }
+
+    /* Sanity checking */
+    if(board_low < 0 || board_high > Globals::_k3lapi.device_count())
+    {
+        switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid board selection (%d-%d) !\n", board_low, board_high);
+        return NULL;            
+    }
+
+    switch_mutex_lock(_pvts_mutex);
+
+    switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel selection: board (%d-%d), channel (%d-%d)!\n", board_low, board_high, channel_low, channel_high);
+    
+    for (int board = board_low ; board < board_high; board++)
+    {
+        if(pvt != NULL)
+            break;
+        
+        if(first_channel_available)
+        {
+            channel_low = 0;
+            channel_high = Globals::_k3lapi.channel_count(board);
+        }
+        else
+        {
+            if(channel_low < 0 || channel_high > Globals::_k3lapi.channel_count(board))
+            {
+                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Invalid channel selection (%d-%d) !\n", channel_low, channel_high);
+                switch_mutex_unlock(_pvts_mutex);
+                return NULL;
+            }
+        }
+        
+        for (int channel = channel_low ; channel < channel_high ; channel++) 
+        {
+            switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Checking if (%d-%d) is free\n", board, channel);
+            try 
+            {
+                K3L_CHANNEL_CONFIG channelConfig;
+                channelConfig = Globals::_k3lapi.channel_config( board, channel );
+            }
+            catch (...)
+            {
+                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Exception while retrieving channel config for board %d, channel%d!\n", board, channel);
+                switch_mutex_unlock(_pvts_mutex);
+                return NULL;
+            }
+            K3L_CHANNEL_STATUS status;
+            if (k3lGetDeviceStatus( board, channel + ksoChannel, &status, sizeof(status) ) != ksSuccess)
+            {
+                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "k3lGetDeviceStatus failed to retrieve channel config for board %d, channel%d!\n", board, channel);
+                switch_mutex_unlock(_pvts_mutex);
+                return NULL;
+            }
+            if(status.CallStatus == kcsFree)
+            {
+                switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Channel (%d-%d) is free, let's check if the session is available ...\n", board, channel);
+                pvt = KhompPvt::khompPvt(board, channel);
+                if(pvt != NULL && pvt->session() == NULL)
+                {
+                    pvt->session(new_session);
+                    break;
+                }
+                pvt = NULL;
+            }
+        }
+    }
+
+    if(pvt != NULL)
+    {
+        *cause = SWITCH_CAUSE_SUCCESS;
+    }
+    else
+    {
+        switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "No channels available\n");
+        *cause = SWITCH_CAUSE_NORMAL_CIRCUIT_CONGESTION;
+    }
+    
+    switch_mutex_unlock(_pvts_mutex);
+    return pvt;
+}
\ No newline at end of file



More information about the Freeswitch-trunk mailing list