update to new boost api SIGBOOST_VERSION 101. Fixes multiple race condition issues with thread waiting for chan and better handling of call rejects. This requires sangoma_prid v1.48 or later
git-svn-id: http://svn.openzap.org/svn/openzap/trunk@1001 a93c3328-9c30-0410-af19-c9cd2b2d52af
This commit is contained in:
parent
cec179037f
commit
7f746a7064
|
@ -47,7 +47,10 @@ static time_t congestion_timeouts[MAX_TRUNK_GROUPS];
|
||||||
typedef enum {
|
typedef enum {
|
||||||
SFLAG_FREE_REQ_ID = (1 << 0),
|
SFLAG_FREE_REQ_ID = (1 << 0),
|
||||||
SFLAG_SENT_FINAL_MSG = (1 << 1),
|
SFLAG_SENT_FINAL_MSG = (1 << 1),
|
||||||
SFLAG_SENT_ACK = (1 << 2)
|
SFLAG_SENT_ACK = (1 << 2),
|
||||||
|
SFLAG_RECVD_ACK = (1 << 3),
|
||||||
|
SFLAG_HANGUP = (1 << 4),
|
||||||
|
SFLAG_TERMINATING = (1 << 5)
|
||||||
} sflag_t;
|
} sflag_t;
|
||||||
|
|
||||||
typedef uint16_t sangoma_boost_request_id_t;
|
typedef uint16_t sangoma_boost_request_id_t;
|
||||||
|
@ -72,6 +75,7 @@ typedef struct {
|
||||||
zap_span_t *span;
|
zap_span_t *span;
|
||||||
zap_channel_t *zchan;
|
zap_channel_t *zchan;
|
||||||
int hangup_cause;
|
int hangup_cause;
|
||||||
|
int flags;
|
||||||
} sangoma_boost_request_t;
|
} sangoma_boost_request_t;
|
||||||
|
|
||||||
//#define MAX_REQ_ID ZAP_MAX_PHYSICAL_SPANS_PER_LOGICAL_SPAN * ZAP_MAX_CHANNELS_PHYSICAL_SPAN
|
//#define MAX_REQ_ID ZAP_MAX_PHYSICAL_SPANS_PER_LOGICAL_SPAN * ZAP_MAX_CHANNELS_PHYSICAL_SPAN
|
||||||
|
@ -220,30 +224,6 @@ static int check_congestion(int trunk_group)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* \brief determines whether media is ready
|
|
||||||
* \param event boost event
|
|
||||||
* \return 1 true, 0 for false
|
|
||||||
*/
|
|
||||||
|
|
||||||
static int boost_media_ready(sangomabc_event_t *event)
|
|
||||||
{
|
|
||||||
/* FORMAT is of type: SMG003-EVI-1-MEDIA-# */
|
|
||||||
char* p = NULL;
|
|
||||||
p = strstr(event->isup_in_rdnis, "MEDIA");
|
|
||||||
if (p) {
|
|
||||||
int media_ready = 0;
|
|
||||||
if ((sscanf(p, "MEDIA-%d", &media_ready)) == 1) {
|
|
||||||
if (media_ready) {
|
|
||||||
return 1;
|
|
||||||
} else {
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
zap_log(ZAP_LOG_ERROR, "Invalid boost isup_rdnis MEDIA format %s\n", p);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief Requests an sangoma boost channel on a span (outgoing call)
|
* \brief Requests an sangoma boost channel on a span (outgoing call)
|
||||||
|
@ -361,28 +341,9 @@ static ZIO_CHANNEL_REQUEST_FUNCTION(sangoma_boost_channel_request)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (OUTBOUND_REQUESTS[r].status == BST_ACK && OUTBOUND_REQUESTS[r].zchan) {
|
|
||||||
*zchan = OUTBOUND_REQUESTS[r].zchan;
|
|
||||||
status = ZAP_SUCCESS;
|
|
||||||
(*zchan)->init_state = ZAP_CHANNEL_STATE_PROGRESS;
|
|
||||||
zap_log(ZAP_LOG_DEBUG, "Channel state changed to PROGRESS [Csid:%d]\n", r);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* This is blocking the channel thread in openzap */
|
|
||||||
/* Once we know the channel we need to get out of here and move to a state */
|
|
||||||
sanity = 60000;
|
|
||||||
while(zap_running() && OUTBOUND_REQUESTS[r].status == BST_ACK) {
|
|
||||||
zap_sleep(1);
|
|
||||||
if (--sanity <= 0) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (OUTBOUND_REQUESTS[r].status == BST_READY && OUTBOUND_REQUESTS[r].zchan) {
|
if (OUTBOUND_REQUESTS[r].status == BST_READY && OUTBOUND_REQUESTS[r].zchan) {
|
||||||
*zchan = OUTBOUND_REQUESTS[r].zchan;
|
*zchan = OUTBOUND_REQUESTS[r].zchan;
|
||||||
status = ZAP_SUCCESS;
|
status = ZAP_SUCCESS;
|
||||||
(*zchan)->init_state = ZAP_CHANNEL_STATE_PROGRESS_MEDIA;
|
|
||||||
zap_log(ZAP_LOG_DEBUG, "Channel state changed to PROGRESS_MEDIA [Csid:%d]\n", r);
|
|
||||||
} else {
|
} else {
|
||||||
status = ZAP_FAIL;
|
status = ZAP_FAIL;
|
||||||
*zchan = NULL;
|
*zchan = NULL;
|
||||||
|
@ -390,21 +351,6 @@ static ZIO_CHANNEL_REQUEST_FUNCTION(sangoma_boost_channel_request)
|
||||||
|
|
||||||
done:
|
done:
|
||||||
|
|
||||||
/* We failed to ever setup media, we need to let go of the channel */
|
|
||||||
/* All of this early media stuff should not be in this function at all */
|
|
||||||
/* Everything after we know the channel should be moved to a new state */
|
|
||||||
if (OUTBOUND_REQUESTS[r].zchan && OUTBOUND_REQUESTS[r].status != BST_READY && zap_test_flag((OUTBOUND_REQUESTS[r].zchan), ZAP_CHANNEL_INUSE)) {
|
|
||||||
status = ZAP_FAIL;
|
|
||||||
*zchan = NULL;
|
|
||||||
if (OUTBOUND_REQUESTS[r].zchan->extra_id) {
|
|
||||||
OUTBOUND_REQUESTS[r].zchan->extra_id = 0;
|
|
||||||
}
|
|
||||||
(OUTBOUND_REQUESTS[r].zchan)->sflags = 0;
|
|
||||||
(OUTBOUND_REQUESTS[r].zchan)->call_data = NULL;
|
|
||||||
zap_channel_done((OUTBOUND_REQUESTS[r].zchan));
|
|
||||||
OUTBOUND_REQUESTS[r].zchan = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
st = OUTBOUND_REQUESTS[r].status;
|
st = OUTBOUND_REQUESTS[r].status;
|
||||||
OUTBOUND_REQUESTS[r].status = BST_FREE;
|
OUTBOUND_REQUESTS[r].status = BST_FREE;
|
||||||
|
|
||||||
|
@ -426,6 +372,7 @@ static ZIO_CHANNEL_REQUEST_FUNCTION(sangoma_boost_channel_request)
|
||||||
0,
|
0,
|
||||||
r,
|
r,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK,
|
SIGBOOST_EVENT_CALL_START_NACK,
|
||||||
|
0,
|
||||||
0);
|
0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -449,63 +396,35 @@ static ZIO_CHANNEL_OUTGOING_CALL_FUNCTION(sangoma_boost_outgoing_call)
|
||||||
* \param mcon sangoma boost connection
|
* \param mcon sangoma boost connection
|
||||||
* \param event Event to handle
|
* \param event Event to handle
|
||||||
*/
|
*/
|
||||||
static void handle_call_progress(sangomabc_connection_t *mcon, sangomabc_short_event_t *event)
|
static void handle_call_progress(zap_span_t *span, sangomabc_connection_t *mcon, sangomabc_short_event_t *event)
|
||||||
{
|
{
|
||||||
zap_channel_t *zchan;
|
zap_channel_t *zchan;
|
||||||
|
|
||||||
if (nack_map[event->call_setup_id]) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
//if we received a progress for this device already
|
if ((zchan = find_zchan(span, event, 1))) {
|
||||||
if (OUTBOUND_REQUESTS[event->call_setup_id].status == BST_ACK) {
|
zap_mutex_lock(zchan->mutex);
|
||||||
if (boost_media_ready((sangomabc_event_t*) event)) {
|
if (zchan->state == ZAP_CHANNEL_STATE_HOLD) {
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_READY;
|
if ((event->flags & SIGBOOST_PROGRESS_MEDIA)) {
|
||||||
zap_log(ZAP_LOG_DEBUG, "chan media ready %d:%d CSid:%d\n", event->span+1, event->chan+1, event->call_setup_id);
|
zchan->init_state = ZAP_CHANNEL_STATE_PROGRESS_MEDIA;
|
||||||
}
|
zap_log(ZAP_LOG_DEBUG, "Channel init state updated to PROGRESS_MEDIA [Csid:%d]\n", event->call_setup_id);
|
||||||
return;
|
} else if ((event->flags & SIGBOOST_PROGRESS_RING)) {
|
||||||
}
|
zchan->init_state = ZAP_CHANNEL_STATE_PROGRESS;
|
||||||
|
zap_log(ZAP_LOG_DEBUG, "Channel init state updated to PROGRESS [Csid:%d]\n", event->call_setup_id);
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].event = *event;
|
|
||||||
SETUP_GRID[event->span][event->chan] = event->call_setup_id;
|
|
||||||
|
|
||||||
if ((zchan = find_zchan(OUTBOUND_REQUESTS[event->call_setup_id].span, (sangomabc_short_event_t*) event, 0))) {
|
|
||||||
if (zap_channel_open_chan(zchan) != ZAP_SUCCESS) {
|
|
||||||
zap_log(ZAP_LOG_ERROR, "OPEN ERROR [%s]\n", zchan->last_error);
|
|
||||||
} else {
|
} else {
|
||||||
zap_set_flag(zchan, ZAP_CHANNEL_OUTBOUND);
|
zchan->init_state = ZAP_CHANNEL_STATE_IDLE;
|
||||||
zap_set_flag_locked(zchan, ZAP_CHANNEL_INUSE);
|
zap_log(ZAP_LOG_DEBUG, "Channel init state updated to IDLE [Csid:%d]\n", event->call_setup_id);
|
||||||
zchan->extra_id = event->call_setup_id;
|
}
|
||||||
zap_log(ZAP_LOG_DEBUG, "Assign chan %d:%d (%d:%d) CSid=%d\n", zchan->span_id, zchan->chan_id, event->span+1,event->chan+1, event->call_setup_id);
|
|
||||||
zchan->sflags = 0;
|
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].zchan = zchan;
|
|
||||||
if (boost_media_ready((sangomabc_event_t*)event)) {
|
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_READY;
|
|
||||||
} else {
|
} else {
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_ACK;
|
if ((event->flags & SIGBOOST_PROGRESS_MEDIA)) {
|
||||||
}
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_PROGRESS_MEDIA);
|
||||||
return;
|
} else if ((event->flags & SIGBOOST_PROGRESS_RING)) {
|
||||||
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_PROGRESS);
|
||||||
|
} else {
|
||||||
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_IDLE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
zap_mutex_unlock(zchan->mutex);
|
||||||
//printf("WTF BAD ACK CSid=%d span=%d chan=%d\n", event->call_setup_id, event->span+1,event->chan+1);
|
|
||||||
if ((zchan = find_zchan(OUTBOUND_REQUESTS[event->call_setup_id].span, event, 1))) {
|
|
||||||
//printf("WTF BAD ACK2 %d:%d (%d:%d) CSid=%d xtra_id=%d out=%d state=%s\n", zchan->span_id, zchan->chan_id, event->span+1,event->chan+1, event->call_setup_id, zchan->extra_id, zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND), zap_channel_state2str(zchan->state));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
zap_log(ZAP_LOG_CRIT, "START PROGRESS CANT FIND A CHAN %d:%d\n", event->span+1,event->chan+1);
|
|
||||||
if (zchan) {
|
|
||||||
zap_set_sflag(zchan, SFLAG_SENT_FINAL_MSG);
|
|
||||||
}
|
|
||||||
sangomabc_exec_command(mcon,
|
|
||||||
event->span,
|
|
||||||
event->chan,
|
|
||||||
event->call_setup_id,
|
|
||||||
SIGBOOST_EVENT_CALL_STOPPED,
|
|
||||||
ZAP_CAUSE_DESTINATION_OUT_OF_ORDER);
|
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_FAIL;
|
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].hangup_cause = ZAP_CAUSE_DESTINATION_OUT_OF_ORDER;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -532,7 +451,22 @@ static void handle_call_start_ack(sangomabc_connection_t *mcon, sangomabc_short_
|
||||||
zap_set_flag_locked(zchan, ZAP_CHANNEL_INUSE);
|
zap_set_flag_locked(zchan, ZAP_CHANNEL_INUSE);
|
||||||
zchan->extra_id = event->call_setup_id;
|
zchan->extra_id = event->call_setup_id;
|
||||||
zap_log(ZAP_LOG_DEBUG, "Assign chan %d:%d (%d:%d) CSid=%d\n", zchan->span_id, zchan->chan_id, event->span+1,event->chan+1, event->call_setup_id);
|
zap_log(ZAP_LOG_DEBUG, "Assign chan %d:%d (%d:%d) CSid=%d\n", zchan->span_id, zchan->chan_id, event->span+1,event->chan+1, event->call_setup_id);
|
||||||
zchan->sflags = 0;
|
zchan->sflags = SFLAG_RECVD_ACK;
|
||||||
|
|
||||||
|
if ((event->flags & SIGBOOST_PROGRESS_MEDIA)) {
|
||||||
|
zchan->init_state = ZAP_CHANNEL_STATE_PROGRESS_MEDIA;
|
||||||
|
zap_log(ZAP_LOG_DEBUG, "Channel init state changed to PROGRESS_MEDIA [Csid:%d]\n", event->call_setup_id);
|
||||||
|
} else if ((event->flags & SIGBOOST_PROGRESS_RING)) {
|
||||||
|
zchan->init_state = ZAP_CHANNEL_STATE_PROGRESS;
|
||||||
|
zap_log(ZAP_LOG_DEBUG, "Channel init state changed to PROGRESS [Csid:%d]\n", event->call_setup_id);
|
||||||
|
} else {
|
||||||
|
zchan->init_state = ZAP_CHANNEL_STATE_IDLE;
|
||||||
|
zap_log(ZAP_LOG_DEBUG, "Channel init state changed to IDLE [Csid:%d]\n", event->call_setup_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HOLD);
|
||||||
|
|
||||||
|
OUTBOUND_REQUESTS[event->call_setup_id].flags = event->flags;
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].zchan = zchan;
|
OUTBOUND_REQUESTS[event->call_setup_id].zchan = zchan;
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_READY;
|
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_READY;
|
||||||
return;
|
return;
|
||||||
|
@ -551,7 +485,7 @@ static void handle_call_start_ack(sangomabc_connection_t *mcon, sangomabc_short_
|
||||||
event->chan,
|
event->chan,
|
||||||
event->call_setup_id,
|
event->call_setup_id,
|
||||||
SIGBOOST_EVENT_CALL_STOPPED,
|
SIGBOOST_EVENT_CALL_STOPPED,
|
||||||
ZAP_CAUSE_DESTINATION_OUT_OF_ORDER);
|
ZAP_CAUSE_DESTINATION_OUT_OF_ORDER, 0);
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_FAIL;
|
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_FAIL;
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].hangup_cause = ZAP_CAUSE_DESTINATION_OUT_OF_ORDER;
|
OUTBOUND_REQUESTS[event->call_setup_id].hangup_cause = ZAP_CAUSE_DESTINATION_OUT_OF_ORDER;
|
||||||
|
|
||||||
|
@ -571,7 +505,7 @@ static void handle_call_done(zap_span_t *span, sangomabc_connection_t *mcon, san
|
||||||
if ((zchan = find_zchan(span, event, 1))) {
|
if ((zchan = find_zchan(span, event, 1))) {
|
||||||
zap_mutex_lock(zchan->mutex);
|
zap_mutex_lock(zchan->mutex);
|
||||||
|
|
||||||
if (zchan->state == ZAP_CHANNEL_STATE_DOWN || zchan->state == ZAP_CHANNEL_STATE_HANGUP_COMPLETE) {
|
if (zchan->state == ZAP_CHANNEL_STATE_DOWN || zchan->state == ZAP_CHANNEL_STATE_HANGUP_COMPLETE || zap_test_sflag(zchan, SFLAG_TERMINATING)) {
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -640,7 +574,7 @@ static void handle_call_start_nack(zap_span_t *span, sangomabc_connection_t *mco
|
||||||
0,
|
0,
|
||||||
event->call_setup_id,
|
event->call_setup_id,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
||||||
0);
|
0, 0);
|
||||||
|
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].event = *event;
|
OUTBOUND_REQUESTS[event->call_setup_id].event = *event;
|
||||||
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_FAIL;
|
OUTBOUND_REQUESTS[event->call_setup_id].status = BST_FAIL;
|
||||||
|
@ -675,7 +609,7 @@ static void handle_call_start_nack(zap_span_t *span, sangomabc_connection_t *mco
|
||||||
event->chan,
|
event->chan,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
||||||
0);
|
0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -693,7 +627,7 @@ static void handle_call_stop(zap_span_t *span, sangomabc_connection_t *mcon, san
|
||||||
|
|
||||||
zap_mutex_lock(zchan->mutex);
|
zap_mutex_lock(zchan->mutex);
|
||||||
|
|
||||||
if (zchan->state == ZAP_CHANNEL_STATE_HANGUP) {
|
if (zap_test_sflag(zchan, SFLAG_HANGUP)) {
|
||||||
/* racing condition where both sides initiated a hangup
|
/* racing condition where both sides initiated a hangup
|
||||||
* Do not change current state as channel is already clearing
|
* Do not change current state as channel is already clearing
|
||||||
* itself through local initiated hangup */
|
* itself through local initiated hangup */
|
||||||
|
@ -703,12 +637,21 @@ static void handle_call_stop(zap_span_t *span, sangomabc_connection_t *mcon, san
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_STOPPED_ACK,
|
SIGBOOST_EVENT_CALL_STOPPED_ACK,
|
||||||
0);
|
0, 0);
|
||||||
|
zap_mutex_unlock(zchan->mutex);
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
if (zchan->state == ZAP_CHANNEL_STATE_HOLD) {
|
||||||
|
zchan->init_state = ZAP_CHANNEL_STATE_TERMINATING;
|
||||||
|
zap_log(ZAP_LOG_DEBUG, "Channel init state updated to TERMINATING [Csid:%d]\n", event->call_setup_id);
|
||||||
|
OUTBOUND_REQUESTS[event->call_setup_id].hangup_cause = event->release_cause;
|
||||||
|
zchan->caller_data.hangup_cause = event->release_cause;
|
||||||
zap_mutex_unlock(zchan->mutex);
|
zap_mutex_unlock(zchan->mutex);
|
||||||
return;
|
return;
|
||||||
} else {
|
} else {
|
||||||
zap_set_state_r(zchan, ZAP_CHANNEL_STATE_TERMINATING, 0, r);
|
zap_set_state_r(zchan, ZAP_CHANNEL_STATE_TERMINATING, 0, r);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (r == ZAP_STATE_CHANGE_SUCCESS) {
|
if (r == ZAP_STATE_CHANGE_SUCCESS) {
|
||||||
zchan->caller_data.hangup_cause = event->release_cause;
|
zchan->caller_data.hangup_cause = event->release_cause;
|
||||||
|
@ -719,6 +662,7 @@ static void handle_call_stop(zap_span_t *span, sangomabc_connection_t *mcon, san
|
||||||
}
|
}
|
||||||
|
|
||||||
zap_mutex_unlock(zchan->mutex);
|
zap_mutex_unlock(zchan->mutex);
|
||||||
|
|
||||||
if (r) {
|
if (r) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -739,25 +683,22 @@ static void handle_call_answer(zap_span_t *span, sangomabc_connection_t *mcon, s
|
||||||
zap_channel_t *zchan;
|
zap_channel_t *zchan;
|
||||||
|
|
||||||
if ((zchan = find_zchan(span, event, 1))) {
|
if ((zchan = find_zchan(span, event, 1))) {
|
||||||
int r = 0;
|
|
||||||
|
|
||||||
if (zchan->extra_id == event->call_setup_id && zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
|
||||||
zap_mutex_lock(zchan->mutex);
|
zap_mutex_lock(zchan->mutex);
|
||||||
if (zchan->state == ZAP_CHANNEL_STATE_DOWN && zchan->init_state != ZAP_CHANNEL_STATE_UP) {
|
if (zchan->state == ZAP_CHANNEL_STATE_HOLD) {
|
||||||
zchan->init_state = ZAP_CHANNEL_STATE_UP;
|
zchan->init_state = ZAP_CHANNEL_STATE_UP;
|
||||||
r = 1;
|
|
||||||
} else {
|
} else {
|
||||||
|
int r = 0;
|
||||||
zap_set_state_r(zchan, ZAP_CHANNEL_STATE_UP, 0, r);
|
zap_set_state_r(zchan, ZAP_CHANNEL_STATE_UP, 0, r);
|
||||||
}
|
}
|
||||||
zap_mutex_unlock(zchan->mutex);
|
zap_mutex_unlock(zchan->mutex);
|
||||||
}
|
|
||||||
#if 0
|
|
||||||
if (!r) {
|
|
||||||
printf("WTF BAD ANSWER %d:%d (%d:%d) CSid=%d xtra_id=%d out=%d state=%s\n", zchan->span_id, zchan->chan_id, event->span+1,event->chan+1, event->call_setup_id, zchan->extra_id, zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND), zap_channel_state2str(zchan->state));
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
} else {
|
} else {
|
||||||
zap_log(ZAP_LOG_CRIT, "ANSWER CANT FIND A CHAN %d:%d\n", event->span+1,event->chan+1);
|
zap_log(ZAP_LOG_CRIT, "ANSWER CANT FIND A CHAN %d:%d\n", event->span+1,event->chan+1);
|
||||||
|
sangomabc_exec_command(mcon,
|
||||||
|
event->span,
|
||||||
|
event->chan,
|
||||||
|
event->call_setup_id,
|
||||||
|
SIGBOOST_EVENT_CALL_STOPPED,
|
||||||
|
ZAP_CAUSE_DESTINATION_OUT_OF_ORDER, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -833,7 +774,7 @@ static void handle_call_start(zap_span_t *span, sangomabc_connection_t *mcon, sa
|
||||||
event->chan,
|
event->chan,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK,
|
SIGBOOST_EVENT_CALL_START_NACK,
|
||||||
0);
|
0, 0);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -948,7 +889,7 @@ static int parse_sangoma_event(zap_span_t *span, sangomabc_connection_t *mcon, s
|
||||||
handle_call_start_ack(mcon, event);
|
handle_call_start_ack(mcon, event);
|
||||||
break;
|
break;
|
||||||
case SIGBOOST_EVENT_CALL_PROGRESS:
|
case SIGBOOST_EVENT_CALL_PROGRESS:
|
||||||
handle_call_progress(mcon, event);
|
handle_call_progress(span, mcon, event);
|
||||||
break;
|
break;
|
||||||
case SIGBOOST_EVENT_CALL_START_NACK:
|
case SIGBOOST_EVENT_CALL_START_NACK:
|
||||||
handle_call_start_nack(span, mcon, event);
|
handle_call_start_nack(span, mcon, event);
|
||||||
|
@ -1018,10 +959,6 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
switch (zchan->state) {
|
switch (zchan->state) {
|
||||||
case ZAP_CHANNEL_STATE_DOWN:
|
case ZAP_CHANNEL_STATE_DOWN:
|
||||||
{
|
{
|
||||||
if (zchan->extra_id) {
|
|
||||||
zchan->extra_id = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (zap_test_sflag(zchan, SFLAG_FREE_REQ_ID)) {
|
if (zap_test_sflag(zchan, SFLAG_FREE_REQ_ID)) {
|
||||||
release_request_id_span_chan(zchan->physical_span_id-1, zchan->physical_chan_id-1);
|
release_request_id_span_chan(zchan->physical_span_id-1, zchan->physical_chan_id-1);
|
||||||
}
|
}
|
||||||
|
@ -1035,7 +972,7 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
SIGBOOST_EVENT_CALL_START_NACK_ACK,
|
||||||
0);
|
0, 0);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
sangomabc_exec_command(mcon,
|
sangomabc_exec_command(mcon,
|
||||||
|
@ -1043,16 +980,19 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_STOPPED_ACK,
|
SIGBOOST_EVENT_CALL_STOPPED_ACK,
|
||||||
0);
|
0, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (zchan->extra_id) {
|
||||||
|
zchan->extra_id = 0;
|
||||||
|
}
|
||||||
zchan->sflags = 0;
|
zchan->sflags = 0;
|
||||||
zchan->call_data = NULL;
|
zchan->call_data = NULL;
|
||||||
zap_channel_done(zchan);
|
zap_channel_done(zchan);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ZAP_CHANNEL_STATE_PROGRESS_MEDIA:
|
case ZAP_CHANNEL_STATE_PROGRESS_MEDIA:
|
||||||
case ZAP_CHANNEL_STATE_PROGRESS:
|
|
||||||
{
|
{
|
||||||
if (zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
if (zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
||||||
sig.event_id = ZAP_SIGEVENT_PROGRESS_MEDIA;
|
sig.event_id = ZAP_SIGEVENT_PROGRESS_MEDIA;
|
||||||
|
@ -1067,11 +1007,37 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_ACK,
|
SIGBOOST_EVENT_CALL_START_ACK,
|
||||||
0);
|
0,
|
||||||
|
SIGBOOST_PROGRESS_MEDIA);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case ZAP_CHANNEL_STATE_PROGRESS:
|
||||||
|
{
|
||||||
|
if (zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
||||||
|
sig.event_id = ZAP_SIGEVENT_PROGRESS;
|
||||||
|
if ((status = sangoma_boost_data->signal_cb(&sig) != ZAP_SUCCESS)) {
|
||||||
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (!zap_test_sflag(zchan, SFLAG_SENT_ACK)) {
|
||||||
|
zap_set_sflag(zchan, SFLAG_SENT_ACK);
|
||||||
|
sangomabc_exec_command(mcon,
|
||||||
|
zchan->physical_span_id-1,
|
||||||
|
zchan->physical_chan_id-1,
|
||||||
|
0,
|
||||||
|
SIGBOOST_EVENT_CALL_START_ACK,
|
||||||
|
0,
|
||||||
|
SIGBOOST_PROGRESS_RING);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case ZAP_CHANNEL_STATE_IDLE:
|
||||||
|
case ZAP_CHANNEL_STATE_HOLD:
|
||||||
|
/* twiddle */
|
||||||
|
break;
|
||||||
case ZAP_CHANNEL_STATE_RING:
|
case ZAP_CHANNEL_STATE_RING:
|
||||||
{
|
{
|
||||||
if (!zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
if (!zap_test_flag(zchan, ZAP_CHANNEL_OUTBOUND)) {
|
||||||
|
@ -1104,7 +1070,7 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_ACK,
|
SIGBOOST_EVENT_CALL_START_ACK,
|
||||||
0);
|
0, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
sangomabc_exec_command(mcon,
|
sangomabc_exec_command(mcon,
|
||||||
|
@ -1112,7 +1078,7 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_ANSWERED,
|
SIGBOOST_EVENT_CALL_ANSWERED,
|
||||||
0);
|
0, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
@ -1127,34 +1093,40 @@ static __inline__ void state_advance(zap_channel_t *zchan)
|
||||||
break;
|
break;
|
||||||
case ZAP_CHANNEL_STATE_HANGUP:
|
case ZAP_CHANNEL_STATE_HANGUP:
|
||||||
{
|
{
|
||||||
if (zchan->last_state == ZAP_CHANNEL_STATE_TERMINATING ||
|
zap_set_sflag_locked(zchan, SFLAG_HANGUP);
|
||||||
zap_test_sflag(zchan, SFLAG_SENT_FINAL_MSG)) {
|
|
||||||
|
if (zap_test_sflag(zchan, SFLAG_SENT_FINAL_MSG)) {
|
||||||
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP_COMPLETE);
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP_COMPLETE);
|
||||||
} else {
|
} else {
|
||||||
zap_set_sflag_locked(zchan, SFLAG_SENT_FINAL_MSG);
|
zap_set_sflag_locked(zchan, SFLAG_SENT_FINAL_MSG);
|
||||||
if (zap_test_flag(zchan, ZAP_CHANNEL_ANSWERED) || zap_test_flag(zchan, ZAP_CHANNEL_PROGRESS) || zap_test_flag(zchan, ZAP_CHANNEL_MEDIA)) {
|
|
||||||
|
if (zap_test_flag(zchan, ZAP_CHANNEL_ANSWERED) ||
|
||||||
|
zap_test_flag(zchan, ZAP_CHANNEL_PROGRESS) ||
|
||||||
|
zap_test_flag(zchan, ZAP_CHANNEL_MEDIA) || zap_test_sflag(zchan, SFLAG_RECVD_ACK)) {
|
||||||
|
|
||||||
sangomabc_exec_command(mcon,
|
sangomabc_exec_command(mcon,
|
||||||
zchan->physical_span_id-1,
|
zchan->physical_span_id-1,
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_STOPPED,
|
SIGBOOST_EVENT_CALL_STOPPED,
|
||||||
zchan->caller_data.hangup_cause);
|
zchan->caller_data.hangup_cause, 0);
|
||||||
} else {
|
} else {
|
||||||
sangomabc_exec_command(mcon,
|
sangomabc_exec_command(mcon,
|
||||||
zchan->physical_span_id-1,
|
zchan->physical_span_id-1,
|
||||||
zchan->physical_chan_id-1,
|
zchan->physical_chan_id-1,
|
||||||
0,
|
0,
|
||||||
SIGBOOST_EVENT_CALL_START_NACK,
|
SIGBOOST_EVENT_CALL_START_NACK,
|
||||||
zchan->caller_data.hangup_cause);
|
zchan->caller_data.hangup_cause, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ZAP_CHANNEL_STATE_TERMINATING:
|
case ZAP_CHANNEL_STATE_TERMINATING:
|
||||||
{
|
{
|
||||||
|
zap_set_sflag_locked(zchan, SFLAG_TERMINATING);
|
||||||
sig.event_id = ZAP_SIGEVENT_STOP;
|
sig.event_id = ZAP_SIGEVENT_STOP;
|
||||||
status = sangoma_boost_data->signal_cb(&sig);
|
status = sangoma_boost_data->signal_cb(&sig);
|
||||||
|
zap_set_state_locked(zchan, ZAP_CHANNEL_STATE_HANGUP_COMPLETE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
@ -1219,7 +1191,7 @@ static __inline__ void check_state(zap_span_t *span)
|
||||||
0,
|
0,
|
||||||
-1,
|
-1,
|
||||||
SIGBOOST_EVENT_SYSTEM_RESTART_ACK,
|
SIGBOOST_EVENT_SYSTEM_RESTART_ACK,
|
||||||
0);
|
0, 0);
|
||||||
zap_clear_flag(sangoma_boost_data, ZAP_SANGOMA_BOOST_RESTARTING);
|
zap_clear_flag(sangoma_boost_data, ZAP_SANGOMA_BOOST_RESTARTING);
|
||||||
zap_clear_flag_locked(span, ZAP_SPAN_SUSPENDED);
|
zap_clear_flag_locked(span, ZAP_SPAN_SUSPENDED);
|
||||||
zap_clear_flag((&sangoma_boost_data->mcon), MSU_FLAG_DOWN);
|
zap_clear_flag((&sangoma_boost_data->mcon), MSU_FLAG_DOWN);
|
||||||
|
@ -1471,19 +1443,32 @@ static zap_state_map_t boost_state_map = {
|
||||||
ZSD_OUTBOUND,
|
ZSD_OUTBOUND,
|
||||||
ZSM_UNACCEPTABLE,
|
ZSM_UNACCEPTABLE,
|
||||||
{ZAP_CHANNEL_STATE_DOWN, ZAP_END},
|
{ZAP_CHANNEL_STATE_DOWN, ZAP_END},
|
||||||
|
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS, ZAP_CHANNEL_STATE_IDLE, ZAP_CHANNEL_STATE_HOLD, ZAP_END}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
ZSD_OUTBOUND,
|
||||||
|
ZSM_UNACCEPTABLE,
|
||||||
|
{ZAP_CHANNEL_STATE_HOLD, ZAP_END},
|
||||||
|
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS,
|
||||||
|
ZAP_CHANNEL_STATE_IDLE, ZAP_CHANNEL_STATE_TERMINATING, ZAP_CHANNEL_STATE_UP, ZAP_END}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
ZSD_OUTBOUND,
|
||||||
|
ZSM_UNACCEPTABLE,
|
||||||
|
{ZAP_CHANNEL_STATE_IDLE, ZAP_END},
|
||||||
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS, ZAP_END}
|
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS, ZAP_END}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
ZSD_OUTBOUND,
|
ZSD_OUTBOUND,
|
||||||
ZSM_UNACCEPTABLE,
|
ZSM_UNACCEPTABLE,
|
||||||
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS, ZAP_END},
|
{ZAP_CHANNEL_STATE_PROGRESS_MEDIA, ZAP_CHANNEL_STATE_PROGRESS, ZAP_CHANNEL_STATE_IDLE, ZAP_END},
|
||||||
{ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_CHANNEL_STATE_UP, ZAP_END}
|
{ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_CHANNEL_STATE_UP, ZAP_END}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
ZSD_OUTBOUND,
|
ZSD_OUTBOUND,
|
||||||
ZSM_UNACCEPTABLE,
|
ZSM_UNACCEPTABLE,
|
||||||
{ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_END},
|
{ZAP_CHANNEL_STATE_HANGUP, ZAP_CHANNEL_STATE_TERMINATING, ZAP_END},
|
||||||
{ZAP_CHANNEL_STATE_HANGUP_COMPLETE, ZAP_CHANNEL_STATE_HANGUP, ZAP_END}
|
{ZAP_CHANNEL_STATE_HANGUP_COMPLETE, ZAP_END}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
ZSD_OUTBOUND,
|
ZSD_OUTBOUND,
|
||||||
|
|
|
@ -198,13 +198,14 @@ int sangomabc_connection_open(sangomabc_connection_t *mcon, char *local_ip, int
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int sangomabc_exec_command(sangomabc_connection_t *mcon, int span, int chan, int id, int cmd, int cause)
|
int sangomabc_exec_command(sangomabc_connection_t *mcon, int span, int chan, int id, int cmd, int cause, int flags)
|
||||||
{
|
{
|
||||||
sangomabc_short_event_t oevent;
|
sangomabc_short_event_t oevent;
|
||||||
int retry = 5;
|
int retry = 5;
|
||||||
|
|
||||||
sangomabc_event_init(&oevent, cmd, chan, span);
|
sangomabc_event_init(&oevent, cmd, chan, span);
|
||||||
oevent.release_cause = cause;
|
oevent.release_cause = cause;
|
||||||
|
oevent.flags = flags;
|
||||||
|
|
||||||
if (cmd == SIGBOOST_EVENT_SYSTEM_RESTART || cmd == SIGBOOST_EVENT_SYSTEM_RESTART_ACK) {
|
if (cmd == SIGBOOST_EVENT_SYSTEM_RESTART || cmd == SIGBOOST_EVENT_SYSTEM_RESTART_ACK) {
|
||||||
mcon->rxseq_reset = 1;
|
mcon->rxseq_reset = 1;
|
||||||
|
|
|
@ -130,7 +130,7 @@ int __sangomabc_connection_writep(sangomabc_connection_t *mcon, sangomabc_event_
|
||||||
void sangomabc_event_init(sangomabc_short_event_t *event, sangomabc_event_id_t event_id, int chan, int span);
|
void sangomabc_event_init(sangomabc_short_event_t *event, sangomabc_event_id_t event_id, int chan, int span);
|
||||||
void sangomabc_call_init(sangomabc_event_t *event, const char *calling, const char *called, int setup_id);
|
void sangomabc_call_init(sangomabc_event_t *event, const char *calling, const char *called, int setup_id);
|
||||||
const char *sangomabc_event_id_name(uint32_t event_id);
|
const char *sangomabc_event_id_name(uint32_t event_id);
|
||||||
int sangomabc_exec_command(sangomabc_connection_t *mcon, int span, int chan, int id, int cmd, int cause);
|
int sangomabc_exec_command(sangomabc_connection_t *mcon, int span, int chan, int id, int cmd, int cause, int flags);
|
||||||
int sangomabc_exec_commandp(sangomabc_connection_t *pcon, int span, int chan, int id, int cmd, int cause);
|
int sangomabc_exec_commandp(sangomabc_connection_t *pcon, int span, int chan, int id, int cmd, int cause);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
#ifndef _SIGBOOST_H_
|
#ifndef _SIGBOOST_H_
|
||||||
#define _SIGBOOST_H_
|
#define _SIGBOOST_H_
|
||||||
|
|
||||||
#define SIGBOOST_VERSION 100
|
#define SIGBOOST_VERSION 101
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <sys/time.h>
|
#include <sys/time.h>
|
||||||
|
@ -76,6 +76,11 @@ enum e_sigboost_event_info_par_values
|
||||||
SIGBOOST_EVI_PROGRESS = 0x02,
|
SIGBOOST_EVI_PROGRESS = 0x02,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum e_sigboost_progress_flags
|
||||||
|
{
|
||||||
|
SIGBOOST_PROGRESS_RING = (1 << 0),
|
||||||
|
SIGBOOST_PROGRESS_MEDIA = (1 << 1)
|
||||||
|
};
|
||||||
|
|
||||||
#define MAX_DIALED_DIGITS 31
|
#define MAX_DIALED_DIGITS 31
|
||||||
|
|
||||||
|
@ -108,6 +113,7 @@ typedef struct
|
||||||
uint32_t trunk_group;
|
uint32_t trunk_group;
|
||||||
uint8_t span;
|
uint8_t span;
|
||||||
uint8_t chan;
|
uint8_t chan;
|
||||||
|
uint32_t flags;
|
||||||
/* struct timeval tv; */
|
/* struct timeval tv; */
|
||||||
uint8_t called_number_digits_count;
|
uint8_t called_number_digits_count;
|
||||||
char called_number_digits [MAX_DIALED_DIGITS + 1]; /* it's a null terminated string */
|
char called_number_digits [MAX_DIALED_DIGITS + 1]; /* it's a null terminated string */
|
||||||
|
@ -136,6 +142,7 @@ typedef struct
|
||||||
uint32_t trunk_group;
|
uint32_t trunk_group;
|
||||||
uint8_t span;
|
uint8_t span;
|
||||||
uint8_t chan;
|
uint8_t chan;
|
||||||
|
uint32_t flags;
|
||||||
/* struct timeval tv; */
|
/* struct timeval tv; */
|
||||||
uint8_t release_cause;
|
uint8_t release_cause;
|
||||||
} t_sigboost_short;
|
} t_sigboost_short;
|
||||||
|
|
Loading…
Reference in New Issue