cd ../gtk ==> cd ../ui/gtk
[obnox/wireshark/wip.git] / tap-rtp-common.c
1 /* tap-rtp-common.c
2  * RTP stream handler functions used by tshark and wireshark
3  *
4  * $Id$
5  *
6  * Copyright 2008, Ericsson AB
7  * By Balint Reczey <balint.reczey@ericsson.com>
8  *
9  * most functions are copied from ui/gtk/rtp_stream.c and ui/gtk/rtp_analisys.c
10  * Copyright 2003, Alcatel Business Systems
11  * By Lars Ruoff <lars.ruoff@gmx.net>
12  *
13  * Wireshark - Network traffic analyzer
14  * By Gerald Combs <gerald@wireshark.org>
15  * Copyright 1998 Gerald Combs
16  *
17  * This program is free software; you can redistribute it and/or
18  * modify it under the terms of the GNU General Public License
19  * as published by the Free Software Foundation; either version 2
20  * of the License, or (at your option) any later version.
21  *
22  * This program is distributed in the hope that it will be useful,
23  * but WITHOUT ANY WARRANTY; without even the implied warranty of
24  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
25  * GNU General Public License for more details.
26  *
27  * You should have received a copy of the GNU General Public License
28  * along with this program; if not, write to the Free Software
29  * Foundation,  Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
30  */
31
32 #ifdef HAVE_CONFIG_H
33 # include "config.h"
34 #endif
35
36 #include <stdio.h>
37 #include <math.h>
38 #include "globals.h"
39
40 #include <epan/tap.h>
41 #include <string.h>
42 #include <epan/rtp_pt.h>
43 #include <epan/addr_resolv.h>
44 #include <epan/dissectors/packet-rtp.h>
45 #include "ui/gtk/rtp_stream.h"
46 #include "tap-rtp-common.h"
47
48 /* XXX: are changes needed to properly handle situations where
49         info_all_data_present == FALSE ?
50         E.G., when captured frames are truncated.
51  */
52
53 /****************************************************************************/
54 /* GCompareFunc style comparison function for _rtp_stream_info */
55 gint rtp_stream_info_cmp(gconstpointer aa, gconstpointer bb)
56 {
57         const struct _rtp_stream_info* a = aa;
58         const struct _rtp_stream_info* b = bb;
59
60         if (a==b)
61                 return 0;
62         if (a==NULL || b==NULL)
63                 return 1;
64         if (ADDRESSES_EQUAL(&(a->src_addr), &(b->src_addr))
65                 && (a->src_port == b->src_port)
66                 && ADDRESSES_EQUAL(&(a->dest_addr), &(b->dest_addr))
67                 && (a->dest_port == b->dest_port)
68                 && (a->ssrc == b->ssrc))
69                 return 0;
70         else
71                 return 1;
72 }
73
74
75 /****************************************************************************/
76 /* when there is a [re]reading of packet's */
77 void rtpstream_reset(rtpstream_tapinfo_t *tapinfo)
78 {
79         GList* list;
80
81         if (tapinfo->mode == TAP_ANALYSE) {
82                 /* free the data items first */
83                 list = g_list_first(tapinfo->strinfo_list);
84                 while (list)
85                 {
86                         g_free(list->data);
87                         list = g_list_next(list);
88                 }
89                 g_list_free(tapinfo->strinfo_list);
90                 tapinfo->strinfo_list = NULL;
91                 tapinfo->nstreams = 0;
92                 tapinfo->npackets = 0;
93         }
94
95         ++(tapinfo->launch_count);
96
97         return;
98 }
99
100 void rtpstream_reset_cb(void *arg)
101 {
102         rtpstream_reset(arg);
103 }
104
105 /*
106 * rtpdump file format
107 *
108 * The file starts with the tool to be used for playing this file,
109 * the multicast/unicast receive address and the port.
110 *
111 * #!rtpplay1.0 224.2.0.1/3456\n
112 *
113 * This is followed by one binary header (RD_hdr_t) and one RD_packet_t
114 * structure for each received packet.  All fields are in network byte
115 * order.  We don't need the source IP address since we can do mapping
116 * based on SSRC.  This saves (a little) space, avoids non-IPv4
117 * problems and privacy/security concerns. The header is followed by
118 * the RTP/RTCP header and (optionally) the actual payload.
119 */
120
121 #define RTPFILE_VERSION "1.0"
122
123 /*
124 * Write a header to the current output file.
125 * The header consists of an identifying string, followed
126 * by a binary structure.
127 */
128 void rtp_write_header(rtp_stream_info_t *strinfo, FILE *file)
129 {
130         guint32 start_sec;     /* start of recording (GMT) (seconds) */
131         guint32 start_usec;    /* start of recording (GMT) (microseconds)*/
132         guint32 source;        /* network source (multicast address) */
133         size_t sourcelen;
134         guint16 port;          /* UDP port */
135         guint16 padding;       /* 2 padding bytes */
136
137         fprintf(file, "#!rtpplay%s %s/%u\n", RTPFILE_VERSION,
138                 get_addr_name(&(strinfo->dest_addr)),
139                 strinfo->dest_port);
140
141         start_sec = g_htonl(strinfo->start_sec);
142         start_usec = g_htonl(strinfo->start_usec);
143         /* rtpdump only accepts guint32 as source, will be fake for IPv6 */
144         memset(&source, 0, sizeof source);
145         sourcelen = strinfo->src_addr.len;
146         if (sourcelen > sizeof source)
147                 sourcelen = sizeof source;
148         memcpy(&source, strinfo->src_addr.data, sourcelen);
149         port = g_htons(strinfo->src_port);
150         padding = 0;
151
152         if (fwrite(&start_sec, 4, 1, file) == 0)
153                 return;
154         if (fwrite(&start_usec, 4, 1, file) == 0)
155                 return;
156         if (fwrite(&source, 4, 1, file) == 0)
157                 return;
158         if (fwrite(&port, 2, 1, file) == 0)
159                 return;
160         if (fwrite(&padding, 2, 1, file) == 0)
161                 return;
162 }
163
164 /* utility function for writing a sample to file in rtpdump -F dump format (.rtp)*/
165 void rtp_write_sample(rtp_sample_t* sample, FILE* file)
166 {
167         guint16 length;    /* length of packet, including this header (may
168                              be smaller than plen if not whole packet recorded) */
169         guint16 plen;      /* actual header+payload length for RTP, 0 for RTCP */
170         guint32 offset;    /* milliseconds since the start of recording */
171
172         length = g_htons(sample->header.frame_length + 8);
173         plen = g_htons(sample->header.frame_length);
174         offset = g_htonl(sample->header.rec_time);
175
176         if (fwrite(&length, 2, 1, file) == 0)
177                 return;
178         if (fwrite(&plen, 2, 1, file) == 0)
179                 return;
180         if (fwrite(&offset, 4, 1, file) == 0)
181                 return;
182         if (fwrite(sample->frame, sample->header.frame_length, 1, file) == 0)
183                 return;
184 }
185
186
187 /****************************************************************************/
188 /* whenever a RTP packet is seen by the tap listener */
189 int rtpstream_packet(void *arg, packet_info *pinfo, epan_dissect_t *edt _U_, const void *arg2)
190 {
191         rtpstream_tapinfo_t *tapinfo = arg;
192         const struct _rtp_info *rtpinfo = arg2;
193         rtp_stream_info_t tmp_strinfo;
194         rtp_stream_info_t *strinfo = NULL;
195         GList* list;
196         rtp_sample_t sample;
197
198         struct _rtp_conversation_info *p_conv_data = NULL;
199
200         /* gather infos on the stream this packet is part of */
201         COPY_ADDRESS(&(tmp_strinfo.src_addr), &(pinfo->src));
202         tmp_strinfo.src_port = pinfo->srcport;
203         COPY_ADDRESS(&(tmp_strinfo.dest_addr), &(pinfo->dst));
204         tmp_strinfo.dest_port = pinfo->destport;
205         tmp_strinfo.ssrc = rtpinfo->info_sync_src;
206         tmp_strinfo.pt = rtpinfo->info_payload_type;
207         tmp_strinfo.info_payload_type_str = rtpinfo->info_payload_type_str;
208
209         if (tapinfo->mode == TAP_ANALYSE) {
210                 /* check whether we already have a stream with these parameters in the list */
211                 list = g_list_first(tapinfo->strinfo_list);
212                 while (list)
213                 {
214                         if (rtp_stream_info_cmp(&tmp_strinfo, (rtp_stream_info_t*)(list->data))==0)
215                         {
216                                 strinfo = (rtp_stream_info_t*)(list->data);  /*found!*/
217                                 break;
218                         }
219                         list = g_list_next(list);
220                 }
221
222                 /* not in the list? then create a new entry */
223                 if (!strinfo) {
224                         tmp_strinfo.npackets = 0;
225                         tmp_strinfo.first_frame_num = pinfo->fd->num;
226                         tmp_strinfo.start_sec = (guint32) pinfo->fd->abs_ts.secs;
227                         tmp_strinfo.start_usec = pinfo->fd->abs_ts.nsecs/1000;
228                         tmp_strinfo.start_rel_sec = (guint32) pinfo->fd->rel_ts.secs;
229                         tmp_strinfo.start_rel_usec = pinfo->fd->rel_ts.nsecs/1000;
230                         tmp_strinfo.tag_vlan_error = 0;
231                         tmp_strinfo.tag_diffserv_error = 0;
232                         tmp_strinfo.vlan_id = 0;
233                         tmp_strinfo.problem = FALSE;
234
235                         /* reset RTP stats */
236                         tmp_strinfo.rtp_stats.first_packet = TRUE;
237                         tmp_strinfo.rtp_stats.max_delta = 0;
238                         tmp_strinfo.rtp_stats.max_jitter = 0;
239                         tmp_strinfo.rtp_stats.mean_jitter = 0;
240                         tmp_strinfo.rtp_stats.delta = 0;
241                         tmp_strinfo.rtp_stats.diff = 0;
242                         tmp_strinfo.rtp_stats.jitter = 0;
243                         tmp_strinfo.rtp_stats.bandwidth = 0;
244                         tmp_strinfo.rtp_stats.total_bytes = 0;
245                         tmp_strinfo.rtp_stats.bw_start_index = 0;
246                         tmp_strinfo.rtp_stats.bw_index = 0;
247                         tmp_strinfo.rtp_stats.timestamp = 0;
248                         tmp_strinfo.rtp_stats.max_nr = 0;
249                         tmp_strinfo.rtp_stats.total_nr = 0;
250                         tmp_strinfo.rtp_stats.sequence = 0;
251                         tmp_strinfo.rtp_stats.start_seq_nr = 0;
252                         tmp_strinfo.rtp_stats.stop_seq_nr = 0;
253                         tmp_strinfo.rtp_stats.cycles = 0;
254                         tmp_strinfo.rtp_stats.under = FALSE;
255                         tmp_strinfo.rtp_stats.start_time = 0;
256                         tmp_strinfo.rtp_stats.time = 0;
257                         tmp_strinfo.rtp_stats.reg_pt = PT_UNDEFINED;
258
259             /* Get the Setup frame number who set this RTP stream */
260             p_conv_data = p_get_proto_data(pinfo->fd, proto_get_id_by_filter_name("rtp"));
261             if (p_conv_data)
262                                 tmp_strinfo.setup_frame_number = p_conv_data->frame_number;
263             else
264                 tmp_strinfo.setup_frame_number = 0xFFFFFFFF;
265
266                         strinfo = g_malloc(sizeof(rtp_stream_info_t));
267                         *strinfo = tmp_strinfo;  /* memberwise copy of struct */
268                         tapinfo->strinfo_list = g_list_append(tapinfo->strinfo_list, strinfo);
269                 }
270
271                 /* get RTP stats for the packet */
272                 rtp_packet_analyse(&(strinfo->rtp_stats), pinfo, rtpinfo);
273                 if (strinfo->rtp_stats.flags & STAT_FLAG_WRONG_TIMESTAMP
274                         || strinfo->rtp_stats.flags & STAT_FLAG_WRONG_SEQ)
275                         strinfo->problem = TRUE;
276
277
278                 /* increment the packets counter for this stream */
279                 ++(strinfo->npackets);
280                 strinfo->stop_rel_sec = (guint32) pinfo->fd->rel_ts.secs;
281                 strinfo->stop_rel_usec = pinfo->fd->rel_ts.nsecs/1000;
282
283                 /* increment the packets counter of all streams */
284                 ++(tapinfo->npackets);
285
286                 return 1;  /* refresh output */
287         }
288         else if (tapinfo->mode == TAP_SAVE) {
289                 if (rtp_stream_info_cmp(&tmp_strinfo, tapinfo->filter_stream_fwd)==0) {
290                         /* XXX - what if rtpinfo->info_all_data_present is
291                            FALSE, so that we don't *have* all the data? */
292                         sample.header.rec_time =
293                                 (pinfo->fd->abs_ts.nsecs/1000 + 1000000 - tapinfo->filter_stream_fwd->start_usec)/1000
294                                 + (guint32) (pinfo->fd->abs_ts.secs - tapinfo->filter_stream_fwd->start_sec - 1)*1000;
295                         sample.header.frame_length = rtpinfo->info_data_len;
296                         sample.frame = rtpinfo->info_data;
297                         rtp_write_sample(&sample, tapinfo->save_file);
298                 }
299         }
300 #ifdef __GTK_H__
301         else if (tapinfo->mode == TAP_MARK) {
302                 if (rtp_stream_info_cmp(&tmp_strinfo, tapinfo->filter_stream_fwd)==0
303                         || rtp_stream_info_cmp(&tmp_strinfo, tapinfo->filter_stream_rev)==0)
304                 {
305                         cf_mark_frame(&cfile, pinfo->fd);
306                 }
307         }
308 #endif
309         return 0;
310 }
311
312
313 typedef struct _key_value {
314   guint32  key;
315   guint32  value;
316 } key_value;
317
318
319 /* RTP sampling clock rates for fixed payload types as defined in
320  http://www.iana.org/assignments/rtp-parameters */
321 static const key_value clock_map[] = {
322         {PT_PCMU,       8000},
323         {PT_1016,       8000},
324         {PT_G721,       8000},
325         {PT_GSM,        8000},
326         {PT_G723,       8000},
327         {PT_DVI4_8000,  8000},
328         {PT_DVI4_16000, 16000},
329         {PT_LPC,        8000},
330         {PT_PCMA,       8000},
331         {PT_G722,       8000},
332         {PT_L16_STEREO, 44100},
333         {PT_L16_MONO,   44100},
334         {PT_QCELP,      8000},
335         {PT_CN,         8000},
336         {PT_MPA,        90000},
337         {PT_G728,       8000},
338         {PT_G728,       8000},
339         {PT_DVI4_11025, 11025},
340         {PT_DVI4_22050, 22050},
341         {PT_G729,       8000},
342         {PT_CN_OLD,     8000},
343         {PT_CELB,       90000},
344         {PT_JPEG,       90000},
345         {PT_NV,         90000},
346         {PT_H261,       90000},
347         {PT_MPV,        90000},
348         {PT_MP2T,       90000},
349         {PT_H263,       90000},
350 };
351
352 #define NUM_CLOCK_VALUES        (sizeof clock_map / sizeof clock_map[0])
353
354 static guint32
355 get_clock_rate(guint32 key)
356 {
357         size_t i;
358
359         for (i = 0; i < NUM_CLOCK_VALUES; i++) {
360                 if (clock_map[i].key == key)
361                         return clock_map[i].value;
362         }
363         return 0;
364 }
365
366 typedef struct _mimetype_and_clock {
367         const gchar   *pt_mime_name_str;
368         guint32 value;
369 } mimetype_and_clock;
370 /*      RTP sampling clock rates for
371         "In addition to the RTP payload formats (encodings) listed in the RTP
372         Payload Types table, there are additional payload formats that do not
373         have static RTP payload types assigned but instead use dynamic payload
374         type number assignment.  Each payload format is named by a registered
375         MIME subtype"
376         http://www.iana.org/assignments/rtp-parameters.
377
378         NOTE: Please keep the mimetypes in case insensitive alphabetical order.
379 */
380 static const mimetype_and_clock mimetype_and_clock_map[] = {
381         {"AMR",         8000},                  /* [RFC4867][RFC3267] */
382         {"AMR-WB",      16000},                 /* [RFC4867][RFC3267] */
383         {"BMPEG",       90000},                 /* [RFC2343],[RFC3555] */
384         {"BT656",       90000},                 /* [RFC2431],[RFC3555] */
385         {"DV",          90000},                 /* [RFC3189] */
386         {"EVRC",        8000},                  /* [RFC3558] */
387         {"EVRC0",       8000},                  /* [RFC4788] */
388         {"EVRC1",       8000},                  /* [RFC4788] */
389         {"EVRCB",       8000},                  /* [RFC4788] */
390         {"EVRCB0",      8000},                  /* [RFC4788] */
391         {"EVRCB1",      8000},                  /* [RFC4788] */
392         {"EVRCWB",      16000},                 /* [RFC5188] */
393         {"EVRCWB0",     16000},                 /* [RFC5188] */
394         {"EVRCWB1",     16000},                 /* [RFC5188] */
395         {"G7221",       16000},                 /* [RFC3047] */
396         {"G726-16",     8000},                  /* [RFC3551][RFC4856] */
397         {"G726-24",     8000},                  /* [RFC3551][RFC4856] */
398         {"G726-32",     8000},                  /* [RFC3551][RFC4856] */
399         {"G726-40",     8000},                  /* [RFC3551][RFC4856] */
400         {"G729D",       8000},                  /* [RFC3551][RFC4856] */
401         {"G729E",       8000},                  /* [RFC3551][RFC4856] */
402         {"GSM-EFR",     8000},                  /* [RFC3551] */
403         {"H263-1998",   90000},         /* [RFC2429],[RFC3555] */
404         {"H263-2000",   90000},         /* [RFC2429],[RFC3555] */
405         {"H264",        90000},         /* [RFC3984] */
406         {"MP1S",        90000},                 /* [RFC2250],[RFC3555] */
407         {"MP2P",        90000},                 /* [RFC2250],[RFC3555] */
408         {"MP4V-ES",     90000},                 /* [RFC3016] */
409         {"mpa-robust",  90000},         /* [RFC3119] */
410         {"pointer",     90000},                 /* [RFC2862] */
411         {"raw",         90000},                 /* [RFC4175] */
412         {"red",         1000},                  /* [RFC4102] */
413         {"SMV",         8000},                  /* [RFC3558] */
414         {"SMV0",        8000},                  /* [RFC3558] */
415         {"t140",        1000},                  /* [RFC4103] */
416         {"telephone-event", 8000},  /* [RFC4733] */
417 };
418
419 #define NUM_DYN_CLOCK_VALUES    (sizeof mimetype_and_clock_map / sizeof mimetype_and_clock_map[0])
420
421 static guint32
422 get_dyn_pt_clock_rate(gchar *payload_type_str)
423 {
424         int i;
425
426         /* Search for matching mimetype in reverse order to avoid false matches
427          * when pt_mime_name_str is the prefix of payload_type_str */
428         for (i = NUM_DYN_CLOCK_VALUES - 1; i > -1 ; i--) {
429                 if (g_ascii_strncasecmp(mimetype_and_clock_map[i].pt_mime_name_str,payload_type_str,(strlen(mimetype_and_clock_map[i].pt_mime_name_str))) == 0)
430                         return mimetype_and_clock_map[i].value;
431         }
432
433         return 0;
434 }
435
436 /****************************************************************************/
437 int rtp_packet_analyse(tap_rtp_stat_t *statinfo,
438                               packet_info *pinfo,
439                               const struct _rtp_info *rtpinfo)
440 {
441         double current_time;
442         double current_jitter;
443         double current_diff = 0;
444         double nominaltime;
445         double arrivaltime;             /* Time relative to start_time */
446         double expected_time;
447         double absskew;
448         guint32 clock_rate;
449
450         /* Store the current time */
451         current_time = nstime_to_msec(&pinfo->fd->rel_ts);
452
453         /*  Is this the first packet we got in this direction? */
454         if (statinfo->first_packet) {
455                 statinfo->start_seq_nr = rtpinfo->info_seq_num;
456                 statinfo->stop_seq_nr = rtpinfo->info_seq_num;
457                 statinfo->seq_num = rtpinfo->info_seq_num;
458                 statinfo->start_time = current_time;
459                 statinfo->timestamp = rtpinfo->info_timestamp;
460                 statinfo->first_timestamp = rtpinfo->info_timestamp;
461                 statinfo->time = current_time;
462                 statinfo->lastnominaltime = 0;
463                 statinfo->pt = rtpinfo->info_payload_type;
464                 statinfo->reg_pt = rtpinfo->info_payload_type;
465                 statinfo->bw_history[statinfo->bw_index].bytes = rtpinfo->info_data_len + 28;
466                 statinfo->bw_history[statinfo->bw_index].time = current_time;
467                 statinfo->bw_index++;
468                 statinfo->total_bytes += rtpinfo->info_data_len + 28;
469                 statinfo->bandwidth = (double)(statinfo->total_bytes*8)/1000;
470                 /* Not needed ? initialised to zero? */
471                 statinfo->delta = 0;
472                 statinfo->jitter = 0;
473                 statinfo->diff = 0;
474
475                 statinfo->total_nr++;
476                 statinfo->flags |= STAT_FLAG_FIRST;
477                 if (rtpinfo->info_marker_set) {
478                         statinfo->flags |= STAT_FLAG_MARKER;
479                 }
480                 statinfo->first_packet = FALSE;
481                 return 0;
482         }
483
484         /* Reset flags */
485         statinfo->flags = 0;
486
487         /* When calculating expected rtp packets the seq number can wrap around
488          * so we have to count the number of cycles
489          * Variable cycles counts the wraps around in forwarding connection and
490          * under is flag that indicates where we are
491          *
492          * XXX How to determine number of cycles with all possible lost, late
493          * and duplicated packets without any doubt? It seems to me, that
494          * because of all possible combination of late, duplicated or lost
495          * packets, this can only be more or less good approximation
496          *
497          * There are some combinations (rare but theoretically possible),
498          * where below code won't work correctly - statistic may be wrong then.
499          */
500
501         /* So if the current sequence number is less than the start one
502          * we assume, that there is another cycle running
503          */
504         if ((rtpinfo->info_seq_num < statinfo->start_seq_nr) && (statinfo->under == FALSE)){
505                 statinfo->cycles++;
506                 statinfo->under = TRUE;
507         }
508         /* what if the start seq nr was 0? Then the above condition will never
509          * be true, so we add another condition. XXX The problem would arise
510          * if one of the packets with seq nr 0 or 65535 would be lost or late
511          */
512         else if ((rtpinfo->info_seq_num == 0) && (statinfo->stop_seq_nr == 65535) &&
513                 (statinfo->under == FALSE)){
514                 statinfo->cycles++;
515                 statinfo->under = TRUE;
516         }
517         /* the whole round is over, so reset the flag */
518         else if ((rtpinfo->info_seq_num > statinfo->start_seq_nr) && (statinfo->under != FALSE)) {
519                 statinfo->under = FALSE;
520         }
521
522         /* Since it is difficult to count lost, duplicate or late packets separately,
523          * we would like to know at least how many times the sequence number was not ok
524          */
525
526         /* If the current seq number equals the last one or if we are here for
527          * the first time, then it is ok, we just store the current one as the last one
528          */
529         if ( (statinfo->seq_num+1 == rtpinfo->info_seq_num) || (statinfo->flags & STAT_FLAG_FIRST) )
530                 statinfo->seq_num = rtpinfo->info_seq_num;
531         /* If the first one is 65535. XXX same problem as above: if seq 65535 or 0 is lost... */
532         else if ( (statinfo->seq_num == 65535) && (rtpinfo->info_seq_num == 0) )
533                 statinfo->seq_num = rtpinfo->info_seq_num;
534         /* Lost packets */
535         else if (statinfo->seq_num+1 < rtpinfo->info_seq_num) {
536                 statinfo->seq_num = rtpinfo->info_seq_num;
537                 statinfo->sequence++;
538                 statinfo->flags |= STAT_FLAG_WRONG_SEQ;
539         }
540         /* Late or duplicated */
541         else if (statinfo->seq_num+1 > rtpinfo->info_seq_num) {
542                 statinfo->sequence++;
543                 statinfo->flags |= STAT_FLAG_WRONG_SEQ;
544         }
545
546         /* Check payload type */
547         if (rtpinfo->info_payload_type == PT_CN
548                 || rtpinfo->info_payload_type == PT_CN_OLD)
549                 statinfo->flags |= STAT_FLAG_PT_CN;
550         if (statinfo->pt == PT_CN
551                 || statinfo->pt == PT_CN_OLD)
552                 statinfo->flags |= STAT_FLAG_FOLLOW_PT_CN;
553         if (rtpinfo->info_payload_type != statinfo->pt)
554                 statinfo->flags |= STAT_FLAG_PT_CHANGE;
555         statinfo->pt = rtpinfo->info_payload_type;
556
557         /*
558          * Return 0 for unknown payload types
559          * Ignore jitter calculation for clockrate = 0
560          */
561         if (statinfo->pt < 96 ){
562                 clock_rate = get_clock_rate(statinfo->pt);
563         }else{ /* Dynamic PT */
564                 if ( rtpinfo->info_payload_type_str != NULL ){
565                         /* Is it a "telephone-event" ?
566                          * Timestamp is not increased for telepone-event packets impacting
567                          * calculation of Jitter Skew and clock drift.
568                          * see 2.2.1 of RFC 4733
569                          */
570                         if (g_ascii_strncasecmp("telephone-event",rtpinfo->info_payload_type_str,(strlen("telephone-event")))==0){
571                                 clock_rate = 0;
572                                 statinfo->flags |= STAT_FLAG_PT_T_EVENT;
573                         }else{
574                                 if(rtpinfo->info_payload_rate !=0){
575                                         clock_rate = rtpinfo->info_payload_rate;
576                                 }else{
577                                         clock_rate = get_dyn_pt_clock_rate(rtpinfo-> info_payload_type_str);
578                                 }
579                         }
580                 }else{
581                         clock_rate = 0;
582                 }
583         }
584
585                 /* Handle wraparound ? */
586         arrivaltime = current_time - statinfo->start_time;
587
588         if (statinfo->first_timestamp > rtpinfo->info_timestamp){
589                 /* Handle wraparound */
590                 nominaltime = (double)(rtpinfo->info_timestamp + 0xffffffff - statinfo->first_timestamp + 1);
591         }else{
592                 nominaltime = (double)(rtpinfo->info_timestamp - statinfo->first_timestamp);
593         }
594
595         /* Can only analyze defined sampling rates */
596     if (clock_rate != 0) {
597                 statinfo->clock_rate = clock_rate;
598                 /* Convert from sampling clock to ms */
599                 nominaltime = nominaltime /(clock_rate/1000);
600
601                 /* Calculate the current jitter(in ms) */
602                 if (!statinfo->first_packet) {
603                         expected_time = statinfo->time + (nominaltime - statinfo->lastnominaltime);
604                         current_diff = fabs(current_time - expected_time);
605                         current_jitter = (15 * statinfo->jitter + current_diff) / 16;
606
607                         statinfo->delta = current_time-(statinfo->time);
608                         statinfo->jitter = current_jitter;
609                         statinfo->diff = current_diff;
610                 }
611                 statinfo->lastnominaltime = nominaltime;
612                 /* Calculate skew, i.e. absolute jitter that also catches clock drift
613                  * Skew is positive if TS (nominal) is too fast
614                  */
615                 statinfo->skew    = nominaltime - arrivaltime;
616                 absskew = fabs(statinfo->skew);
617                 if(absskew > fabs(statinfo->max_skew)){
618                         statinfo->max_skew = statinfo->skew;
619                 }
620                 /* Gather data for calculation of average, minimum and maximum framerate based on timestamp */
621 #if 0
622                 if (numPackets > 0 && (!hardPayloadType || !alternatePayloadType)) {
623                         /* Skip first packet and possibly alternate payload type packets */
624                         double dt;
625                         dt     = nominaltime - statinfo->lastnominaltime;
626                         sumdt += 1.0 * dt;
627                         numdt += (dt != 0 ? 1 : 0);
628                         mindt  = (dt < mindt ? dt : mindt);
629                         maxdt  = (dt > maxdt ? dt : maxdt);
630                 }
631 #endif
632                 /* Gather data for calculation of skew least square */
633                 statinfo->sumt   += 1.0 * current_time;
634                 statinfo->sumTS  += 1.0 * nominaltime;
635                 statinfo->sumt2  += 1.0 * current_time * current_time;
636                 statinfo->sumtTS += 1.0 * current_time * nominaltime;
637         }
638
639         /* Calculate the BW in Kbps adding the IP+UDP header to the RTP -> IP header+8bytes(UDP) */
640         statinfo->bw_history[statinfo->bw_index].bytes = rtpinfo->info_data_len + pinfo->iphdrlen + 8;
641         statinfo->bw_history[statinfo->bw_index].time = current_time;
642
643         /* Check if there are more than 1sec in the history buffer to calculate BW in bps. If so, remove those for the calculation */
644         while ((statinfo->bw_history[statinfo->bw_start_index].time+1000/* ms */)<current_time){
645                 statinfo->total_bytes -= statinfo->bw_history[statinfo->bw_start_index].bytes;
646                 statinfo->bw_start_index++;
647                 if (statinfo->bw_start_index == BUFF_BW) statinfo->bw_start_index=0;
648         };
649         /* IP hdr + UDP + RTP */
650         statinfo->total_bytes += rtpinfo->info_data_len + pinfo->iphdrlen + 8;
651         statinfo->bandwidth = (double)(statinfo->total_bytes*8)/1000;
652         statinfo->bw_index++;
653         if (statinfo->bw_index == BUFF_BW) statinfo->bw_index = 0;
654
655
656         /* Is it a packet with the mark bit set? */
657         if (rtpinfo->info_marker_set) {
658                 statinfo->delta_timestamp = rtpinfo->info_timestamp - statinfo->timestamp;
659                 if (rtpinfo->info_timestamp > statinfo->timestamp){
660                         statinfo->flags |= STAT_FLAG_MARKER;
661                 }
662                 else{
663                         statinfo->flags |= STAT_FLAG_WRONG_TIMESTAMP;
664                 }
665         }
666         /* Is it a regular packet? */
667         if (!(statinfo->flags & STAT_FLAG_FIRST)
668                 && !(statinfo->flags & STAT_FLAG_MARKER)
669                 && !(statinfo->flags & STAT_FLAG_PT_CN)
670                 && !(statinfo->flags & STAT_FLAG_WRONG_TIMESTAMP)
671                 && !(statinfo->flags & STAT_FLAG_FOLLOW_PT_CN)) {
672                 /* Include it in maximum delta calculation */
673                 if (statinfo->delta > statinfo->max_delta) {
674                         statinfo->max_delta = statinfo->delta;
675                         statinfo->max_nr = pinfo->fd->num;
676                 }
677                 if (clock_rate != 0) {
678                         /* Maximum and mean jitter calculation */
679                         if (statinfo->jitter > statinfo->max_jitter) {
680                                 statinfo->max_jitter = statinfo->jitter;
681                         }
682                         statinfo->mean_jitter = (statinfo->mean_jitter*statinfo->total_nr + current_diff) / (statinfo->total_nr+1);
683                 }
684         }
685         /* Regular payload change? (CN ignored) */
686         if (!(statinfo->flags & STAT_FLAG_FIRST)
687                 && !(statinfo->flags & STAT_FLAG_PT_CN)) {
688                 if ((statinfo->pt != statinfo->reg_pt)
689                         && (statinfo->reg_pt != PT_UNDEFINED)) {
690                         statinfo->flags |= STAT_FLAG_REG_PT_CHANGE;
691                 }
692         }
693
694         /* Set regular payload*/
695         if (!(statinfo->flags & STAT_FLAG_PT_CN)) {
696                 statinfo->reg_pt = statinfo->pt;
697         }
698
699         statinfo->time = current_time;
700         statinfo->timestamp = rtpinfo->info_timestamp;
701         statinfo->stop_seq_nr = rtpinfo->info_seq_num;
702         statinfo->total_nr++;
703
704         return 0;
705 }
706
707