123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167 |
- #include "precompile.h"
- #include "audiodtmf.h"
- #include "audiocontext.h"
- #include "audiolog.h"
- #include "audiostream.h"
- #define TX_DTMF_INTERVAL 320
- static void process_frame(void *self)
- {
- audiodtmf_t *dtmf = CONTAINING_RECORD(self, audiodtmf_t, base);
- apr_status_t status;
- if (!dtmf->binitialized)
- return;
- if (dtmf->fin)
- return;
- dtmf->progress += FRAME_TIME;
- if (dtmf->bsender) { /* act as sender */
- if (dtmf->progress >= TX_DTMF_INTERVAL) {
- if (dtmf->tx_digits_offset < dtmf->tx_digits_len) { /* send one digit */
- status = audiortp_send_dtmf(dtmf->rtp, dtmf->tx_digits + dtmf->tx_digits_offset, 1);
- if (status == APR_SUCCESS) {
- dtmf->tx_digits_offset ++;
- if (dtmf->tx_digits_offset == dtmf->tx_digits_len) {
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_SENT, 0, 0);
- dtmf->fin = 1;
- }
- } else {
- AUDIO_LOG_ERROR("send dtmf to rtp stream failed!");
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_SENT, status, 0);
- dtmf->fin = 1;
- }
- }
- dtmf->progress -= TX_DTMF_INTERVAL;
- }
- } else { /* act as receiver */
- char tmp[MAX_DTMF];
- unsigned int tmp_cnt = MAX_DTMF;
- if (dtmf->rx_timeout != -1) {
- dtmf->rx_ellapsed += FRAME_TIME;
- if (dtmf->rx_ellapsed >= dtmf->rx_timeout) {
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_RECV, -1, (int)&dtmf->rx_digits[0]);
- dtmf->fin = 1;
- return;
- }
- }
- status = audiortp_recv_dtmf(dtmf->rtp, &tmp[0], &tmp_cnt);
- if (status == APR_SUCCESS) {
- unsigned int i;
- for (i = 0; i < tmp_cnt; ++i) {
- char ch = tmp[i];
- if (ch == dtmf->rx_interdigit) {
- dtmf->rx_digits[dtmf->rx_digits_len] = 0;
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_RECV, 0, (int)&dtmf->rx_digits[0]);
- dtmf->fin = 1;
- } else {
- dtmf->rx_digits[dtmf->rx_digits_len++] = ch;
- if (dtmf->rx_digits_len == dtmf->rx_maxdigits) {
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_RECV, 0, (int)&dtmf->rx_digits[0]);
- dtmf->fin = 1;
- }
- }
- }
- } else {
- AUDIO_LOG_ERROR("recv dtmf from rtp stream failed!");
- audiodriver_raise_event(&dtmf->base, DRIVER_EVT_DTMF_RECV, status, 0);
- dtmf->fin = 1;
- }
- }
- }
- static audiodriver_vtbl_t g_driver_vtbl = {
- &process_frame,
- };
- apr_status_t audiodtmf_create(apr_pool_t *pool, audioengine_t *engine, audiodtmf_t **p_dtmf)
- {
- audiodtmf_t *dtmf;
- dtmf = apr_palloc(pool, sizeof(audiodtmf_t));
- memset(dtmf, 0, sizeof(audiodtmf_t));
- dtmf->rtp = NULL;
- dtmf->bsender = 0;
- dtmf->tx_digits = NULL;
- dtmf->tx_digits_len = 0;
- dtmf->tx_digits_offset = 0;
- dtmf->rx_maxdigits = MAX_DTMF;
- dtmf->rx_interval = 100; // 100ms
- dtmf->rx_timeout = -1;
- dtmf->rx_interdigit = 0;
- dtmf->binitialized = FALSE;
- dtmf->progress = 0;
- audiodriver_init(engine, &g_driver_vtbl, &dtmf->base);
- *p_dtmf = dtmf;
- return APR_SUCCESS;
- }
- void audiodtmf_destroy(audiodtmf_t *dtmf)
- {
- if (dtmf->tx_digits)
- free(dtmf->tx_digits);
- }
- apr_status_t audiodtmf_set_rtpstream(audiodtmf_t *dtmf, audiortp_t* rtp)
- {
- dtmf->rtp = rtp;
- return APR_SUCCESS;
- }
- apr_status_t audiodtmf_set_sender(audiodtmf_t *dtmf, int on)
- {
- dtmf->bsender = !!on;
- return APR_SUCCESS;
- }
- apr_status_t audiodtmf_set_txparam(audiodtmf_t *dtmf, const char *digits, int n)
- {
- if (n == -1)
- n = strlen(digits);
- dtmf->tx_digits_len = n;
- dtmf->tx_digits_offset = 0;
- dtmf->tx_digits = realloc(dtmf->tx_digits, n + 1);
- strncpy(dtmf->tx_digits, digits, n);
- return APR_SUCCESS;
- }
- apr_status_t audiodtmf_set_rxparam(audiodtmf_t *dtmf, int maxdigit, int interval, int interdigit, int timeout)
- {
- dtmf->rx_interdigit = interdigit;
- dtmf->rx_interval = interval;
- dtmf->rx_maxdigits = maxdigit;
- dtmf->rx_timeout = timeout;
- return APR_SUCCESS;
- }
- apr_status_t audiodtmf_init(audiodtmf_t *dtmf)
- {
- if (dtmf->binitialized)
- return APR_EAGAIN;
- if (!dtmf->rtp)
- return APR_EGENERAL;
- if (dtmf->bsender) {
- if (!dtmf->tx_digits)
- return APR_EGENERAL;
- }
- dtmf->binitialized = TRUE;
- dtmf->progress = 0;
- dtmf->rx_digits_len = 0;
- dtmf->rx_ellapsed = 0;
- dtmf->fin = 0;
- return APR_SUCCESS;
- }
- apr_status_t audiodtmf_term(audiodtmf_t *dtmf)
- {
- if (dtmf->binitialized) {
- dtmf->binitialized = FALSE;
- return APR_SUCCESS;
- }
- return APR_EGENERAL;
- }
|