aboutsummaryrefslogtreecommitdiff
path: root/src/cmd/ip/snoopy/rtcp.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/cmd/ip/snoopy/rtcp.c')
-rwxr-xr-xsrc/cmd/ip/snoopy/rtcp.c97
1 files changed, 97 insertions, 0 deletions
diff --git a/src/cmd/ip/snoopy/rtcp.c b/src/cmd/ip/snoopy/rtcp.c
new file mode 100755
index 00000000..1036caaf
--- /dev/null
+++ b/src/cmd/ip/snoopy/rtcp.c
@@ -0,0 +1,97 @@
+#include <u.h>
+#include <libc.h>
+#include <ip.h>
+#include "dat.h"
+#include "protos.h"
+
+typedef struct Hdr Hdr;
+struct Hdr {
+ uchar hdr; // RTCP header
+ uchar pt; // Packet type
+ uchar len[2]; // Report length
+ uchar ssrc[4]; // Synchronization source identifier
+ uchar ntp[8]; // NTP time stamp
+ uchar rtp[4]; // RTP time stamp
+ uchar pktc[4]; // Sender's packet count
+ uchar octc[4]; // Sender's octect count
+};
+
+typedef struct Report Report;
+struct Report {
+ uchar ssrc[4]; // SSRC identifier
+ uchar lost[4]; // Fraction + cumu lost
+ uchar seqhi[4]; // Highest seq number received
+ uchar jitter[4]; // Interarrival jitter
+ uchar lsr[4]; // Last SR
+ uchar dlsr[4]; // Delay since last SR
+};
+
+enum{
+ RTCPLEN = 28, // Minimum size of an RTCP header
+ REPORTLEN = 24,
+};
+
+
+static void
+p_compile(Filter *f)
+{
+ sysfatal("unknown rtcp field: %s", f->s);
+}
+
+static int
+p_filter(Filter *f, Msg *m)
+{
+ USED(f);
+ USED(m);
+ return 0;
+}
+
+static int
+p_seprint(Msg *m)
+{
+ Hdr*h;
+ Report*r;
+ int rc, i, frac;
+ float dlsr;
+
+ if(m->pe - m->ps < RTCPLEN)
+ return -1;
+
+ h = (Hdr*)m->ps;
+ if(m->pe - m->ps < (NetS(h->len) + 1) * 4)
+ return -1;
+
+ rc = h->hdr & 0x1f;
+ m->ps += RTCPLEN;
+ m->p = seprint(m->p, m->e, "version=%d rc=%d tp=%d ssrc=%8ux ntp=%d.%.10ud rtp=%d pktc=%d octc=%d hlen=%d",
+ (h->hdr >> 6) & 3, rc, h->pt, NetL(h->ssrc),
+ NetL(h->ntp), (uint)NetL(&h->ntp[4]), NetL(h->rtp),
+ NetL(h->pktc), NetL(h->octc),
+ (NetS(h->len) + 1) * 4);
+
+ for(i = 0; i < rc; i++){
+ r = (Report*)m->ps;
+ m->ps += REPORTLEN;
+
+ frac = (int)(((float)r->lost[0] * 100.) / 256.);
+ r->lost[0] = 0;
+ dlsr = (float)NetL(r->dlsr) / 65536.;
+
+ m->p = seprint(m->p, m->e, "\n\trr(csrc=%8ux frac=%3d%% cumu=%10d seqhi=%10ud jitter=%10d lsr=%8ux dlsr=%f)",
+ NetL(r->ssrc), frac, NetL(r->lost), NetL(r->seqhi),
+ NetL(r->jitter), NetL(r->lsr),
+ dlsr);
+ }
+ m->pr = nil;
+ return 0;
+}
+
+Proto rtcp = {
+ "rtcp",
+ p_compile,
+ p_filter,
+ p_seprint,
+ nil,
+ nil,
+ defaultframer,
+};