int lpwrap_init_pri(struct lpwrap_pri *spri, ftdm_span_t *span, ftdm_channel_t *dchan, int swtype, int node, int debug) { int ret = -1; memset(spri, 0, sizeof(struct lpwrap_pri)); spri->dchan = dchan; spri->span = span; if (!spri->dchan) { ftdm_log(FTDM_LOG_ERROR, "No D-Channel available, unable to create PRI\n"); return ret; } if ((spri->pri = pri_new_cb(spri->dchan->sockfd, node, swtype, __pri_lpwrap_read, __pri_lpwrap_write, spri))) { unsigned char buf[4] = { 0 }; size_t buflen = sizeof(buf), len = 0; pri_set_debug(spri->pri, debug); #ifdef HAVE_LIBPRI_AOC pri_aoc_events_enable(spri->pri, 1); #endif ftdm_channel_write(spri->dchan, buf, buflen, &len); ret = 0; } else { ftdm_log(FTDM_LOG_ERROR, "Unable to create PRI\n"); } return ret; }
int sangoma_init_pri(struct sangoma_pri *spri, int span, int dchan, int swtype, int node, int debug) { int ret = -1; ftdm_socket_t dfd = 0; memset(spri, 0, sizeof(struct sangoma_pri)); if (ftdm_channel_open(span, dchan, &spri->zdchan) != FTDM_SUCCESS) { fprintf(stderr, "Unable to open DCHAN %d for span %d (%s)\n", dchan, span, strerror(errno)); } else { if ((spri->pri = pri_new_cb(spri->zdchan->sockfd, node, swtype, __pri_sangoma_read, __pri_sangoma_write, spri))){ spri->span = span; pri_set_debug(spri->pri, debug); ret = 0; } else { fprintf(stderr, "Unable to create PRI\n"); } } return ret; }
int sangoma_init_pri(struct sangoma_pri *spri, int span, int dchan, int swtype, int node, int debug) { int ret = -1; sng_fd_t dfd = 0; memset(spri, 0, sizeof(struct sangoma_pri)); if((dfd = sangoma_open_tdmapi_span_chan(span, dchan)) < 0) { sbridge_log(SBRIDGE_LOG_ERROR, "Unable to open PRI DCHAN %d for span %d (%s)\n", dchan, span, sbridge_os_get_last_error()); } else { if ((spri->pri = pri_new_cb((int)dfd, node, swtype, __pri_sangoma_read, __pri_sangoma_write, NULL))){ spri->span = span; pri_set_debug(spri->pri, debug); sbridge_mutex_initialize(&spri->lock); ret = 0; } else { sbridge_log(SBRIDGE_LOG_ERROR, "Unable to create PRI for span %d\n", span); } } return ret; }
int lpwrap_init_pri(struct lpwrap_pri *spri, zap_span_t *span, zap_channel_t *dchan, int swtype, int node, int debug) { int ret = -1; memset(spri, 0, sizeof(struct lpwrap_pri)); spri->dchan = dchan; spri->span = span; if ((spri->pri = pri_new_cb(spri->dchan->sockfd, node, swtype, __pri_lpwrap_read, __pri_lpwrap_write, spri))){ unsigned char buf[4] = { 0 }; size_t buflen = sizeof(buf), len = 0; pri_set_debug(spri->pri, debug); ret = 0; zap_set_flag(spri, LPWRAP_PRI_READY); zap_channel_write(spri->dchan, buf, buflen, &len); } else { fprintf(stderr, "Unable to create PRI\n"); } return ret; }
static void *ftdm_pritap_run(ftdm_thread_t *me, void *obj) { ftdm_span_t *span = (ftdm_span_t *) obj; ftdm_span_t *peer = NULL; pritap_t *pritap = span->signal_data; pritap_t *p_pritap = NULL; pri_event *event = NULL; struct pollfd dpoll[2]; int rc = 0; ftdm_log(FTDM_LOG_DEBUG, "Tapping PRI thread started on span %s\n", span->name); pritap->span = span; ftdm_set_flag(span, FTDM_SPAN_IN_THREAD); if (ftdm_channel_open(span->span_id, pritap->dchan->chan_id, &pritap->dchan) != FTDM_SUCCESS) { ftdm_log(FTDM_LOG_ERROR, "Failed to open D-channel for span %s\n", span->name); goto done; } if ((pritap->pri = pri_new_cb(pritap->dchan->sockfd, PRI_NETWORK, PRI_SWITCH_NI2, pri_io_read, pri_io_write, pritap))) { pri_set_debug(pritap->pri, pritap->debug); } else { ftdm_log(FTDM_LOG_CRIT, "Failed to create tapping PRI\n"); goto done; } /* The last span starting runs the show ... * This simplifies locking and avoid races by having multiple threads for a single tapped link * Since both threads really handle a single tapped link there is no benefit on multi-threading, just complications ... */ peer = pritap->peerspan; p_pritap = peer->signal_data; if (!ftdm_test_flag(pritap, PRITAP_MASTER)) { ftdm_log(FTDM_LOG_DEBUG, "Running dummy thread on span %s\n", span->name); while (ftdm_running() && !ftdm_test_flag(span, FTDM_SPAN_STOP_THREAD)) { poll(NULL, 0, 100); } } else { memset(&dpoll, 0, sizeof(dpoll)); dpoll[0].fd = pritap->dchan->sockfd; dpoll[1].fd = p_pritap->dchan->sockfd; ftdm_log(FTDM_LOG_DEBUG, "Master tapping thread on span %s (fd1=%d, fd2=%d)\n", span->name, pritap->dchan->sockfd, p_pritap->dchan->sockfd); while (ftdm_running() && !ftdm_test_flag(span, FTDM_SPAN_STOP_THREAD)) { pritap_check_state(span); pritap_check_state(peer); dpoll[0].revents = 0; dpoll[0].events = POLLIN; dpoll[1].revents = 0; dpoll[1].events = POLLIN; rc = poll(&dpoll[0], 2, 10); if (rc < 0) { if (errno == EINTR) { ftdm_log(FTDM_LOG_DEBUG, "D-channel waiting interrupted, continuing ...\n"); continue; } ftdm_log(FTDM_LOG_ERROR, "poll failed: %s\n", strerror(errno)); continue; } pri_schedule_run(pritap->pri); pri_schedule_run(p_pritap->pri); pritap_check_state(span); pritap_check_state(peer); if (rc) { if (dpoll[0].revents & POLLIN) { event = pri_read_event(pritap->pri); if (event) { handle_pri_passive_event(pritap, event); pritap_check_state(span); } } if (dpoll[1].revents & POLLIN) { event = pri_read_event(p_pritap->pri); if (event) { handle_pri_passive_event(p_pritap, event); pritap_check_state(peer); } } } } } done: ftdm_log(FTDM_LOG_DEBUG, "Tapping PRI thread ended on span %s\n", span->name); ftdm_clear_flag(span, FTDM_SPAN_IN_THREAD); ftdm_clear_flag(pritap, PRITAP_RUNNING); ftdm_clear_flag(pritap, PRITAP_MASTER); return NULL; }