added hardware link notification
git-svn-id: http://svn.openzap.org/svn/openzap/branches/sangoma_boost@871 a93c3328-9c30-0410-af19-c9cd2b2d52af
This commit is contained in:
parent
c557472f25
commit
c6cf9e61cd
|
@ -140,7 +140,6 @@ typedef enum {
|
|||
ZAP_STR2ENUM_P(zap_str2zap_analog_start_type, zap_analog_start_type2str, zap_analog_start_type_t)
|
||||
|
||||
typedef enum {
|
||||
ZAP_OOB_DTMF,
|
||||
ZAP_OOB_ONHOOK,
|
||||
ZAP_OOB_OFFHOOK,
|
||||
ZAP_OOB_WINK,
|
||||
|
@ -212,10 +211,13 @@ typedef enum {
|
|||
ZAP_SIGEVENT_RESTART,
|
||||
/* Signaling link status changed (D-chan up, down, R2 blocked etc) */
|
||||
ZAP_SIGEVENT_SIGSTATUS_CHANGED,
|
||||
/* Hardware link status changed (Line connected, disconnected) */
|
||||
ZAP_SIGEVENT_HWSTATUS_CHANGED,
|
||||
ZAP_SIGEVENT_INVALID
|
||||
} zap_signal_event_t;
|
||||
#define SIGNAL_STRINGS "START", "STOP", "TRANSFER", "ANSWER", "UP", "FLASH", "PROGRESS", \
|
||||
"PROGRESS_MEDIA", "NOTIFY", "TONE_DETECTED", "ALARM_TRAP", "ALARM_CLEAR", "MISC", "COLLECTED_DIGIT", "ADD_CALL", "RESTART", "SIGLINK_CHANGED", "INVALID"
|
||||
"PROGRESS_MEDIA", "NOTIFY", "TONE_DETECTED", "ALARM_TRAP", "ALARM_CLEAR", "MISC", \
|
||||
"COLLECTED_DIGIT", "ADD_CALL", "RESTART", "SIGLINK_CHANGED", "HWSTATUS_CHANGED", "INVALID"
|
||||
ZAP_STR2ENUM_P(zap_str2zap_signal_event, zap_signal_event2str, zap_signal_event_t)
|
||||
|
||||
typedef enum {
|
||||
|
@ -421,10 +423,10 @@ struct zap_state_map {
|
|||
};
|
||||
typedef struct zap_state_map zap_state_map_t;
|
||||
|
||||
typedef enum zap_hw_link_status {
|
||||
typedef enum zap_channel_hw_link_status {
|
||||
ZAP_HW_LINK_DISCONNECTED = 0,
|
||||
ZAP_HW_LINK_CONNECTED
|
||||
} zap_hw_link_status_t;
|
||||
} zap_channel_hw_link_status_t;
|
||||
|
||||
typedef struct zap_channel zap_channel_t;
|
||||
typedef struct zap_event zap_event_t;
|
||||
|
|
|
@ -874,35 +874,6 @@ static __inline__ zap_status_t process_event(zap_span_t *span, zap_event_t *even
|
|||
zap_set_state_locked(event->channel, ZAP_CHANNEL_STATE_DOWN);
|
||||
}
|
||||
}
|
||||
case ZAP_OOB_DTMF:
|
||||
{
|
||||
const char * digit_str = (const char *)event->data;
|
||||
if(digit_str) {
|
||||
if (event->channel->state == ZAP_CHANNEL_STATE_CALLWAITING && (*digit_str == 'D' || *digit_str == 'A')) {
|
||||
event->channel->detected_tones[ZAP_TONEMAP_CALLWAITING_ACK]++;
|
||||
} else {
|
||||
zio_event_cb_t event_callback = NULL;
|
||||
|
||||
zap_channel_queue_dtmf(event->channel, digit_str);
|
||||
if (span->event_callback) {
|
||||
event_callback = span->event_callback;
|
||||
} else if (event->channel->event_callback) {
|
||||
event_callback = event->channel->event_callback;
|
||||
}
|
||||
|
||||
if (event_callback) {
|
||||
event->channel->event_header.channel = event->channel;
|
||||
event->channel->event_header.e_type = ZAP_EVENT_DTMF;
|
||||
event->channel->event_header.data = (void *)digit_str;
|
||||
event_callback(event->channel, &event->channel->event_header);
|
||||
event->channel->event_header.e_type = ZAP_EVENT_NONE;
|
||||
event->channel->event_header.data = NULL;
|
||||
}
|
||||
|
||||
}
|
||||
zap_safe_free(event->data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
end:
|
||||
|
|
|
@ -1519,7 +1519,8 @@ static __inline__ zap_status_t process_event(zap_span_t *span, zap_event_t *even
|
|||
switch(event->enum_id) {
|
||||
case ZAP_OOB_ALARM_TRAP:
|
||||
{
|
||||
sig.event_id = ZAP_OOB_ALARM_TRAP;
|
||||
sig.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sig.raw_data = (void *)ZAP_HW_LINK_DISCONNECTED;
|
||||
if (event->channel->state != ZAP_CHANNEL_STATE_DOWN) {
|
||||
if (event->channel->type == ZAP_CHAN_TYPE_B) {
|
||||
zap_set_state_locked(event->channel, ZAP_CHANNEL_STATE_RESTART);
|
||||
|
@ -1544,7 +1545,8 @@ static __inline__ zap_status_t process_event(zap_span_t *span, zap_event_t *even
|
|||
zap_log(ZAP_LOG_WARNING, "channel %d:%d (%d:%d) alarms Cleared!\n", event->channel->span_id, event->channel->chan_id,
|
||||
event->channel->physical_span_id, event->channel->physical_chan_id);
|
||||
|
||||
sig.event_id = ZAP_OOB_ALARM_CLEAR;
|
||||
sig.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sig.raw_data = (void *)ZAP_HW_LINK_CONNECTED;
|
||||
zap_clear_flag(event->channel, ZAP_CHANNEL_SUSPENDED);
|
||||
zap_channel_get_alarms(event->channel);
|
||||
isdn_data->sig_cb(&sig);
|
||||
|
|
|
@ -820,7 +820,8 @@ static __inline__ zap_status_t process_event(zap_span_t *span, zap_event_t *even
|
|||
switch(event->enum_id) {
|
||||
case ZAP_OOB_ALARM_TRAP:
|
||||
{
|
||||
sig.event_id = ZAP_OOB_ALARM_TRAP;
|
||||
sig.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sig.raw_data = (void *)ZAP_HW_LINK_CONNECTED;
|
||||
if (event->channel->state != ZAP_CHANNEL_STATE_DOWN) {
|
||||
if (event->channel->type == ZAP_CHAN_TYPE_B) {
|
||||
zap_set_state_locked(event->channel, ZAP_CHANNEL_STATE_RESTART);
|
||||
|
@ -845,7 +846,8 @@ static __inline__ zap_status_t process_event(zap_span_t *span, zap_event_t *even
|
|||
zap_log(ZAP_LOG_WARNING, "channel %d:%d (%d:%d) alarms Cleared!\n", event->channel->span_id, event->channel->chan_id,
|
||||
event->channel->physical_span_id, event->channel->physical_chan_id);
|
||||
|
||||
sig.event_id = ZAP_OOB_ALARM_CLEAR;
|
||||
sig.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sig.raw_data = (void *)ZAP_HW_LINK_CONNECTED;
|
||||
zap_clear_flag(event->channel, ZAP_CHANNEL_SUSPENDED);
|
||||
zap_channel_get_alarms(event->channel);
|
||||
isdn_data->sig_cb(&sig);
|
||||
|
|
|
@ -1088,6 +1088,10 @@ static __inline__ void check_state(zap_span_t *span)
|
|||
static __inline__ void check_events(zap_span_t *span, int ms_timeout)
|
||||
{
|
||||
zap_status_t status;
|
||||
zap_sigmsg_t sigmsg;
|
||||
zap_sangoma_boost_data_t *sangoma_boost_data = span->signal_data;
|
||||
|
||||
memset(&sigmsg, 0, sizeof(sigmsg));
|
||||
|
||||
status = zap_span_poll_event(span, ms_timeout);
|
||||
|
||||
|
@ -1096,9 +1100,27 @@ static __inline__ void check_events(zap_span_t *span, int ms_timeout)
|
|||
{
|
||||
zap_event_t *event;
|
||||
while (zap_span_next_event(span, &event) == ZAP_SUCCESS) {
|
||||
// for now we do nothing with events, this is here
|
||||
// just to have the hardware layer to get any HW DTMF
|
||||
// events and enqueue the DTMF on the channel (done during zap_span_next_event())
|
||||
sigmsg.span_id = event->channel->span_id;
|
||||
sigmsg.chan_id = event->channel->chan_id;
|
||||
sigmsg.channel = event->channel;
|
||||
switch (event->enum_id) {
|
||||
case ZAP_OOB_ALARM_TRAP:
|
||||
sigmsg.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sigmsg.raw_data = (void *)ZAP_HW_LINK_DISCONNECTED;
|
||||
if (sangoma_boost_data->sigmod) {
|
||||
sangoma_boost_data->sigmod->on_hw_link_status_change(event->channel, ZAP_HW_LINK_DISCONNECTED);
|
||||
}
|
||||
sangoma_boost_data->signal_cb(&sigmsg);
|
||||
break;
|
||||
case ZAP_OOB_ALARM_CLEAR:
|
||||
sigmsg.event_id = ZAP_SIGEVENT_HWSTATUS_CHANGED;
|
||||
sigmsg.raw_data = (void *)ZAP_HW_LINK_CONNECTED;
|
||||
if (sangoma_boost_data->sigmod) {
|
||||
sangoma_boost_data->sigmod->on_hw_link_status_change(event->channel, ZAP_HW_LINK_CONNECTED);
|
||||
}
|
||||
sangoma_boost_data->signal_cb(&sigmsg);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -1523,7 +1545,6 @@ static BOOST_SIG_STATUS_CB_FUNCTION(zap_boost_sig_status_change)
|
|||
sig.channel = zchan;
|
||||
sig.event_id = ZAP_SIGEVENT_SIGSTATUS_CHANGED;
|
||||
sig.raw_data = &status;
|
||||
sig.raw_data_len = sizeof(status);
|
||||
sangoma_boost_data->signal_cb(&sig);
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -85,15 +85,24 @@ typedef void (*boost_set_sig_status_cb_func_t) BOOST_SET_SIG_STATUS_CB_ARGS;
|
|||
#define BOOST_SET_SIG_STATUS_CB_FUNCTION(name) void name BOOST_SET_SIG_STATUS_CB_ARGS
|
||||
|
||||
/*!
|
||||
\brief Get the signaling status on the given channel.
|
||||
\brief Notify hardware status change
|
||||
\param zchan The openzap channel
|
||||
\param status The status pointer where the current signaling status will be set
|
||||
\param status The hw status
|
||||
\return ZAP_SUCCESS or ZAP_FAIL
|
||||
*/
|
||||
#define BOOST_GET_SIG_STATUS_ARGS (zap_channel_t *zchan, zap_channel_sig_status_t *status)
|
||||
typedef zap_status_t (*boost_get_sig_status_func_t) BOOST_GET_SIG_STATUS_ARGS;
|
||||
#define BOOST_GET_SIG_STATUS_FUNCTION(name) zap_status_t name BOOST_GET_SIG_STATUS_ARGS
|
||||
|
||||
/*!
|
||||
\brief Get the signaling status on the given channel.
|
||||
\param zchan The openzap channel
|
||||
\param status The status pointer where the current signaling status will be set
|
||||
*/
|
||||
#define BOOST_ON_HW_STATUS_CHANGE_ARGS (zap_channel_t *zchan, zap_channel_hw_link_status_t status)
|
||||
typedef void (*boost_on_hw_link_status_change_t) BOOST_ON_HW_STATUS_CHANGE_ARGS;
|
||||
#define BOOST_ON_HW_STATUS_CHANGE_FUNCTION(name) void name BOOST_ON_HW_STATUS_CHANGE_ARGS
|
||||
|
||||
/*!
|
||||
\brief Set the signaling status on the given channel.
|
||||
\param zchan The openzap channel
|
||||
|
@ -148,6 +157,8 @@ typedef struct boost_sigmod_interface_s {
|
|||
boost_get_sig_status_func_t get_sig_status;
|
||||
/*! \brief set channel signaling status */
|
||||
boost_set_sig_status_func_t set_sig_status;
|
||||
/*! \brief set notify hardware link status change */
|
||||
boost_on_hw_link_status_change_t on_hw_link_status_change;
|
||||
/*! \brief configure span signaling */
|
||||
boost_configure_span_func_t configure_span;
|
||||
/*! \brief start openzap span */
|
||||
|
|
|
@ -597,7 +597,7 @@ static ZIO_COMMAND_FUNCTION(wanpipe_command)
|
|||
break;
|
||||
case ZAP_COMMAND_SET_LINK_STATUS:
|
||||
{
|
||||
zap_hw_link_status_t status = ZAP_COMMAND_OBJ_INT;
|
||||
zap_channel_hw_link_status_t status = ZAP_COMMAND_OBJ_INT;
|
||||
char sangoma_status = status == ZAP_HW_LINK_CONNECTED ? FE_CONNECTED : FE_DISCONNECTED;
|
||||
err = sangoma_tdm_set_fe_status(zchan->sockfd, &tdm_api, sangoma_status);
|
||||
}
|
||||
|
@ -741,30 +741,24 @@ static ZIO_WAIT_FUNCTION(wanpipe_wait)
|
|||
ZIO_SPAN_POLL_EVENT_FUNCTION(wanpipe_poll_event)
|
||||
{
|
||||
#ifdef LIBSANGOMA_VERSION
|
||||
sangoma_status_t sangstatus;
|
||||
sangoma_status_t sangstatus;
|
||||
sangoma_wait_obj_t *pfds[ZAP_MAX_CHANNELS_SPAN] = { 0 };
|
||||
uint32_t inflags[ZAP_MAX_CHANNELS_SPAN];
|
||||
uint32_t outflags[ZAP_MAX_CHANNELS_SPAN];
|
||||
uint32_t inflags[ZAP_MAX_CHANNELS_SPAN];
|
||||
uint32_t outflags[ZAP_MAX_CHANNELS_SPAN];
|
||||
#else
|
||||
struct pollfd pfds[ZAP_MAX_CHANNELS_SPAN];
|
||||
#endif
|
||||
|
||||
uint32_t i, j = 0, k = 0, l = 0;
|
||||
int r;
|
||||
|
||||
for(i = 1; i <= span->chan_count; i++) {
|
||||
zap_channel_t *zchan = span->channels[i];
|
||||
|
||||
if (!strncasecmp(span->name, "smg_prid_nfas", 8) && span->trunk_type == ZAP_TRUNK_T1 && zchan->physical_chan_id == 24) {
|
||||
continue;
|
||||
}
|
||||
|
||||
#ifdef LIBSANGOMA_VERSION
|
||||
if (!zchan->mod_data) {
|
||||
continue; /* should never happen but happens when shutting down */
|
||||
}
|
||||
pfds[j] = zchan->mod_data;
|
||||
inflags[j] = POLLPRI;
|
||||
inflags[j] = POLLPRI;
|
||||
#else
|
||||
memset(&pfds[j], 0, sizeof(pfds[j]));
|
||||
pfds[j].fd = span->channels[i]->sockfd;
|
||||
|
@ -772,7 +766,6 @@ ZIO_SPAN_POLL_EVENT_FUNCTION(wanpipe_poll_event)
|
|||
#endif
|
||||
|
||||
/* The driver probably should be able to do this wink/flash/ringing by itself this is sort of a hack to make it work! */
|
||||
|
||||
if (zap_test_flag(zchan, ZAP_CHANNEL_WINK) || zap_test_flag(zchan, ZAP_CHANNEL_FLASH)) {
|
||||
l = 5;
|
||||
}
|
||||
|
@ -788,7 +781,7 @@ ZIO_SPAN_POLL_EVENT_FUNCTION(wanpipe_poll_event)
|
|||
int err;
|
||||
memset(&tdm_api, 0, sizeof(tdm_api));
|
||||
if (zap_test_pflag(zchan, WP_RINGING)) {
|
||||
err=sangoma_tdm_txsig_offhook(zchan->sockfd,&tdm_api);
|
||||
err = sangoma_tdm_txsig_offhook(zchan->sockfd,&tdm_api);
|
||||
if (err) {
|
||||
snprintf(zchan->last_error, sizeof(zchan->last_error), "Ring-off Failed");
|
||||
return ZAP_FAIL;
|
||||
|
@ -812,13 +805,13 @@ ZIO_SPAN_POLL_EVENT_FUNCTION(wanpipe_poll_event)
|
|||
}
|
||||
#ifdef LIBSANGOMA_VERSION
|
||||
sangstatus = sangoma_waitfor_many(pfds, inflags, outflags, j, ms);
|
||||
if (SANG_STATUS_APIPOLL_TIMEOUT == sangstatus) {
|
||||
r = 0;
|
||||
} else if (SANG_STATUS_SUCCESS == sangstatus) {
|
||||
r = 1; /* hopefully we never need how many changed -_- */
|
||||
} else {
|
||||
r = -1;
|
||||
}
|
||||
if (SANG_STATUS_APIPOLL_TIMEOUT == sangstatus) {
|
||||
r = 0;
|
||||
} else if (SANG_STATUS_SUCCESS == sangstatus) {
|
||||
r = 1; /* hopefully we never need how many changed -_- */
|
||||
} else {
|
||||
r = -1;
|
||||
}
|
||||
#else
|
||||
r = poll(pfds, j, ms);
|
||||
#endif
|
||||
|
@ -863,15 +856,15 @@ static ZIO_GET_ALARMS_FUNCTION(wanpipe_get_alarms)
|
|||
|
||||
#ifdef LIBSANGOMA_VERSION
|
||||
if ((err = sangoma_tdm_get_fe_alarms(zchan->sockfd, &tdm_api, &alarms))) {
|
||||
snprintf(zchan->last_error, sizeof(zchan->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
snprintf(zchan->span->last_error, sizeof(zchan->span->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
return ZAP_FAIL;
|
||||
snprintf(zchan->last_error, sizeof(zchan->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
snprintf(zchan->span->last_error, sizeof(zchan->span->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
return ZAP_FAIL;
|
||||
}
|
||||
#else
|
||||
if ((err = sangoma_tdm_get_fe_alarms(zchan->sockfd, &tdm_api)) < 0){
|
||||
snprintf(zchan->last_error, sizeof(zchan->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
snprintf(zchan->span->last_error, sizeof(zchan->span->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
return ZAP_FAIL;
|
||||
snprintf(zchan->last_error, sizeof(zchan->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
snprintf(zchan->span->last_error, sizeof(zchan->span->last_error), "ioctl failed (%s)", strerror(errno));
|
||||
return ZAP_FAIL;
|
||||
}
|
||||
alarms = tdm_api.wp_tdm_cmd.fe_alarms;
|
||||
#endif
|
||||
|
@ -1003,24 +996,25 @@ ZIO_SPAN_NEXT_EVENT_FUNCTION(wanpipe_next_event)
|
|||
span->channels[i]->rx_cas_bits = wanpipe_swap_bits(tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_rbs_bits);
|
||||
}
|
||||
break;
|
||||
case WP_TDMAPI_EVENT_DTMF:
|
||||
{
|
||||
char tmp_dtmf[2] = { tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_digit, 0 };
|
||||
case WP_TDMAPI_EVENT_DTMF:
|
||||
{
|
||||
char tmp_dtmf[2] = { tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_digit, 0 };
|
||||
event_id = ZAP_OOB_NOOP;
|
||||
|
||||
//zap_log(ZAP_LOG_DEBUG, "%d:%d queue hardware dtmf %s\n", zchan->span_id, zchan->chan_id, tmp_dtmf);
|
||||
if (tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_type == WAN_EC_TONE_PRESENT) {
|
||||
if (tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_type == WAN_EC_TONE_PRESENT) {
|
||||
zap_set_flag_locked(zchan, ZAP_CHANNEL_MUTE);
|
||||
}
|
||||
|
||||
if (tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_type == WAN_EC_TONE_STOP) {
|
||||
if (tdm_api.wp_tdm_cmd.event.wp_tdm_api_event_dtmf_type == WAN_EC_TONE_STOP) {
|
||||
zap_clear_flag_locked(zchan, ZAP_CHANNEL_MUTE);
|
||||
zap_channel_queue_dtmf(zchan, tmp_dtmf);
|
||||
}
|
||||
}
|
||||
break;
|
||||
zap_channel_queue_dtmf(zchan, tmp_dtmf);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case WP_TDMAPI_EVENT_ALARM:
|
||||
event_id = ZAP_OOB_NOOP;
|
||||
{
|
||||
event_id = ZAP_OOB_NOOP;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue