Fri May 26 01:45:36 2006

Asterisk developer's documentation


rtp.c

Go to the documentation of this file.
00001 /*
00002  * Asterisk -- An open source telephony toolkit.
00003  *
00004  * Copyright (C) 1999 - 2005, Digium, Inc.
00005  *
00006  * Mark Spencer <markster@digium.com>
00007  *
00008  * See http://www.asterisk.org for more information about
00009  * the Asterisk project. Please do not directly contact
00010  * any of the maintainers of this project for assistance;
00011  * the project provides a web site, mailing lists and IRC
00012  * channels for your use.
00013  *
00014  * This program is free software, distributed under the terms of
00015  * the GNU General Public License Version 2. See the LICENSE file
00016  * at the top of the source tree.
00017  */
00018 
00019 /*! 
00020  * \file 
00021  * \brief Supports RTP and RTCP with Symmetric RTP support for NAT traversal.
00022  * 
00023  * RTP is deffined in RFC 3550.
00024  */
00025 
00026 #include <stdio.h>
00027 #include <stdlib.h>
00028 #include <string.h>
00029 #include <sys/time.h>
00030 #include <signal.h>
00031 #include <errno.h>
00032 #include <unistd.h>
00033 #include <netinet/in.h>
00034 #include <sys/time.h>
00035 #include <sys/socket.h>
00036 #include <arpa/inet.h>
00037 #include <fcntl.h>
00038 
00039 #include "asterisk.h"
00040 
00041 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 13095 $")
00042 
00043 #include "asterisk/rtp.h"
00044 #include "asterisk/frame.h"
00045 #include "asterisk/logger.h"
00046 #include "asterisk/options.h"
00047 #include "asterisk/channel.h"
00048 #include "asterisk/acl.h"
00049 #include "asterisk/channel.h"
00050 #include "asterisk/config.h"
00051 #include "asterisk/lock.h"
00052 #include "asterisk/utils.h"
00053 #include "asterisk/cli.h"
00054 #include "asterisk/unaligned.h"
00055 #include "asterisk/utils.h"
00056 
00057 #define MAX_TIMESTAMP_SKEW 640
00058 
00059 #define RTP_MTU      1200
00060 
00061 #define DEFAULT_DTMF_TIMEOUT 3000 /* samples */
00062 
00063 static int dtmftimeout = DEFAULT_DTMF_TIMEOUT;
00064 
00065 static int rtpstart = 0;
00066 static int rtpend = 0;
00067 static int rtpdebug = 0;      /* Are we debugging? */
00068 static struct sockaddr_in rtpdebugaddr;   /* Debug packets to/from this host */
00069 #ifdef SO_NO_CHECK
00070 static int nochecksums = 0;
00071 #endif
00072 
00073 /* The value of each payload format mapping: */
00074 struct rtpPayloadType {
00075    int isAstFormat;  /* whether the following code is an AST_FORMAT */
00076    int code;
00077 };
00078 
00079 #define MAX_RTP_PT 256
00080 
00081 #define FLAG_3389_WARNING     (1 << 0)
00082 #define FLAG_NAT_ACTIVE       (3 << 1)
00083 #define FLAG_NAT_INACTIVE     (0 << 1)
00084 #define FLAG_NAT_INACTIVE_NOWARN (1 << 1)
00085 
00086 struct ast_rtp {
00087    int s;
00088    char resp;
00089    struct ast_frame f;
00090    unsigned char rawdata[8192 + AST_FRIENDLY_OFFSET];
00091    /*! Synchronization source, RFC 3550, page 10. */
00092    unsigned int ssrc;
00093    unsigned int lastts;
00094    unsigned int lastdigitts;
00095    unsigned int lastrxts;
00096    unsigned int lastividtimestamp;
00097    unsigned int lastovidtimestamp;
00098    unsigned int lasteventseqn;
00099    unsigned int lasteventendseqn;
00100    int lasttxformat;
00101    int lastrxformat;
00102    int dtmfcount;
00103    unsigned int dtmfduration;
00104    int nat;
00105    unsigned int flags;
00106    /*! Socket representation of the local endpoint. */
00107    struct sockaddr_in us;
00108    /*! Socket representation of the remote endpoint. */
00109    struct sockaddr_in them;
00110    struct timeval rxcore;
00111    struct timeval txcore;
00112    struct timeval dtmfmute;
00113    struct ast_smoother *smoother;
00114    int *ioid;
00115    /*! Sequence number, RFC 3550, page 13. */
00116    unsigned short seqno;
00117    unsigned short rxseqno;
00118    struct sched_context *sched;
00119    struct io_context *io;
00120    void *data;
00121    ast_rtp_callback callback;
00122    struct rtpPayloadType current_RTP_PT[MAX_RTP_PT];
00123    /*! a cache for the result of rtp_lookup_code(): */
00124    int rtp_lookup_code_cache_isAstFormat;
00125    int rtp_lookup_code_cache_code;
00126    int rtp_lookup_code_cache_result;
00127    int rtp_offered_from_local;
00128    struct ast_rtcp *rtcp;
00129 };
00130 
00131 /*!
00132  * \brief Structure defining an RTCP session.
00133  * 
00134  * The concept "RTCP session" is not defined in RFC 3550, but since 
00135  * this structure is analogous to ast_rtp, which tracks a RTP session, 
00136  * it is logical to think of this as a RTCP session.
00137  *
00138  * RTCP packet is defined on page 9 of RFC 3550.
00139  * 
00140  */
00141 struct ast_rtcp {
00142    /*! Socket */
00143    int s;
00144    /*! Socket representation of the local endpoint. */
00145    struct sockaddr_in us;
00146    /*! Socket representation of the remote endpoint. */
00147    struct sockaddr_in them;
00148 };
00149 
00150 static struct ast_rtp_protocol *protos = NULL;
00151 
00152 int ast_rtp_fd(struct ast_rtp *rtp)
00153 {
00154    return rtp->s;
00155 }
00156 
00157 int ast_rtcp_fd(struct ast_rtp *rtp)
00158 {
00159    if (rtp->rtcp)
00160       return rtp->rtcp->s;
00161    return -1;
00162 }
00163 
00164 void ast_rtp_set_data(struct ast_rtp *rtp, void *data)
00165 {
00166    rtp->data = data;
00167 }
00168 
00169 void ast_rtp_set_callback(struct ast_rtp *rtp, ast_rtp_callback callback)
00170 {
00171    rtp->callback = callback;
00172 }
00173 
00174 void ast_rtp_setnat(struct ast_rtp *rtp, int nat)
00175 {
00176    rtp->nat = nat;
00177 }
00178 
00179 static struct ast_frame *send_dtmf(struct ast_rtp *rtp)
00180 {
00181    static struct ast_frame null_frame = { AST_FRAME_NULL, };
00182    char iabuf[INET_ADDRSTRLEN];
00183 
00184    if (ast_tvcmp(ast_tvnow(), rtp->dtmfmute) < 0) {
00185       if (option_debug)
00186          ast_log(LOG_DEBUG, "Ignore potential DTMF echo from '%s'\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr));
00187       rtp->resp = 0;
00188       rtp->dtmfduration = 0;
00189       return &null_frame;
00190    }
00191    if (option_debug)
00192       ast_log(LOG_DEBUG, "Sending dtmf: %d (%c), at %s\n", rtp->resp, rtp->resp, ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr));
00193    if (rtp->resp == 'X') {
00194       rtp->f.frametype = AST_FRAME_CONTROL;
00195       rtp->f.subclass = AST_CONTROL_FLASH;
00196    } else {
00197       rtp->f.frametype = AST_FRAME_DTMF;
00198       rtp->f.subclass = rtp->resp;
00199    }
00200    rtp->f.datalen = 0;
00201    rtp->f.samples = 0;
00202    rtp->f.mallocd = 0;
00203    rtp->f.src = "RTP";
00204    rtp->resp = 0;
00205    rtp->dtmfduration = 0;
00206    return &rtp->f;
00207    
00208 }
00209 
00210 static inline int rtp_debug_test_addr(struct sockaddr_in *addr)
00211 {
00212    if (rtpdebug == 0)
00213       return 0;
00214    if (rtpdebugaddr.sin_addr.s_addr) {
00215       if (((ntohs(rtpdebugaddr.sin_port) != 0)
00216          && (rtpdebugaddr.sin_port != addr->sin_port))
00217          || (rtpdebugaddr.sin_addr.s_addr != addr->sin_addr.s_addr))
00218       return 0;
00219    }
00220    return 1;
00221 }
00222 
00223 static struct ast_frame *process_cisco_dtmf(struct ast_rtp *rtp, unsigned char *data, int len)
00224 {
00225    unsigned int event;
00226    char resp = 0;
00227    struct ast_frame *f = NULL;
00228    event = ntohl(*((unsigned int *)(data)));
00229    event &= 0x001F;
00230 #if 0
00231    printf("Cisco Digit: %08x (len = %d)\n", event, len);
00232 #endif   
00233    if (event < 10) {
00234       resp = '0' + event;
00235    } else if (event < 11) {
00236       resp = '*';
00237    } else if (event < 12) {
00238       resp = '#';
00239    } else if (event < 16) {
00240       resp = 'A' + (event - 12);
00241    } else if (event < 17) {
00242       resp = 'X';
00243    }
00244    if (rtp->resp && (rtp->resp != resp)) {
00245       f = send_dtmf(rtp);
00246    }
00247    rtp->resp = resp;
00248    rtp->dtmfcount = dtmftimeout;
00249    return f;
00250 }
00251 
00252 /*! 
00253  * \brief Process RTP DTMF and events according to RFC 2833.
00254  * 
00255  * RFC 2833 is "RTP Payload for DTMF Digits, Telephony Tones and Telephony Signals".
00256  * 
00257  * \param rtp
00258  * \param data
00259  * \param len
00260  * \param seqno
00261  * \returns
00262  */
00263 static struct ast_frame *process_rfc2833(struct ast_rtp *rtp, unsigned char *data, int len, unsigned int seqno)
00264 {
00265    unsigned int event;
00266    unsigned int event_end;
00267    unsigned int duration;
00268    char resp = 0;
00269    struct ast_frame *f = NULL;
00270    event = ntohl(*((unsigned int *)(data)));
00271    event >>= 24;
00272    event_end = ntohl(*((unsigned int *)(data)));
00273    event_end <<= 8;
00274    event_end >>= 24;
00275    duration = ntohl(*((unsigned int *)(data)));
00276    duration &= 0xFFFF;
00277    if (rtpdebug)
00278       ast_log(LOG_DEBUG, "- RTP 2833 Event: %08x (len = %d)\n", event, len);
00279    if (event < 10) {
00280       resp = '0' + event;
00281    } else if (event < 11) {
00282       resp = '*';
00283    } else if (event < 12) {
00284       resp = '#';
00285    } else if (event < 16) {
00286       resp = 'A' + (event - 12);
00287    } else if (event < 17) {   /* Event 16: Hook flash */
00288       resp = 'X'; 
00289    }
00290    if (rtp->resp && (rtp->resp != resp)) {
00291       f = send_dtmf(rtp);
00292    } else if(event_end & 0x80) {
00293       if (rtp->resp) {
00294          if(rtp->lasteventendseqn != seqno) {
00295             f = send_dtmf(rtp);
00296             rtp->lasteventendseqn = seqno;
00297          }
00298          rtp->resp = 0;
00299       }
00300       resp = 0;
00301       duration = 0;
00302    } else if (rtp->resp && rtp->dtmfduration && (duration < rtp->dtmfduration)) {
00303       f = send_dtmf(rtp);
00304    }
00305    if (!(event_end & 0x80))
00306       rtp->resp = resp;
00307    rtp->dtmfcount = dtmftimeout;
00308    rtp->dtmfduration = duration;
00309    return f;
00310 }
00311 
00312 /*!
00313  * \brief Process Comfort Noise RTP.
00314  * 
00315  * This is incomplete at the moment.
00316  * 
00317 */
00318 static struct ast_frame *process_rfc3389(struct ast_rtp *rtp, unsigned char *data, int len)
00319 {
00320    struct ast_frame *f = NULL;
00321    /* Convert comfort noise into audio with various codecs.  Unfortunately this doesn't
00322       totally help us out becuase we don't have an engine to keep it going and we are not
00323       guaranteed to have it every 20ms or anything */
00324    if (rtpdebug)
00325       ast_log(LOG_DEBUG, "- RTP 3389 Comfort noise event: Level %d (len = %d)\n", rtp->lastrxformat, len);
00326 
00327    if (!(ast_test_flag(rtp, FLAG_3389_WARNING))) {
00328       char iabuf[INET_ADDRSTRLEN];
00329 
00330       ast_log(LOG_NOTICE, "Comfort noise support incomplete in Asterisk (RFC 3389). Please turn off on client if possible. Client IP: %s\n",
00331          ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr));
00332       ast_set_flag(rtp, FLAG_3389_WARNING);
00333    }
00334 
00335    /* Must have at least one byte */
00336    if (!len)
00337       return NULL;
00338    if (len < 24) {
00339       rtp->f.data = rtp->rawdata + AST_FRIENDLY_OFFSET;
00340       rtp->f.datalen = len - 1;
00341       rtp->f.offset = AST_FRIENDLY_OFFSET;
00342       memcpy(rtp->f.data, data + 1, len - 1);
00343    } else {
00344       rtp->f.data = NULL;
00345       rtp->f.offset = 0;
00346       rtp->f.datalen = 0;
00347    }
00348    rtp->f.frametype = AST_FRAME_CNG;
00349    rtp->f.subclass = data[0] & 0x7f;
00350    rtp->f.datalen = len - 1;
00351    rtp->f.samples = 0;
00352    rtp->f.delivery.tv_usec = rtp->f.delivery.tv_sec = 0;
00353    f = &rtp->f;
00354    return f;
00355 }
00356 
00357 static int rtpread(int *id, int fd, short events, void *cbdata)
00358 {
00359    struct ast_rtp *rtp = cbdata;
00360    struct ast_frame *f;
00361    f = ast_rtp_read(rtp);
00362    if (f) {
00363       if (rtp->callback)
00364          rtp->callback(rtp, f, rtp->data);
00365    }
00366    return 1;
00367 }
00368 
00369 struct ast_frame *ast_rtcp_read(struct ast_rtp *rtp)
00370 {
00371    static struct ast_frame null_frame = { AST_FRAME_NULL, };
00372    socklen_t len;
00373    int hdrlen = 8;
00374    int res;
00375    struct sockaddr_in sin;
00376    unsigned int rtcpdata[1024];
00377    char iabuf[INET_ADDRSTRLEN];
00378    
00379    if (!rtp || !rtp->rtcp)
00380       return &null_frame;
00381 
00382    len = sizeof(sin);
00383    
00384    res = recvfrom(rtp->rtcp->s, rtcpdata, sizeof(rtcpdata),
00385                0, (struct sockaddr *)&sin, &len);
00386    
00387    if (res < 0) {
00388       if (errno != EAGAIN)
00389          ast_log(LOG_WARNING, "RTP Read error: %s\n", strerror(errno));
00390       if (errno == EBADF)
00391          CRASH;
00392       return &null_frame;
00393    }
00394 
00395    if (res < hdrlen) {
00396       ast_log(LOG_WARNING, "RTP Read too short\n");
00397       return &null_frame;
00398    }
00399 
00400    if (rtp->nat) {
00401       /* Send to whoever sent to us */
00402       if ((rtp->rtcp->them.sin_addr.s_addr != sin.sin_addr.s_addr) ||
00403           (rtp->rtcp->them.sin_port != sin.sin_port)) {
00404          memcpy(&rtp->rtcp->them, &sin, sizeof(rtp->rtcp->them));
00405          if (option_debug || rtpdebug)
00406             ast_log(LOG_DEBUG, "RTCP NAT: Got RTCP from other end. Now sending to address %s:%d\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->rtcp->them.sin_addr), ntohs(rtp->rtcp->them.sin_port));
00407       }
00408    }
00409    if (option_debug)
00410       ast_log(LOG_DEBUG, "Got RTCP report of %d bytes\n", res);
00411    return &null_frame;
00412 }
00413 
00414 static void calc_rxstamp(struct timeval *tv, struct ast_rtp *rtp, unsigned int timestamp, int mark)
00415 {
00416    struct timeval ts = ast_samp2tv( timestamp, 8000);
00417    if (ast_tvzero(rtp->rxcore) || mark) {
00418       rtp->rxcore = ast_tvsub(ast_tvnow(), ts);
00419       /* Round to 20ms for nice, pretty timestamps */
00420       rtp->rxcore.tv_usec -= rtp->rxcore.tv_usec % 20000;
00421    }
00422    *tv = ast_tvadd(rtp->rxcore, ts);
00423 }
00424 
00425 struct ast_frame *ast_rtp_read(struct ast_rtp *rtp)
00426 {
00427    int res;
00428    struct sockaddr_in sin;
00429    socklen_t len;
00430    unsigned int seqno;
00431    int version;
00432    int payloadtype;
00433    int hdrlen = 12;
00434    int padding;
00435    int mark;
00436    int ext;
00437    int x;
00438    char iabuf[INET_ADDRSTRLEN];
00439    unsigned int timestamp;
00440    unsigned int *rtpheader;
00441    static struct ast_frame *f, null_frame = { AST_FRAME_NULL, };
00442    struct rtpPayloadType rtpPT;
00443    
00444    len = sizeof(sin);
00445    
00446    /* Cache where the header will go */
00447    res = recvfrom(rtp->s, rtp->rawdata + AST_FRIENDLY_OFFSET, sizeof(rtp->rawdata) - AST_FRIENDLY_OFFSET,
00448                0, (struct sockaddr *)&sin, &len);
00449 
00450 
00451    rtpheader = (unsigned int *)(rtp->rawdata + AST_FRIENDLY_OFFSET);
00452    if (res < 0) {
00453       if (errno != EAGAIN)
00454          ast_log(LOG_WARNING, "RTP Read error: %s\n", strerror(errno));
00455       if (errno == EBADF)
00456          CRASH;
00457       return &null_frame;
00458    }
00459    if (res < hdrlen) {
00460       ast_log(LOG_WARNING, "RTP Read too short\n");
00461       return &null_frame;
00462    }
00463 
00464    /* Ignore if the other side hasn't been given an address
00465       yet.  */
00466    if (!rtp->them.sin_addr.s_addr || !rtp->them.sin_port)
00467       return &null_frame;
00468 
00469    if (rtp->nat) {
00470       /* Send to whoever sent to us */
00471       if ((rtp->them.sin_addr.s_addr != sin.sin_addr.s_addr) ||
00472           (rtp->them.sin_port != sin.sin_port)) {
00473          memcpy(&rtp->them, &sin, sizeof(rtp->them));
00474          rtp->rxseqno = 0;
00475          ast_set_flag(rtp, FLAG_NAT_ACTIVE);
00476          if (option_debug || rtpdebug)
00477             ast_log(LOG_DEBUG, "RTP NAT: Got audio from other end. Now sending to address %s:%d\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port));
00478       }
00479    }
00480 
00481    /* Get fields */
00482    seqno = ntohl(rtpheader[0]);
00483 
00484    /* Check RTP version */
00485    version = (seqno & 0xC0000000) >> 30;
00486    if (version != 2)
00487       return &null_frame;
00488    
00489    payloadtype = (seqno & 0x7f0000) >> 16;
00490    padding = seqno & (1 << 29);
00491    mark = seqno & (1 << 23);
00492    ext = seqno & (1 << 28);
00493    seqno &= 0xffff;
00494    timestamp = ntohl(rtpheader[1]);
00495    
00496    if (padding) {
00497       /* Remove padding bytes */
00498       res -= rtp->rawdata[AST_FRIENDLY_OFFSET + res - 1];
00499    }
00500    
00501    if (ext) {
00502       /* RTP Extension present */
00503       hdrlen += 4;
00504       hdrlen += (ntohl(rtpheader[3]) & 0xffff) << 2;
00505    }
00506 
00507    if (res < hdrlen) {
00508       ast_log(LOG_WARNING, "RTP Read too short (%d, expecting %d)\n", res, hdrlen);
00509       return &null_frame;
00510    }
00511 
00512    if(rtp_debug_test_addr(&sin))
00513       ast_verbose("Got RTP packet from %s:%d (type %d, seq %d, ts %d, len %d)\n"
00514          , ast_inet_ntoa(iabuf, sizeof(iabuf), sin.sin_addr), ntohs(sin.sin_port), payloadtype, seqno, timestamp,res - hdrlen);
00515 
00516    rtpPT = ast_rtp_lookup_pt(rtp, payloadtype);
00517    if (!rtpPT.isAstFormat) {
00518       /* This is special in-band data that's not one of our codecs */
00519       if (rtpPT.code == AST_RTP_DTMF) {
00520          /* It's special -- rfc2833 process it */
00521          if(rtp_debug_test_addr(&sin)) {
00522             unsigned char *data;
00523             unsigned int event;
00524             unsigned int event_end;
00525             unsigned int duration;
00526             data = rtp->rawdata + AST_FRIENDLY_OFFSET + hdrlen;
00527             event = ntohl(*((unsigned int *)(data)));
00528             event >>= 24;
00529             event_end = ntohl(*((unsigned int *)(data)));
00530             event_end <<= 8;
00531             event_end >>= 24;
00532             duration = ntohl(*((unsigned int *)(data)));
00533             duration &= 0xFFFF;
00534             ast_verbose("Got rfc2833 RTP packet from %s:%d (type %d, seq %d, ts %d, len %d, mark %d, event %08x, end %d, duration %d) \n", ast_inet_ntoa(iabuf, sizeof(iabuf), sin.sin_addr), ntohs(sin.sin_port), payloadtype, seqno, timestamp, res - hdrlen, (mark?1:0), event, ((event_end & 0x80)?1:0), duration);
00535          }
00536          if (rtp->lasteventseqn <= seqno || rtp->resp == 0 || (rtp->lasteventseqn >= 65530 && seqno <= 6)) {
00537             f = process_rfc2833(rtp, rtp->rawdata + AST_FRIENDLY_OFFSET + hdrlen, res - hdrlen, seqno);
00538             rtp->lasteventseqn = seqno;
00539          } else
00540             f = NULL;
00541          if (f)
00542             return f;
00543          else
00544             return &null_frame;
00545       } else if (rtpPT.code == AST_RTP_CISCO_DTMF) {
00546          /* It's really special -- process it the Cisco way */
00547          if (rtp->lasteventseqn <= seqno || rtp->resp == 0 || (rtp->lasteventseqn >= 65530 && seqno <= 6)) {
00548             f = process_cisco_dtmf(rtp, rtp->rawdata + AST_FRIENDLY_OFFSET + hdrlen, res - hdrlen);
00549             rtp->lasteventseqn = seqno;
00550          } else 
00551             f = NULL;
00552             if (f) 
00553             return f; 
00554          else 
00555             return &null_frame;
00556       } else if (rtpPT.code == AST_RTP_CN) {
00557          /* Comfort Noise */
00558          f = process_rfc3389(rtp, rtp->rawdata + AST_FRIENDLY_OFFSET + hdrlen, res - hdrlen);
00559          if (f) 
00560             return f; 
00561          else 
00562             return &null_frame;
00563       } else {
00564          ast_log(LOG_NOTICE, "Unknown RTP codec %d received\n", payloadtype);
00565          return &null_frame;
00566       }
00567    }
00568    rtp->f.subclass = rtpPT.code;
00569    if (rtp->f.subclass < AST_FORMAT_MAX_AUDIO)
00570       rtp->f.frametype = AST_FRAME_VOICE;
00571    else
00572       rtp->f.frametype = AST_FRAME_VIDEO;
00573    rtp->lastrxformat = rtp->f.subclass;
00574 
00575    if (!rtp->lastrxts)
00576       rtp->lastrxts = timestamp;
00577 
00578    if (rtp->rxseqno) {
00579       for (x=rtp->rxseqno + 1; x < seqno; x++) {
00580          /* Queue empty frames */
00581          rtp->f.mallocd = 0;
00582          rtp->f.datalen = 0;
00583          rtp->f.data = NULL;
00584          rtp->f.offset = 0;
00585          rtp->f.samples = 0;
00586          rtp->f.src = "RTPMissedFrame";
00587       }
00588    }
00589    rtp->rxseqno = seqno;
00590 
00591    if (rtp->dtmfcount) {
00592 #if 0
00593       printf("dtmfcount was %d\n", rtp->dtmfcount);
00594 #endif      
00595       rtp->dtmfcount -= (timestamp - rtp->lastrxts);
00596       if (rtp->dtmfcount < 0)
00597          rtp->dtmfcount = 0;
00598 #if 0
00599       if (dtmftimeout != rtp->dtmfcount)
00600          printf("dtmfcount is %d\n", rtp->dtmfcount);
00601 #endif
00602    }
00603    rtp->lastrxts = timestamp;
00604 
00605    /* Send any pending DTMF */
00606    if (rtp->resp && !rtp->dtmfcount) {
00607       if (option_debug)
00608          ast_log(LOG_DEBUG, "Sending pending DTMF\n");
00609       return send_dtmf(rtp);
00610    }
00611    rtp->f.mallocd = 0;
00612    rtp->f.datalen = res - hdrlen;
00613    rtp->f.data = rtp->rawdata + hdrlen + AST_FRIENDLY_OFFSET;
00614    rtp->f.offset = hdrlen + AST_FRIENDLY_OFFSET;
00615    if (rtp->f.subclass < AST_FORMAT_MAX_AUDIO) {
00616       rtp->f.samples = ast_codec_get_samples(&rtp->f);
00617       if (rtp->f.subclass == AST_FORMAT_SLINEAR) 
00618          ast_frame_byteswap_be(&rtp->f);
00619       calc_rxstamp(&rtp->f.delivery, rtp, timestamp, mark);
00620    } else {
00621       /* Video -- samples is # of samples vs. 90000 */
00622       if (!rtp->lastividtimestamp)
00623          rtp->lastividtimestamp = timestamp;
00624       rtp->f.samples = timestamp - rtp->lastividtimestamp;
00625       rtp->lastividtimestamp = timestamp;
00626       rtp->f.delivery.tv_sec = 0;
00627       rtp->f.delivery.tv_usec = 0;
00628       if (mark)
00629          rtp->f.subclass |= 0x1;
00630       
00631    }
00632    rtp->f.src = "RTP";
00633    return &rtp->f;
00634 }
00635 
00636 /* The following array defines the MIME Media type (and subtype) for each
00637    of our codecs, or RTP-specific data type. */
00638 static struct {
00639   struct rtpPayloadType payloadType;
00640   char* type;
00641   char* subtype;
00642 } mimeTypes[] = {
00643   {{1, AST_FORMAT_G723_1}, "audio", "G723"},
00644   {{1, AST_FORMAT_GSM}, "audio", "GSM"},
00645   {{1, AST_FORMAT_ULAW}, "audio", "PCMU"},
00646   {{1, AST_FORMAT_ALAW}, "audio", "PCMA"},
00647   {{1, AST_FORMAT_G726}, "audio", "G726-32"},
00648   {{1, AST_FORMAT_ADPCM}, "audio", "DVI4"},
00649   {{1, AST_FORMAT_SLINEAR}, "audio", "L16"},
00650   {{1, AST_FORMAT_LPC10}, "audio", "LPC"},
00651   {{1, AST_FORMAT_G729A}, "audio", "G729"},
00652   {{1, AST_FORMAT_SPEEX}, "audio", "speex"},
00653   {{1, AST_FORMAT_ILBC}, "audio", "iLBC"},
00654   {{0, AST_RTP_DTMF}, "audio", "telephone-event"},
00655   {{0, AST_RTP_CISCO_DTMF}, "audio", "cisco-telephone-event"},
00656   {{0, AST_RTP_CN}, "audio", "CN"},
00657   {{1, AST_FORMAT_JPEG}, "video", "JPEG"},
00658   {{1, AST_FORMAT_PNG}, "video", "PNG"},
00659   {{1, AST_FORMAT_H261}, "video", "H261"},
00660   {{1, AST_FORMAT_H263}, "video", "H263"},
00661   {{1, AST_FORMAT_H263_PLUS}, "video", "h263-1998"},
00662 };
00663 
00664 /* Static (i.e., well-known) RTP payload types for our "AST_FORMAT..."s:
00665    also, our own choices for dynamic payload types.  This is our master
00666    table for transmission */
00667 static struct rtpPayloadType static_RTP_PT[MAX_RTP_PT] = {
00668   [0] = {1, AST_FORMAT_ULAW},
00669 #ifdef USE_DEPRECATED_G726
00670   [2] = {1, AST_FORMAT_G726}, /* Technically this is G.721, but if Cisco can do it, so can we... */
00671 #endif
00672   [3] = {1, AST_FORMAT_GSM},
00673   [4] = {1, AST_FORMAT_G723_1},
00674   [5] = {1, AST_FORMAT_ADPCM}, /* 8 kHz */
00675   [6] = {1, AST_FORMAT_ADPCM}, /* 16 kHz */
00676   [7] = {1, AST_FORMAT_LPC10},
00677   [8] = {1, AST_FORMAT_ALAW},
00678   [10] = {1, AST_FORMAT_SLINEAR}, /* 2 channels */
00679   [11] = {1, AST_FORMAT_SLINEAR}, /* 1 channel */
00680   [13] = {0, AST_RTP_CN},
00681   [16] = {1, AST_FORMAT_ADPCM}, /* 11.025 kHz */
00682   [17] = {1, AST_FORMAT_ADPCM}, /* 22.050 kHz */
00683   [18] = {1, AST_FORMAT_G729A},
00684   [19] = {0, AST_RTP_CN},     /* Also used for CN */
00685   [26] = {1, AST_FORMAT_JPEG},
00686   [31] = {1, AST_FORMAT_H261},
00687   [34] = {1, AST_FORMAT_H263},
00688   [103] = {1, AST_FORMAT_H263_PLUS},
00689   [97] = {1, AST_FORMAT_ILBC},
00690   [101] = {0, AST_RTP_DTMF},
00691   [110] = {1, AST_FORMAT_SPEEX},
00692   [111] = {1, AST_FORMAT_G726},
00693   [121] = {0, AST_RTP_CISCO_DTMF}, /* Must be type 121 */
00694 };
00695 
00696 void ast_rtp_pt_clear(struct ast_rtp* rtp) 
00697 {
00698    int i;
00699    if (!rtp)
00700       return;
00701 
00702    for (i = 0; i < MAX_RTP_PT; ++i) {
00703       rtp->current_RTP_PT[i].isAstFormat = 0;
00704       rtp->current_RTP_PT[i].code = 0;
00705    }
00706 
00707    rtp->rtp_lookup_code_cache_isAstFormat = 0;
00708    rtp->rtp_lookup_code_cache_code = 0;
00709    rtp->rtp_lookup_code_cache_result = 0;
00710 }
00711 
00712 void ast_rtp_pt_default(struct ast_rtp* rtp) 
00713 {
00714    int i;
00715 
00716    /* Initialize to default payload types */
00717    for (i = 0; i < MAX_RTP_PT; ++i) {
00718       rtp->current_RTP_PT[i].isAstFormat = static_RTP_PT[i].isAstFormat;
00719       rtp->current_RTP_PT[i].code = static_RTP_PT[i].code;
00720    }
00721 
00722    rtp->rtp_lookup_code_cache_isAstFormat = 0;
00723    rtp->rtp_lookup_code_cache_code = 0;
00724    rtp->rtp_lookup_code_cache_result = 0;
00725 }
00726 
00727 /* Make a note of a RTP paymoad type that was seen in a SDP "m=" line. */
00728 /* By default, use the well-known value for this type (although it may */
00729 /* still be set to a different value by a subsequent "a=rtpmap:" line): */
00730 void ast_rtp_set_m_type(struct ast_rtp* rtp, int pt) {
00731    if (pt < 0 || pt > MAX_RTP_PT) 
00732       return; /* bogus payload type */
00733 
00734    if (static_RTP_PT[pt].code != 0) {
00735       rtp->current_RTP_PT[pt] = static_RTP_PT[pt];
00736    }
00737 } 
00738 
00739 /* Make a note of a RTP payload type (with MIME type) that was seen in */
00740 /* a SDP "a=rtpmap:" line. */
00741 void ast_rtp_set_rtpmap_type(struct ast_rtp* rtp, int pt,
00742           char* mimeType, char* mimeSubtype) {
00743    int i;
00744 
00745    if (pt < 0 || pt > MAX_RTP_PT) 
00746          return; /* bogus payload type */
00747 
00748    for (i = 0; i < sizeof mimeTypes/sizeof mimeTypes[0]; ++i) {
00749       if (strcasecmp(mimeSubtype, mimeTypes[i].subtype) == 0 &&
00750            strcasecmp(mimeType, mimeTypes[i].type) == 0) {
00751          rtp->current_RTP_PT[pt] = mimeTypes[i].payloadType;
00752       return;
00753       }
00754    }
00755 } 
00756 
00757 /* Return the union of all of the codecs that were set by rtp_set...() calls */
00758 /* They're returned as two distinct sets: AST_FORMATs, and AST_RTPs */
00759 void ast_rtp_get_current_formats(struct ast_rtp* rtp,
00760               int* astFormats, int* nonAstFormats) {
00761    int pt;
00762 
00763    *astFormats = *nonAstFormats = 0;
00764    for (pt = 0; pt < MAX_RTP_PT; ++pt) {
00765       if (rtp->current_RTP_PT[pt].isAstFormat) {
00766          *astFormats |= rtp->current_RTP_PT[pt].code;
00767       } else {
00768          *nonAstFormats |= rtp->current_RTP_PT[pt].code;
00769       }
00770    }
00771 }
00772 
00773 void ast_rtp_offered_from_local(struct ast_rtp* rtp, int local) {
00774    if (rtp)
00775       rtp->rtp_offered_from_local = local;
00776    else
00777       ast_log(LOG_WARNING, "rtp structure is null\n");
00778 }
00779 
00780 struct rtpPayloadType ast_rtp_lookup_pt(struct ast_rtp* rtp, int pt) 
00781 {
00782    struct rtpPayloadType result;
00783 
00784    result.isAstFormat = result.code = 0;
00785    if (pt < 0 || pt > MAX_RTP_PT) 
00786       return result; /* bogus payload type */
00787 
00788    /* Start with the negotiated codecs */
00789    if (!rtp->rtp_offered_from_local)
00790       result = rtp->current_RTP_PT[pt];
00791 
00792    /* If it doesn't exist, check our static RTP type list, just in case */
00793    if (!result.code) 
00794       result = static_RTP_PT[pt];
00795    return result;
00796 }
00797 
00798 /* Looks up an RTP code out of our *static* outbound list */
00799 int ast_rtp_lookup_code(struct ast_rtp* rtp, const int isAstFormat, const int code) {
00800 
00801    int pt;
00802 
00803    if (isAstFormat == rtp->rtp_lookup_code_cache_isAstFormat &&
00804       code == rtp->rtp_lookup_code_cache_code) {
00805 
00806       /* Use our cached mapping, to avoid the overhead of the loop below */
00807       return rtp->rtp_lookup_code_cache_result;
00808    }
00809 
00810    /* Check the dynamic list first */
00811    for (pt = 0; pt < MAX_RTP_PT; ++pt) {
00812       if (rtp->current_RTP_PT[pt].code == code && rtp->current_RTP_PT[pt].isAstFormat == isAstFormat) {
00813          rtp->rtp_lookup_code_cache_isAstFormat = isAstFormat;
00814          rtp->rtp_lookup_code_cache_code = code;
00815          rtp->rtp_lookup_code_cache_result = pt;
00816          return pt;
00817       }
00818    }
00819 
00820    /* Then the static list */
00821    for (pt = 0; pt < MAX_RTP_PT; ++pt) {
00822       if (static_RTP_PT[pt].code == code && static_RTP_PT[pt].isAstFormat == isAstFormat) {
00823          rtp->rtp_lookup_code_cache_isAstFormat = isAstFormat;
00824          rtp->rtp_lookup_code_cache_code = code;
00825          rtp->rtp_lookup_code_cache_result = pt;
00826          return pt;
00827       }
00828    }
00829    return -1;
00830 }
00831 
00832 char* ast_rtp_lookup_mime_subtype(const int isAstFormat, const int code) {
00833 
00834    int i;
00835 
00836    for (i = 0; i < sizeof mimeTypes/sizeof mimeTypes[0]; ++i) {
00837    if (mimeTypes[i].payloadType.code == code && mimeTypes[i].payloadType.isAstFormat == isAstFormat) {
00838             return mimeTypes[i].subtype;
00839       }
00840    }
00841    return "";
00842 }
00843 
00844 char *ast_rtp_lookup_mime_multiple(char *buf, int size, const int capability, const int isAstFormat)
00845 {
00846    int format;
00847    unsigned len;
00848    char *end = buf;
00849    char *start = buf;
00850 
00851    if (!buf || !size)
00852       return NULL;
00853 
00854    snprintf(end, size, "0x%x (", capability);
00855 
00856    len = strlen(end);
00857    end += len;
00858    size -= len;
00859    start = end;
00860 
00861    for (format = 1; format < AST_RTP_MAX; format <<= 1) {
00862       if (capability & format) {
00863          const char *name = ast_rtp_lookup_mime_subtype(isAstFormat, format);
00864          snprintf(end, size, "%s|", name);
00865          len = strlen(end);
00866          end += len;
00867          size -= len;
00868       }
00869    }
00870 
00871    if (start == end)
00872       snprintf(start, size, "nothing)"); 
00873    else if (size > 1)
00874       *(end -1) = ')';
00875    
00876    return buf;
00877 }
00878 
00879 static int rtp_socket(void)
00880 {
00881    int s;
00882    long flags;
00883    s = socket(AF_INET, SOCK_DGRAM, 0);
00884    if (s > -1) {
00885       flags = fcntl(s, F_GETFL);
00886       fcntl(s, F_SETFL, flags | O_NONBLOCK);
00887 #ifdef SO_NO_CHECK
00888       if (nochecksums)
00889          setsockopt(s, SOL_SOCKET, SO_NO_CHECK, &nochecksums, sizeof(nochecksums));
00890 #endif
00891    }
00892    return s;
00893 }
00894 
00895 /*!
00896  * \brief Initialize a new RTCP session.
00897  * 
00898  * \returns The newly initialized RTCP session.
00899  */
00900 static struct ast_rtcp *ast_rtcp_new(void)
00901 {
00902    struct ast_rtcp *rtcp;
00903    rtcp = malloc(sizeof(struct ast_rtcp));
00904    if (!rtcp)
00905       return NULL;
00906    memset(rtcp, 0, sizeof(struct ast_rtcp));
00907    rtcp->s = rtp_socket();
00908    rtcp->us.sin_family = AF_INET;
00909    if (rtcp->s < 0) {
00910       free(rtcp);
00911       ast_log(LOG_WARNING, "Unable to allocate socket: %s\n", strerror(errno));
00912       return NULL;
00913    }
00914    return rtcp;
00915 }
00916 
00917 struct ast_rtp *ast_rtp_new_with_bindaddr(struct sched_context *sched, struct io_context *io, int rtcpenable, int callbackmode, struct in_addr addr)
00918 {
00919    struct ast_rtp *rtp;
00920    int x;
00921    int first;
00922    int startplace;
00923    rtp = malloc(sizeof(struct ast_rtp));
00924    if (!rtp)
00925       return NULL;
00926    memset(rtp, 0, sizeof(struct ast_rtp));
00927    rtp->them.sin_family = AF_INET;
00928    rtp->us.sin_family = AF_INET;
00929    rtp->s = rtp_socket();
00930    rtp->ssrc = rand();
00931    rtp->seqno = rand() & 0xffff;
00932    if (rtp->s < 0) {
00933       free(rtp);
00934       ast_log(LOG_ERROR, "Unable to allocate socket: %s\n", strerror(errno));
00935       return NULL;
00936    }
00937    if (sched && rtcpenable) {
00938       rtp->sched = sched;
00939       rtp->rtcp = ast_rtcp_new();
00940    }
00941    
00942    /* Select a random port number in the range of possible RTP */
00943    x = (rand() % (rtpend-rtpstart)) + rtpstart;
00944    x = x & ~1;
00945    /* Save it for future references. */
00946    startplace = x;
00947    /* Iterate tring to bind that port and incrementing it otherwise untill a port was found or no ports are available. */
00948    for (;;) {
00949       /* Must be an even port number by RTP spec */
00950       rtp->us.sin_port = htons(x);
00951       rtp->us.sin_addr = addr;
00952       /* If there's rtcp, initialize it as well. */
00953       if (rtp->rtcp)
00954          rtp->rtcp->us.sin_port = htons(x + 1);
00955       /* Try to bind it/them. */
00956       if (!(first = bind(rtp->s, (struct sockaddr *)&rtp->us, sizeof(rtp->us))) &&
00957          (!rtp->rtcp || !bind(rtp->rtcp->s, (struct sockaddr *)&rtp->rtcp->us, sizeof(rtp->rtcp->us))))
00958          break;
00959       if (!first) {
00960          /* Primary bind succeeded! Gotta recreate it */
00961          close(rtp->s);
00962          rtp->s = rtp_socket();
00963       }
00964       if (errno != EADDRINUSE) {
00965          /* We got an error that wasn't expected, abort! */
00966          ast_log(LOG_ERROR, "Unexpected bind error: %s\n", strerror(errno));
00967          close(rtp->s);
00968          if (rtp->rtcp) {
00969             close(rtp->rtcp->s);
00970             free(rtp->rtcp);
00971          }
00972          free(rtp);
00973          return NULL;
00974       }
00975       /* The port was used, increment it (by two). */
00976       x += 2;
00977       /* Did we go over the limit ? */
00978       if (x > rtpend)
00979          /* then, start from the begingig. */
00980          x = (rtpstart + 1) & ~1;
00981       /* Check if we reached the place were we started. */
00982       if (x == startplace) {
00983          /* If so, there's no ports available. */
00984          ast_log(LOG_ERROR, "No RTP ports remaining. Can't setup media stream for this call.\n");
00985          close(rtp->s);
00986          if (rtp->rtcp) {
00987             close(rtp->rtcp->s);
00988             free(rtp->rtcp);
00989          }
00990          free(rtp);
00991          return NULL;
00992       }
00993    }
00994    if (io && sched && callbackmode) {
00995       /* Operate this one in a callback mode */
00996       rtp->sched = sched;
00997       rtp->io = io;
00998       rtp->ioid = ast_io_add(rtp->io, rtp->s, rtpread, AST_IO_IN, rtp);
00999    }
01000    ast_rtp_pt_default(rtp);
01001    return rtp;
01002 }
01003 
01004 struct ast_rtp *ast_rtp_new(struct sched_context *sched, struct io_context *io, int rtcpenable, int callbackmode)
01005 {
01006    struct in_addr ia;
01007 
01008    memset(&ia, 0, sizeof(ia));
01009    return ast_rtp_new_with_bindaddr(sched, io, rtcpenable, callbackmode, ia);
01010 }
01011 
01012 int ast_rtp_settos(struct ast_rtp *rtp, int tos)
01013 {
01014    int res;
01015 
01016    if ((res = setsockopt(rtp->s, IPPROTO_IP, IP_TOS, &tos, sizeof(tos)))) 
01017       ast_log(LOG_WARNING, "Unable to set TOS to %d\n", tos);
01018    return res;
01019 }
01020 
01021 void ast_rtp_set_peer(struct ast_rtp *rtp, struct sockaddr_in *them)
01022 {
01023    rtp->them.sin_port = them->sin_port;
01024    rtp->them.sin_addr = them->sin_addr;
01025    if (rtp->rtcp) {
01026       rtp->rtcp->them.sin_port = htons(ntohs(them->sin_port) + 1);
01027       rtp->rtcp->them.sin_addr = them->sin_addr;
01028    }
01029    rtp->rxseqno = 0;
01030 }
01031 
01032 void ast_rtp_get_peer(struct ast_rtp *rtp, struct sockaddr_in *them)
01033 {
01034    them->sin_family = AF_INET;
01035    them->sin_port = rtp->them.sin_port;
01036    them->sin_addr = rtp->them.sin_addr;
01037 }
01038 
01039 void ast_rtp_get_us(struct ast_rtp *rtp, struct sockaddr_in *us)
01040 {
01041    memcpy(us, &rtp->us, sizeof(rtp->us));
01042 }
01043 
01044 void ast_rtp_stop(struct ast_rtp *rtp)
01045 {
01046    memset(&rtp->them.sin_addr, 0, sizeof(rtp->them.sin_addr));
01047    memset(&rtp->them.sin_port, 0, sizeof(rtp->them.sin_port));
01048    if (rtp->rtcp) {
01049       memset(&rtp->rtcp->them.sin_addr, 0, sizeof(rtp->them.sin_addr));
01050       memset(&rtp->rtcp->them.sin_port, 0, sizeof(rtp->them.sin_port));
01051    }
01052 }
01053 
01054 void ast_rtp_reset(struct ast_rtp *rtp)
01055 {
01056    memset(&rtp->rxcore, 0, sizeof(rtp->rxcore));
01057    memset(&rtp->txcore, 0, sizeof(rtp->txcore));
01058    memset(&rtp->dtmfmute, 0, sizeof(rtp->dtmfmute));
01059    rtp->lastts = 0;
01060    rtp->lastdigitts = 0;
01061    rtp->lastrxts = 0;
01062    rtp->lastividtimestamp = 0;
01063    rtp->lastovidtimestamp = 0;
01064    rtp->lasteventseqn = 0;
01065    rtp->lasteventendseqn = 0;
01066    rtp->lasttxformat = 0;
01067    rtp->lastrxformat = 0;
01068    rtp->dtmfcount = 0;
01069    rtp->dtmfduration = 0;
01070    rtp->seqno = 0;
01071    rtp->rxseqno = 0;
01072 }
01073 
01074 void ast_rtp_destroy(struct ast_rtp *rtp)
01075 {
01076    if (rtp->smoother)
01077       ast_smoother_free(rtp->smoother);
01078    if (rtp->ioid)
01079       ast_io_remove(rtp->io, rtp->ioid);
01080    if (rtp->s > -1)
01081       close(rtp->s);
01082    if (rtp->rtcp) {
01083       close(rtp->rtcp->s);
01084       free(rtp->rtcp);
01085    }
01086    free(rtp);
01087 }
01088 
01089 static unsigned int calc_txstamp(struct ast_rtp *rtp, struct timeval *delivery)
01090 {
01091    struct timeval t;
01092    long ms;
01093    if (ast_tvzero(rtp->txcore)) {
01094       rtp->txcore = ast_tvnow();
01095       /* Round to 20ms for nice, pretty timestamps */
01096       rtp->txcore.tv_usec -= rtp->txcore.tv_usec % 20000;
01097    }
01098    /* Use previous txcore if available */
01099    t = (delivery && !ast_tvzero(*delivery)) ? *delivery : ast_tvnow();
01100    ms = ast_tvdiff_ms(t, rtp->txcore);
01101    if (ms < 0)
01102       ms = 0;
01103    /* Use what we just got for next time */
01104    rtp->txcore = t;
01105    return (unsigned int) ms;
01106 }
01107 
01108 int ast_rtp_senddigit(struct ast_rtp *rtp, char digit)
01109 {
01110    unsigned int *rtpheader;
01111    int hdrlen = 12;
01112    int res;
01113    int x;
01114    int payload;
01115    char data[256];
01116    char iabuf[INET_ADDRSTRLEN];
01117 
01118    if ((digit <= '9') && (digit >= '0'))
01119       digit -= '0';
01120    else if (digit == '*')
01121       digit = 10;
01122    else if (digit == '#')
01123       digit = 11;
01124    else if ((digit >= 'A') && (digit <= 'D')) 
01125       digit = digit - 'A' + 12;
01126    else if ((digit >= 'a') && (digit <= 'd')) 
01127       digit = digit - 'a' + 12;
01128    else {
01129       ast_log(LOG_WARNING, "Don't know how to represent '%c'\n", digit);
01130       return -1;
01131    }
01132    payload = ast_rtp_lookup_code(rtp, 0, AST_RTP_DTMF);
01133 
01134    /* If we have no peer, return immediately */ 
01135    if (!rtp->them.sin_addr.s_addr)
01136       return 0;
01137 
01138    rtp->dtmfmute = ast_tvadd(ast_tvnow(), ast_tv(0, 500000));
01139    
01140    /* Get a pointer to the header */
01141    rtpheader = (unsigned int *)data;
01142    rtpheader[0] = htonl((2 << 30) | (1 << 23) | (payload << 16) | (rtp->seqno));
01143    rtpheader[1] = htonl(rtp->lastdigitts);
01144    rtpheader[2] = htonl(rtp->ssrc); 
01145    rtpheader[3] = htonl((digit << 24) | (0xa << 16) | (0));
01146    for (x = 0; x < 6; x++) {
01147       if (rtp->them.sin_port && rtp->them.sin_addr.s_addr) {
01148          res = sendto(rtp->s, (void *) rtpheader, hdrlen + 4, 0, (struct sockaddr *) &rtp->them, sizeof(rtp->them));
01149          if (res < 0) 
01150             ast_log(LOG_ERROR, "RTP Transmission error to %s:%d: %s\n",
01151                ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr),
01152                ntohs(rtp->them.sin_port), strerror(errno));
01153          if (rtp_debug_test_addr(&rtp->them))
01154             ast_verbose("Sent RTP packet to %s:%d (type %d, seq %u, ts %u, len %u)\n",
01155                    ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr),
01156                    ntohs(rtp->them.sin_port), payload, rtp->seqno, rtp->lastdigitts, res - hdrlen);
01157       }
01158       /* Sequence number of last two end packets does not get incremented */
01159       if (x < 3)
01160          rtp->seqno++;
01161       /* Clear marker bit and set seqno */
01162       rtpheader[0] = htonl((2 << 30) | (payload << 16) | (rtp->seqno));
01163       /* For the last three packets, set the duration and the end bit */
01164       if (x == 2) {
01165 #if 0
01166          /* No, this is wrong...  Do not increment lastdigitts, that's not according
01167             to the RFC, as best we can determine */
01168          rtp->lastdigitts++; /* or else the SPA3000 will click instead of beeping... */
01169          rtpheader[1] = htonl(rtp->lastdigitts);
01170 #endif         
01171          /* Make duration 800 (100ms) */
01172          rtpheader[3] |= htonl((800));
01173          /* Set the End bit */
01174          rtpheader[3] |= htonl((1 << 23));
01175       }
01176    }
01177    /* Increment the digit timestamp by 120ms, to ensure that digits
01178       sent sequentially with no intervening non-digit packets do not
01179       get sent with the same timestamp, and that sequential digits
01180       have some 'dead air' in between them
01181    */
01182    rtp->lastdigitts += 960;
01183    /* Increment the sequence number to reflect the last packet
01184       that was sent
01185    */
01186    rtp->seqno++;
01187    return 0;
01188 }
01189 
01190 int ast_rtp_sendcng(struct ast_rtp *rtp, int level)
01191 {
01192    unsigned int *rtpheader;
01193    int hdrlen = 12;
01194    int res;
01195    int payload;
01196    char data[256];
01197    char iabuf[INET_ADDRSTRLEN];
01198    level = 127 - (level & 0x7f);
01199    payload = ast_rtp_lookup_code(rtp, 0, AST_RTP_CN);
01200 
01201    /* If we have no peer, return immediately */ 
01202    if (!rtp->them.sin_addr.s_addr)
01203       return 0;
01204 
01205    rtp->dtmfmute = ast_tvadd(ast_tvnow(), ast_tv(0, 500000));
01206 
01207    /* Get a pointer to the header */
01208    rtpheader = (unsigned int *)data;
01209    rtpheader[0] = htonl((2 << 30) | (1 << 23) | (payload << 16) | (rtp->seqno++));
01210    rtpheader[1] = htonl(rtp->lastts);
01211    rtpheader[2] = htonl(rtp->ssrc); 
01212    data[12] = level;
01213    if (rtp->them.sin_port && rtp->them.sin_addr.s_addr) {
01214       res = sendto(rtp->s, (void *)rtpheader, hdrlen + 1, 0, (struct sockaddr *)&rtp->them, sizeof(rtp->them));
01215       if (res <0) 
01216          ast_log(LOG_ERROR, "RTP Comfort Noise Transmission error to %s:%d: %s\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port), strerror(errno));
01217       if(rtp_debug_test_addr(&rtp->them))
01218          ast_verbose("Sent Comfort Noise RTP packet to %s:%d (type %d, seq %d, ts %d, len %d)\n"
01219                , ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port), payload, rtp->seqno, rtp->lastts,res - hdrlen);        
01220          
01221    }
01222    return 0;
01223 }
01224 
01225 static int ast_rtp_raw_write(struct ast_rtp *rtp, struct ast_frame *f, int codec)
01226 {
01227    unsigned char *rtpheader;
01228    char iabuf[INET_ADDRSTRLEN];
01229    int hdrlen = 12;
01230    int res;
01231    unsigned int ms;
01232    int pred;
01233    int mark = 0;
01234 
01235    ms = calc_txstamp(rtp, &f->delivery);
01236    /* Default prediction */
01237    if (f->subclass < AST_FORMAT_MAX_AUDIO) {
01238       pred = rtp->lastts + f->samples;
01239 
01240       /* Re-calculate last TS */
01241       rtp->lastts = rtp->lastts + ms * 8;
01242       if (ast_tvzero(f->delivery)) {
01243          /* If this isn't an absolute delivery time, Check if it is close to our prediction, 
01244             and if so, go with our prediction */
01245          if (abs(rtp->lastts - pred) < MAX_TIMESTAMP_SKEW)
01246             rtp->lastts = pred;
01247          else {
01248             if (option_debug > 2)
01249                ast_log(LOG_DEBUG, "Difference is %d, ms is %d\n", abs(rtp->lastts - pred), ms);
01250             mark = 1;
01251          }
01252       }
01253    } else {
01254       mark = f->subclass & 0x1;
01255       pred = rtp->lastovidtimestamp + f->samples;
01256       /* Re-calculate last TS */
01257       rtp->lastts = rtp->lastts + ms * 90;
01258       /* If it's close to our prediction, go for it */
01259       if (ast_tvzero(f->delivery)) {
01260          if (abs(rtp->lastts - pred) < 7200) {
01261             rtp->lastts = pred;
01262             rtp->lastovidtimestamp += f->samples;
01263          } else {
01264             if (option_debug > 2)
01265                ast_log(LOG_DEBUG, "Difference is %d, ms is %d (%d), pred/ts/samples %d/%d/%d\n", abs(rtp->lastts - pred), ms, ms * 90, rtp->lastts, pred, f->samples);
01266             rtp->lastovidtimestamp = rtp->lastts;
01267          }
01268       }
01269    }
01270    /* If the timestamp for non-digit packets has moved beyond the timestamp
01271       for digits, update the digit timestamp.
01272    */
01273    if (rtp->lastts > rtp->lastdigitts)
01274       rtp->lastdigitts = rtp->lastts;
01275 
01276    /* Get a pointer to the header */
01277    rtpheader = (unsigned char *)(f->data - hdrlen);
01278 
01279    put_unaligned_uint32(rtpheader, htonl((2 << 30) | (codec << 16) | (rtp->seqno) | (mark << 23)));
01280    put_unaligned_uint32(rtpheader + 4, htonl(rtp->lastts));
01281    put_unaligned_uint32(rtpheader + 8, htonl(rtp->ssrc)); 
01282 
01283    if (rtp->them.sin_port && rtp->them.sin_addr.s_addr) {
01284       res = sendto(rtp->s, (void *)rtpheader, f->datalen + hdrlen, 0, (struct sockaddr *)&rtp->them, sizeof(rtp->them));
01285       if (res <0) {
01286          if (!rtp->nat || (rtp->nat && (ast_test_flag(rtp, FLAG_NAT_ACTIVE) == FLAG_NAT_ACTIVE))) {
01287             ast_log(LOG_DEBUG, "RTP Transmission error of packet %d to %s:%d: %s\n", rtp->seqno, ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port), strerror(errno));
01288          } else if ((ast_test_flag(rtp, FLAG_NAT_ACTIVE) == FLAG_NAT_INACTIVE) || rtpdebug) {
01289             /* Only give this error message once if we are not RTP debugging */
01290             if (option_debug || rtpdebug)
01291                ast_log(LOG_DEBUG, "RTP NAT: Can't write RTP to private address %s:%d, waiting for other end to send audio...\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port));
01292             ast_set_flag(rtp, FLAG_NAT_INACTIVE_NOWARN);
01293          }
01294       }
01295             
01296       if(rtp_debug_test_addr(&rtp->them))
01297          ast_verbose("Sent RTP packet to %s:%d (type %d, seq %u, ts %u, len %u)\n"
01298                , ast_inet_ntoa(iabuf, sizeof(iabuf), rtp->them.sin_addr), ntohs(rtp->them.sin_port), codec, rtp->seqno, rtp->lastts,res - hdrlen);
01299    }
01300 
01301    rtp->seqno++;
01302 
01303    return 0;
01304 }
01305 
01306 int ast_rtp_write(struct ast_rtp *rtp, struct ast_frame *_f)
01307 {
01308    struct ast_frame *f;
01309    int codec;
01310    int hdrlen = 12;
01311    int subclass;
01312    
01313 
01314    /* If we have no peer, return immediately */ 
01315    if (!rtp->them.sin_addr.s_addr)
01316       return 0;
01317 
01318    /* If there is no data length, return immediately */
01319    if (!_f->datalen) 
01320       return 0;
01321    
01322    /* Make sure we have enough space for RTP header */
01323    if ((_f->frametype != AST_FRAME_VOICE) && (_f->frametype != AST_FRAME_VIDEO)) {
01324       ast_log(LOG_WARNING, "RTP can only send voice\n");
01325       return -1;
01326    }
01327 
01328    subclass = _f->subclass;
01329    if (_f->frametype == AST_FRAME_VIDEO)
01330       subclass &= ~0x1;
01331 
01332    codec = ast_rtp_lookup_code(rtp, 1, subclass);
01333    if (codec < 0) {
01334       ast_log(LOG_WARNING, "Don't know how to send format %s packets with RTP\n", ast_getformatname(_f->subclass));
01335       return -1;
01336    }
01337 
01338    if (rtp->lasttxformat != subclass) {
01339       /* New format, reset the smoother */
01340       if (option_debug)
01341          ast_log(LOG_DEBUG, "Ooh, format changed from %s to %s\n", ast_getformatname(rtp->lasttxformat), ast_getformatname(subclass));
01342       rtp->lasttxformat = subclass;
01343       if (rtp->smoother)
01344          ast_smoother_free(rtp->smoother);
01345       rtp->smoother = NULL;
01346    }
01347 
01348 
01349    switch(subclass) {
01350    case AST_FORMAT_SLINEAR:
01351       if (!rtp->smoother) {
01352          rtp->smoother = ast_smoother_new(320);
01353       }
01354       if (!rtp->smoother) {
01355          ast_log(LOG_WARNING, "Unable to create smoother :(\n");
01356          return -1;
01357       }
01358       ast_smoother_feed_be(rtp->smoother, _f);
01359       
01360       while((f = ast_smoother_read(rtp->smoother)))
01361          ast_rtp_raw_write(rtp, f, codec);
01362       break;
01363    case AST_FORMAT_ULAW:
01364    case AST_FORMAT_ALAW:
01365       if (!rtp->smoother) {
01366          rtp->smoother = ast_smoother_new(160);
01367       }
01368       if (!rtp->smoother) {
01369          ast_log(LOG_WARNING, "Unable to create smoother :(\n");
01370          return -1;
01371       }
01372       ast_smoother_feed(rtp->smoother, _f);
01373       
01374       while((f = ast_smoother_read(rtp->smoother)))
01375          ast_rtp_raw_write(rtp, f, codec);
01376       break;
01377    case AST_FORMAT_ADPCM:
01378    case AST_FORMAT_G726:
01379       if (!rtp->smoother) {
01380          rtp->smoother = ast_smoother_new(80);
01381       }
01382       if (!rtp->smoother) {
01383          ast_log(LOG_WARNING, "Unable to create smoother :(\n");
01384          return -1;
01385       }
01386       ast_smoother_feed(rtp->smoother, _f);
01387       
01388       while((f = ast_smoother_read(rtp->smoother)))
01389          ast_rtp_raw_write(rtp, f, codec);
01390       break;
01391    case AST_FORMAT_G729A:
01392       if (!rtp->smoother) {
01393          rtp->smoother = ast_smoother_new(20);
01394          if (rtp->smoother)
01395             ast_smoother_set_flags(rtp->smoother, AST_SMOOTHER_FLAG_G729);
01396       }
01397       if (!rtp->smoother) {
01398          ast_log(LOG_WARNING, "Unable to create g729 smoother :(\n");
01399          return -1;
01400       }
01401       ast_smoother_feed(rtp->smoother, _f);
01402       
01403       while((f = ast_smoother_read(rtp->smoother)))
01404          ast_rtp_raw_write(rtp, f, codec);
01405       break;
01406    case AST_FORMAT_GSM:
01407       if (!rtp->smoother) {
01408          rtp->smoother = ast_smoother_new(33);
01409       }
01410       if (!rtp->smoother) {
01411          ast_log(LOG_WARNING, "Unable to create GSM smoother :(\n");
01412          return -1;
01413       }
01414       ast_smoother_feed(rtp->smoother, _f);
01415       while((f = ast_smoother_read(rtp->smoother)))
01416          ast_rtp_raw_write(rtp, f, codec);
01417       break;
01418    case AST_FORMAT_ILBC:
01419       if (!rtp->smoother) {
01420          rtp->smoother = ast_smoother_new(50);
01421       }
01422       if (!rtp->smoother) {
01423          ast_log(LOG_WARNING, "Unable to create ILBC smoother :(\n");
01424          return -1;
01425       }
01426       ast_smoother_feed(rtp->smoother, _f);
01427       while((f = ast_smoother_read(rtp->smoother)))
01428          ast_rtp_raw_write(rtp, f, codec);
01429       break;
01430    default: 
01431       ast_log(LOG_WARNING, "Not sure about sending format %s packets\n", ast_getformatname(subclass));
01432       /* fall through to... */
01433    case AST_FORMAT_H261:
01434    case AST_FORMAT_H263:
01435    case AST_FORMAT_H263_PLUS:
01436    case AST_FORMAT_G723_1:
01437    case AST_FORMAT_LPC10:
01438    case AST_FORMAT_SPEEX:
01439            /* Don't buffer outgoing frames; send them one-per-packet: */
01440       if (_f->offset < hdrlen) {
01441          f = ast_frdup(_f);
01442       } else {
01443          f = _f;
01444       }
01445       ast_rtp_raw_write(rtp, f, codec);
01446    }
01447       
01448    return 0;
01449 }
01450 
01451 /*--- ast_rtp_proto_unregister: Unregister interface to channel driver */
01452 void ast_rtp_proto_unregister(struct ast_rtp_protocol *proto)
01453 {
01454    struct ast_rtp_protocol *cur, *prev;
01455 
01456    cur = protos;
01457    prev = NULL;
01458    while(cur) {
01459       if (cur == proto) {
01460          if (prev)
01461             prev->next = proto->next;
01462          else
01463             protos = proto->next;
01464          return;
01465       }
01466       prev = cur;
01467       cur = cur->next;
01468    }
01469 }
01470 
01471 /*--- ast_rtp_proto_register: Register interface to channel driver */
01472 int ast_rtp_proto_register(struct ast_rtp_protocol *proto)
01473 {
01474    struct ast_rtp_protocol *cur;
01475    cur = protos;
01476    while(cur) {
01477       if (cur->type == proto->type) {
01478          ast_log(LOG_WARNING, "Tried to register same protocol '%s' twice\n", cur->type);
01479          return -1;
01480       }
01481       cur = cur->next;
01482    }
01483    proto->next = protos;
01484    protos = proto;
01485    return 0;
01486 }
01487 
01488 /*--- get_proto: Get channel driver interface structure */
01489 static struct ast_rtp_protocol *get_proto(struct ast_channel *chan)
01490 {
01491    struct ast_rtp_protocol *cur;
01492 
01493    cur = protos;
01494    while(cur) {
01495       if (cur->type == chan->type) {
01496          return cur;
01497       }
01498       cur = cur->next;
01499    }
01500    return NULL;
01501 }
01502 
01503 /* ast_rtp_bridge: Bridge calls. If possible and allowed, initiate
01504    re-invite so the peers exchange media directly outside 
01505    of Asterisk. */
01506 enum ast_bridge_result ast_rtp_bridge(struct ast_channel *c0, struct ast_channel *c1, int flags, struct ast_frame **fo, struct ast_channel **rc, int timeoutms)
01507 {
01508    struct ast_frame *f;
01509    struct ast_channel *who, *cs[3];
01510    struct ast_rtp *p0, *p1;      /* Audio RTP Channels */
01511    struct ast_rtp *vp0, *vp1;    /* Video RTP channels */
01512    struct ast_rtp_protocol *pr0, *pr1;
01513    struct sockaddr_in ac0, ac1;
01514    struct sockaddr_in vac0, vac1;
01515    struct sockaddr_in t0, t1;
01516    struct sockaddr_in vt0, vt1;
01517    char iabuf[INET_ADDRSTRLEN];
01518    
01519    void *pvt0, *pvt1;
01520    int codec0,codec1, oldcodec0, oldcodec1;
01521    
01522    memset(&vt0, 0, sizeof(vt0));
01523    memset(&vt1, 0, sizeof(vt1));
01524    memset(&vac0, 0, sizeof(vac0));
01525    memset(&vac1, 0, sizeof(vac1));
01526 
01527    /* if need DTMF, cant native bridge */
01528    if (flags & (AST_BRIDGE_DTMF_CHANNEL_0 | AST_BRIDGE_DTMF_CHANNEL_1))
01529       return AST_BRIDGE_FAILED_NOWARN;
01530 
01531    /* Lock channels */
01532    ast_mutex_lock(&c0->lock);
01533    while(ast_mutex_trylock(&c1->lock)) {
01534       ast_mutex_unlock(&c0->lock);
01535       usleep(1);
01536       ast_mutex_lock(&c0->lock);
01537    }
01538 
01539    /* Find channel driver interfaces */
01540    pr0 = get_proto(c0);
01541    pr1 = get_proto(c1);
01542    if (!pr0) {
01543       ast_log(LOG_WARNING, "Can't find native functions for channel '%s'\n", c0->name);
01544       ast_mutex_unlock(&c0->lock);
01545       ast_mutex_unlock(&c1->lock);
01546       return AST_BRIDGE_FAILED;
01547    }
01548    if (!pr1) {
01549       ast_log(LOG_WARNING, "Can't find native functions for channel '%s'\n", c1->name);
01550       ast_mutex_unlock(&c0->lock);
01551       ast_mutex_unlock(&c1->lock);
01552       return AST_BRIDGE_FAILED;
01553    }
01554 
01555    /* Get channel specific interface structures */
01556    pvt0 = c0->tech_pvt;
01557    pvt1 = c1->tech_pvt;
01558 
01559    /* Get audio and video interface (if native bridge is possible) */
01560    p0 = pr0->get_rtp_info(c0);
01561    if (pr0->get_vrtp_info)
01562       vp0 = pr0->get_vrtp_info(c0);
01563    else
01564       vp0 = NULL;
01565    p1 = pr1->get_rtp_info(c1);
01566    if (pr1->get_vrtp_info)
01567       vp1 = pr1->get_vrtp_info(c1);
01568    else
01569       vp1 = NULL;
01570 
01571    /* Check if bridge is still possible (In SIP canreinvite=no stops this, like NAT) */
01572    if (!p0 || !p1) {
01573       /* Somebody doesn't want to play... */
01574       ast_mutex_unlock(&c0->lock);
01575       ast_mutex_unlock(&c1->lock);
01576       return AST_BRIDGE_FAILED_NOWARN;
01577    }
01578    /* Get codecs from both sides */
01579    if (pr0->get_codec)
01580       codec0 = pr0->get_codec(c0);
01581    else
01582       codec0 = 0;
01583    if (pr1->get_codec)
01584       codec1 = pr1->get_codec(c1);
01585    else
01586       codec1 = 0;
01587    if (pr0->get_codec && pr1->get_codec) {
01588       /* Hey, we can't do reinvite if both parties speak different codecs */
01589       if (!(codec0 & codec1)) {
01590          if (option_debug)
01591             ast_log(LOG_DEBUG, "Channel codec0 = %d is not codec1 = %d, cannot native bridge in RTP.\n", codec0, codec1);
01592          ast_mutex_unlock(&c0->lock);
01593          ast_mutex_unlock(&c1->lock);
01594          return AST_BRIDGE_FAILED_NOWARN;
01595       }
01596    }
01597 
01598    /* Ok, we should be able to redirect the media. Start with one channel */
01599    if (pr0->set_rtp_peer(c0, p1, vp1, codec1, ast_test_flag(p1, FLAG_NAT_ACTIVE))) 
01600       ast_log(LOG_WARNING, "Channel '%s' failed to talk to '%s'\n", c0->name, c1->name);
01601    else {
01602       /* Store RTP peer */
01603       ast_rtp_get_peer(p1, &ac1);
01604       if (vp1)
01605          ast_rtp_get_peer(vp1, &vac1);
01606    }
01607    /* Then test the other channel */
01608    if (pr1->set_rtp_peer(c1, p0, vp0, codec0, ast_test_flag(p0, FLAG_NAT_ACTIVE)))
01609       ast_log(LOG_WARNING, "Channel '%s' failed to talk back to '%s'\n", c1->name, c0->name);
01610    else {
01611       /* Store RTP peer */
01612       ast_rtp_get_peer(p0, &ac0);
01613       if (vp0)
01614          ast_rtp_get_peer(vp0, &vac0);
01615    }
01616    ast_mutex_unlock(&c0->lock);
01617    ast_mutex_unlock(&c1->lock);
01618    /* External RTP Bridge up, now loop and see if something happes that force us to take the
01619       media back to Asterisk */
01620    cs[0] = c0;
01621    cs[1] = c1;
01622    cs[2] = NULL;
01623    oldcodec0 = codec0;
01624    oldcodec1 = codec1;
01625    for (;;) {
01626       /* Check if something changed... */
01627       if ((c0->tech_pvt != pvt0)  ||
01628          (c1->tech_pvt != pvt1) ||
01629          (c0->masq || c0->masqr || c1->masq || c1->masqr)) {
01630             ast_log(LOG_DEBUG, "Oooh, something is weird, backing out\n");
01631             if (c0->tech_pvt == pvt0) {
01632                if (pr0->set_rtp_peer(c0, NULL, NULL, 0, 0)) 
01633                   ast_log(LOG_WARNING, "Channel '%s' failed to break RTP bridge\n", c0->name);
01634             }
01635             if (c1->tech_pvt == pvt1) {
01636                if (pr1->set_rtp_peer(c1, NULL, NULL, 0, 0)) 
01637                   ast_log(LOG_WARNING, "Channel '%s' failed to break RTP bridge\n", c1->name);
01638             }
01639             return AST_BRIDGE_RETRY;
01640       }
01641       /* Now check if they have changed address */
01642       ast_rtp_get_peer(p1, &t1);
01643       ast_rtp_get_peer(p0, &t0);
01644       if (pr0->get_codec)
01645          codec0 = pr0->get_codec(c0);
01646       if (pr1->get_codec)
01647          codec1 = pr1->get_codec(c1);
01648       if (vp1)
01649          ast_rtp_get_peer(vp1, &vt1);
01650       if (vp0)
01651          ast_rtp_get_peer(vp0, &vt0);
01652       if (inaddrcmp(&t1, &ac1) || (vp1 && inaddrcmp(&vt1, &vac1)) || (codec1 != oldcodec1)) {
01653          if (option_debug > 1) {
01654             ast_log(LOG_DEBUG, "Oooh, '%s' changed end address to %s:%d (format %d)\n", 
01655                c1->name, ast_inet_ntoa(iabuf, sizeof(iabuf), t1.sin_addr), ntohs(t1.sin_port), codec1);
01656             ast_log(LOG_DEBUG, "Oooh, '%s' changed end vaddress to %s:%d (format %d)\n", 
01657                c1->name, ast_inet_ntoa(iabuf, sizeof(iabuf), vt1.sin_addr), ntohs(vt1.sin_port), codec1);
01658             ast_log(LOG_DEBUG, "Oooh, '%s' was %s:%d/(format %d)\n", 
01659                c1->name, ast_inet_ntoa(iabuf, sizeof(iabuf), ac1.sin_addr), ntohs(ac1.sin_port), oldcodec1);
01660             ast_log(LOG_DEBUG, "Oooh, '%s' was %s:%d/(format %d)\n", 
01661                c1->name, ast_inet_ntoa(iabuf, sizeof(iabuf), vac1.sin_addr), ntohs(vac1.sin_port), oldcodec1);
01662          }
01663          if (pr0->set_rtp_peer(c0, t1.sin_addr.s_addr ? p1 : NULL, vt1.sin_addr.s_addr ? vp1 : NULL, codec1, ast_test_flag(p1, FLAG_NAT_ACTIVE))) 
01664             ast_log(LOG_WARNING, "Channel '%s' failed to update to '%s'\n", c0->name, c1->name);
01665          memcpy(&ac1, &t1, sizeof(ac1));
01666          memcpy(&vac1, &vt1, sizeof(vac1));
01667          oldcodec1 = codec1;
01668       }
01669       if (inaddrcmp(&t0, &ac0) || (vp0 && inaddrcmp(&vt0, &vac0))) {
01670          if (option_debug) {
01671             ast_log(LOG_DEBUG, "Oooh, '%s' changed end address to %s:%d (format %d)\n", 
01672                c0->name, ast_inet_ntoa(iabuf, sizeof(iabuf), t0.sin_addr), ntohs(t0.sin_port), codec0);
01673             ast_log(LOG_DEBUG, "Oooh, '%s' was %s:%d/(format %d)\n", 
01674                c0->name, ast_inet_ntoa(iabuf, sizeof(iabuf), ac0.sin_addr), ntohs(ac0.sin_port), oldcodec0);
01675          }
01676          if (pr1->set_rtp_peer(c1, t0.sin_addr.s_addr ? p0 : NULL, vt0.sin_addr.s_addr ? vp0 : NULL, codec0, ast_test_flag(p0, FLAG_NAT_ACTIVE)))
01677             ast_log(LOG_WARNING, "Channel '%s' failed to update to '%s'\n", c1->name, c0->name);
01678          memcpy(&ac0, &t0, sizeof(ac0));
01679          memcpy(&vac0, &vt0, sizeof(vac0));
01680          oldcodec0 = codec0;
01681       }
01682       who = ast_waitfor_n(cs, 2, &timeoutms);
01683       if (!who) {
01684          if (!timeoutms) 
01685             return AST_BRIDGE_RETRY;
01686          if (option_debug)
01687             ast_log(LOG_DEBUG, "Ooh, empty read...\n");
01688          /* check for hangup / whentohangup */
01689          if (ast_check_hangup(c0) || ast_check_hangup(c1))
01690             break;
01691          continue;
01692       }
01693       f = ast_read(who);
01694       if (!f || ((f->frametype == AST_FRAME_DTMF) &&
01695                (((who == c0) && (flags & AST_BRIDGE_DTMF_CHANNEL_0)) || 
01696                 ((who == c1) && (flags & AST_BRIDGE_DTMF_CHANNEL_1))))) {
01697          *fo = f;
01698          *rc = who;
01699          if (option_debug)
01700             ast_log(LOG_DEBUG, "Oooh, got a %s\n", f ? "digit" : "hangup");
01701          if ((c0->tech_pvt == pvt0) && (!c0->_softhangup)) {
01702             if (pr0->set_rtp_peer(c0, NULL, NULL, 0, 0)) 
01703                ast_log(LOG_WARNING, "Channel '%s' failed to break RTP bridge\n", c0->name);
01704          }
01705          if ((c1->tech_pvt == pvt1) && (!c1->_softhangup)) {
01706             if (pr1->set_rtp_peer(c1, NULL, NULL, 0, 0)) 
01707                ast_log(LOG_WARNING, "Channel '%s' failed to break RTP bridge\n", c1->name);
01708          }
01709          return AST_BRIDGE_COMPLETE;
01710       } else if ((f->frametype == AST_FRAME_CONTROL) && !(flags & AST_BRIDGE_IGNORE_SIGS)) {
01711          if ((f->subclass == AST_CONTROL_HOLD) || (f->subclass == AST_CONTROL_UNHOLD) ||
01712              (f->subclass == AST_CONTROL_VIDUPDATE)) {
01713             ast_indicate(who == c0 ? c1 : c0, f->subclass);
01714             ast_frfree(f);
01715          } else {
01716             *fo = f;
01717             *rc = who;
01718             ast_log(LOG_DEBUG, "Got a FRAME_CONTROL (%d) frame on channel %s\n", f->subclass, who->name);
01719             return AST_BRIDGE_COMPLETE;
01720          }
01721       } else {
01722          if ((f->frametype == AST_FRAME_DTMF) || 
01723             (f->frametype == AST_FRAME_VOICE) || 
01724             (f->frametype == AST_FRAME_VIDEO)) {
01725             /* Forward voice or DTMF frames if they happen upon us */
01726             if (who == c0) {
01727                ast_write(c1, f);
01728             } else if (who == c1) {
01729                ast_write(c0, f);
01730             }
01731          }
01732          ast_frfree(f);
01733       }
01734       /* Swap priority not that it's a big deal at this point */
01735       cs[2] = cs[0];
01736       cs[0] = cs[1];
01737       cs[1] = cs[2];
01738       
01739    }
01740    return AST_BRIDGE_FAILED;
01741 }
01742 
01743 static int rtp_do_debug_ip(int fd, int argc, char *argv[])
01744 {
01745    struct hostent *hp;
01746    struct ast_hostent ahp;
01747    char iabuf[INET_ADDRSTRLEN];
01748    int port = 0;
01749    char *p, *arg;
01750 
01751    if (argc != 4)
01752       return RESULT_SHOWUSAGE;
01753    arg = argv[3];
01754    p = strstr(arg, ":");
01755    if (p) {
01756       *p = '\0';
01757       p++;
01758       port = atoi(p);
01759    }
01760    hp = ast_gethostbyname(arg, &ahp);
01761    if (hp == NULL)
01762       return RESULT_SHOWUSAGE;
01763    rtpdebugaddr.sin_family = AF_INET;
01764    memcpy(&rtpdebugaddr.sin_addr, hp->h_addr, sizeof(rtpdebugaddr.sin_addr));
01765    rtpdebugaddr.sin_port = htons(port);
01766    if (port == 0)
01767       ast_cli(fd, "RTP Debugging Enabled for IP: %s\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtpdebugaddr.sin_addr));
01768    else
01769       ast_cli(fd, "RTP Debugging Enabled for IP: %s:%d\n", ast_inet_ntoa(iabuf, sizeof(iabuf), rtpdebugaddr.sin_addr), port);
01770    rtpdebug = 1;
01771    return RESULT_SUCCESS;
01772 }
01773 
01774 static int rtp_do_debug(int fd, int argc, char *argv[])
01775 {
01776    if(argc != 2) {
01777       if(argc != 4)
01778          return RESULT_SHOWUSAGE;
01779       return rtp_do_debug_ip(fd, argc, argv);
01780    }
01781    rtpdebug = 1;
01782    memset(&rtpdebugaddr,0,sizeof(rtpdebugaddr));
01783    ast_cli(fd, "RTP Debugging Enabled\n");
01784    return RESULT_SUCCESS;
01785 }
01786    
01787 static int rtp_no_debug(int fd, int argc, char *argv[])
01788 {
01789    if(argc !=3)
01790       return RESULT_SHOWUSAGE;
01791    rtpdebug = 0;
01792    ast_cli(fd,"RTP Debugging Disabled\n");
01793    return RESULT_SUCCESS;
01794 }
01795 
01796 static char debug_usage[] =
01797   "Usage: rtp debug [ip host[:port]]\n"
01798   "       Enable dumping of all RTP packets to and from host.\n";
01799 
01800 static char no_debug_usage[] =
01801   "Usage: rtp no debug\n"
01802   "       Disable all RTP debugging\n";
01803 
01804 static struct ast_cli_entry  cli_debug_ip =
01805 {{ "rtp", "debug", "ip", NULL } , rtp_do_debug, "Enable RTP debugging on IP", debug_usage };
01806 
01807 static struct ast_cli_entry  cli_debug =
01808 {{ "rtp", "debug", NULL } , rtp_do_debug, "Enable RTP debugging", debug_usage };
01809 
01810 static struct ast_cli_entry  cli_no_debug =
01811 {{ "rtp", "no", "debug", NULL } , rtp_no_debug, "Disable RTP debugging", no_debug_usage };
01812 
01813 void ast_rtp_reload(void)
01814 {
01815    struct ast_config *cfg;
01816    char *s;
01817 
01818    rtpstart = 5000;
01819    rtpend = 31000;
01820    dtmftimeout = DEFAULT_DTMF_TIMEOUT;
01821    cfg = ast_config_load("rtp.conf");
01822    if (cfg) {
01823       if ((s = ast_variable_retrieve(cfg, "general", "rtpstart"))) {
01824          rtpstart = atoi(s);
01825          if (rtpstart < 1024)
01826             rtpstart = 1024;
01827          if (rtpstart > 65535)
01828             rtpstart = 65535;
01829       }
01830       if ((s = ast_variable_retrieve(cfg, "general", "rtpend"))) {
01831          rtpend = atoi(s);
01832          if (rtpend < 1024)
01833             rtpend = 1024;
01834          if (rtpend > 65535)
01835             rtpend = 65535;
01836       }
01837       if ((s = ast_variable_retrieve(cfg, "general", "rtpchecksums"))) {
01838 #ifdef SO_NO_CHECK
01839          if (ast_false(s))
01840             nochecksums = 1;
01841          else
01842             nochecksums = 0;
01843 #else
01844          if (ast_false(s))
01845             ast_log(LOG_WARNING, "Disabling RTP checksums is not supported on this operating system!\n");
01846 #endif
01847       }
01848       if ((s = ast_variable_retrieve(cfg, "general", "dtmftimeout"))) {
01849          dtmftimeout = atoi(s);
01850          if ((dtmftimeout < 0) || (dtmftimeout > 20000)) {
01851             ast_log(LOG_WARNING, "DTMF timeout of '%d' outside range, using default of '%d' instead\n",
01852                dtmftimeout, DEFAULT_DTMF_TIMEOUT);
01853             dtmftimeout = DEFAULT_DTMF_TIMEOUT;
01854          };
01855       }
01856       ast_config_destroy(cfg);
01857    }
01858    if (rtpstart >= rtpend) {
01859       ast_log(LOG_WARNING, "Unreasonable values for RTP start/end port in rtp.conf\n");
01860       rtpstart = 5000;
01861       rtpend = 31000;
01862    }
01863    if (option_verbose > 1)
01864       ast_verbose(VERBOSE_PREFIX_2 "RTP Allocating from port range %d -> %d\n", rtpstart, rtpend);
01865    
01866 }
01867 
01868 /*--- ast_rtp_init: Initialize the RTP system in Asterisk */
01869 void ast_rtp_init(void)
01870 {
01871    ast_cli_register(&cli_debug);
01872    ast_cli_register(&cli_debug_ip);
01873    ast_cli_register(&cli_no_debug);
01874    ast_rtp_reload();
01875 }

Generated on Fri May 26 01:45:36 2006 for Asterisk - the Open Source PBX by  doxygen 1.4.6