fixed overlap dialing problem:
[lcr.git] / chan_lcr.c
index ff8da54..5978865 100644 (file)
@@ -475,6 +475,14 @@ void apply_opt(struct chan_call *call, char *data)
                        if (call->bchannel)
                                bchannel_pipeline(call->bchannel, call->pipeline);
                        break;
+               case 'r':
+                       if (opt[1] == '\0') {
+                               CERROR(call, call->ast, "Option 'r' (re-buffer 160 bytes) expects no parameter.\n", opt);
+                               break;
+                       }
+                       CDEBUG(call, call->ast, "Option 'r' (re-buffer 160 bytes)");
+                       call->rebuffer = 1;
+                       break;
 #if 0
                case 's':
                        if (opt[1] != '\0') {
@@ -732,6 +740,10 @@ static void lcr_start_pbx(struct chan_call *call, struct ast_channel *ast, int c
                goto release;
        }
        call->pbx_started = 1;
+//     if (call->state == CHAN_LCR_STATE_IN_DIALING)
+//             ast_setstate(ast, AST_STATE_DIALING);
+//     else
+//             ast_setstate(ast, AST_STATE_OFFHOOK);
        return;
 }
 
@@ -986,6 +998,13 @@ static void lcr_in_information(struct chan_call *call, int message_type, union p
                return;
        }
        
+       /* change dailing state after setup */
+       if (call->state == CHAN_LCR_STATE_IN_SETUP) {
+               CDEBUG(call, call->ast, "Changing from SETUP to DIALING state.\n");
+               call->state = CHAN_LCR_STATE_IN_DIALING;
+//             ast_setstate(ast, AST_STATE_DIALING);
+       }
+       
        /* queue digits */
        if (call->state == CHAN_LCR_STATE_IN_DIALING && param->information.id[0])
                strncat(call->queue_string, param->information.id, sizeof(call->queue_string)-1);
@@ -1510,10 +1529,11 @@ static int queue_send(void)
                                                CDEBUG(call, ast, "Sending queued digit '%c' to Asterisk.\n", *p);
                                                /* send digit to asterisk */
                                                memset(&fr, 0, sizeof(fr));
-                                               fr.frametype = AST_FRAME_DTMF;
+                                               fr.frametype = AST_FRAME_DTMF_BEGIN;
                                                fr.subclass = *p;
                                                fr.delivery = ast_tv(0, 0);
-                                               fr.len = 100;
+                                               ast_queue_frame(ast, &fr);
+                                               fr.frametype = AST_FRAME_DTMF_END;
                                                ast_queue_frame(ast, &fr);
                                                break;
                                        default:
@@ -1813,17 +1833,19 @@ static int lcr_answer(struct ast_channel *ast)
                return -1;
        }
        
-       CDEBUG(call, ast, "Received answer from Asterisk.\n");
+       CDEBUG(call, ast, "Received answer from Asterisk (maybe during lcr_bridge).\n");
                
        /* copy connectinfo, if bridged */
        if (call->bridge_call)
                memcpy(&call->connectinfo, &call->bridge_call->connectinfo, sizeof(struct connect_info));
        /* send connect message to lcr */
-       memset(&newparam, 0, sizeof(union parameter));
-       memcpy(&newparam.connectinfo, &call->connectinfo, sizeof(struct connect_info));
-       send_message(MESSAGE_CONNECT, call->ref, &newparam);
+       if (call->state != CHAN_LCR_STATE_CONNECT) {
+               memset(&newparam, 0, sizeof(union parameter));
+               memcpy(&newparam.connectinfo, &call->connectinfo, sizeof(struct connect_info));
+               send_message(MESSAGE_CONNECT, call->ref, &newparam);
+               call->state = CHAN_LCR_STATE_CONNECT;
+       }
        /* change state */
-       call->state = CHAN_LCR_STATE_CONNECT;
        /* request bchannel */
        if (!call->bchannel) {
                CDEBUG(call, ast, "Requesting B-channel.\n");
@@ -1935,7 +1957,11 @@ static struct ast_frame *lcr_read(struct ast_channel *ast)
                return NULL;
        }
        if (call->pipe[0] > -1) {
-               len = read(call->pipe[0], call->read_buff, sizeof(call->read_buff));
+               if (call->rebuffer) {
+                       len = read(call->pipe[0], call->read_buff, 160);
+               } else {
+                       len = read(call->pipe[0], call->read_buff, sizeof(call->read_buff));
+               }
                if (len <= 0) {
                        close(call->pipe[0]);
                        call->pipe[0] = -1;
@@ -2129,7 +2155,7 @@ enum ast_bridge_result lcr_bridge(struct ast_channel *ast1,
 
        carr[0] = ast1;
        carr[1] = ast2;
-       
+
        /* join via dsp (if the channels are currently open) */
        ast_mutex_lock(&chan_lock);
        bridge_id = new_bridge_id();
@@ -2149,6 +2175,22 @@ enum ast_bridge_result lcr_bridge(struct ast_channel *ast1,
                        bchannel_join(call2->bchannel, bridge_id);
                call2->bridge_call = call1;
        }
+
+       if (call1->state == CHAN_LCR_STATE_IN_SETUP
+        || call1->state == CHAN_LCR_STATE_IN_DIALING
+        || call1->state == CHAN_LCR_STATE_IN_PROCEEDING
+        || call1->state == CHAN_LCR_STATE_IN_ALERTING) {
+               CDEBUG(call1, ast1, "Bridge established before lcr_answer, so we call it ourself: Calling lcr_answer...\n");
+               lcr_answer(ast1);
+       }
+       if (call2->state == CHAN_LCR_STATE_IN_SETUP
+        || call2->state == CHAN_LCR_STATE_IN_DIALING
+        || call2->state == CHAN_LCR_STATE_IN_PROCEEDING
+        || call2->state == CHAN_LCR_STATE_IN_ALERTING) {
+               CDEBUG(call2, ast2, "Bridge established before lcr_answer, so we call it ourself: Calling lcr_answer...\n");
+               lcr_answer(ast2);
+       }
+       
        ast_mutex_unlock(&chan_lock);
        
        while(1) {