uint32_thigh_ext_seq_recv;/* Packet loss calculation, highest extended sequence number received and processed for stats */
uint16_tcycle;/* Packet loss calculation, sequence number cycle of the current RTCP report interval */
uint32_tbad_seq;/* Bad SEQ found, used to detect reset on the other side */
uint16_tbase_seq;/* Packet loss calculation, first sequence number received */
uint32_tcum_lost;/* Packet loss calculation, cumulative number of packet lost */
uint32_tlast_recv_lsr_local;/* RTT calculation, When receiving an SR we save our local timestamp in fraction of 65536 seconds */
uint32_tlast_recv_lsr_peer;/* RTT calculation, When receiving an SR we extract the middle 32bits of the remote NTP timestamp to include it in the next SR LSR */
}switch_rtcp_numbers_t;
typedefstruct{
...
...
@@ -884,7 +900,7 @@ typedef struct {
#endif
#if SWITCH_BYTE_ORDER == __BIG_ENDIAN
typedefstruct{
typedefstructswitch_rtcp_hdr_s{
unsignedversion:2;/* protocol version */
unsignedp:1;/* padding flag */
unsignedcount:5;/* number of reception report blocks */
...
...
@@ -894,7 +910,7 @@ typedef struct {
#else /* BIG_ENDIAN */
typedefstruct{
typedefstructswitch_rtcp_hdr_s{
unsignedcount:5;/* number of reception report blocks */
uint32_t dlsr; /* The delay, expressed in units of 1/65536 seconds, between receiving the last SR packet from source SSRC_n and sending this reception report block */
};
/* This was previously used, but a similar struct switch_rtcp_report_block existed and I merged them both. It also fixed the problem of lost being an integer and not a unsigned.
struct switch_rtcp_source {
unsigned ssrc1:32;
unsigned fraction_lost:8;
unsigned cumulative_lost:24;
unsigned hi_seq_recieved:32;
unsigned interarrival_jitter:32;
unsigned lsr:32;
unsigned lsr_delay:32;
};
*/
struct switch_rtcp_sr_head {
unsignedssrc:32;
unsignedntp_msw:32;
unsignedntp_lsw:32;
unsignedts:32;
unsignedpc:32;
unsignedoc:32;
};
#if SWITCH_BYTE_ORDER == __BIG_ENDIAN
structswitch_rtcp_s_desc_head{
unsignedv:2;
unsignedpadding:1;
unsignedsc:5;
unsignedpt:8;
unsignedlength:16;
uint32_t ssrc;
uint32_t ntp_msw;
uint32_t ntp_lsw;
uint32_t ts;
uint32_t pc;
uint32_t oc;
};
#else /* BIG_ENDIAN */
structswitch_rtcp_s_desc_head{
unsignedsc:5;
unsignedpadding:1;
unsignedv:2;
unsignedpt:8;
unsignedlength:16;
struct switch_rtcp_sender_info {
uint32_t ntp_msw;
uint32_t ntp_lsw;
uint32_t ts;
uint32_t pc;
uint32_t oc;
};
#endif
structswitch_rtcp_s_desc_trunk{
unsignedssrc:32;
unsignedcname:8;
unsignedlength:8;
chartext[1];
struct switch_rtcp_sender_report {
uint32_t ssrc;
struct switch_rtcp_sender_info sender_info;
struct switch_rtcp_report_block report_block;
};
/* This is limited to a single block with force description. Not to be used as reference of the rtcp packet*/
ntp_sec = sec+NTP_TIME_OFFSET; /* convert to NTP seconds */
sr->ntp_msw = htonl(ntp_sec); /* store result in "most significant word" */
ntp_usec = now - (sec*1000000); /* remove seconds to keep only the microseconds */
sr->ntp_lsw = htonl(ntp_usec*(double)(((uint64_t)1)<<32)*1.0e-6); /* convert microseconds to fraction of 32bits and store result in "least significatn word" */
/* Delay since Last Sender Report (DLSR) : 32bits, 1/65536 seconds */
lsr_now = (uint32_t)(ntp_usec*0.065536) | (ntp_sec&0x0000ffff)<<16; /* 0.065536 is used for convertion from useconds to fraction of 65536 (x65536/1000000) */
/* Extracting LSR from NTP timestamp and save it */
lsr = (ntohl(sr->sender_info.ntp_lsw)&0xffff0000)>>16 | (ntohl(sr->sender_info.ntp_msw)&0x0000ffff)<<16; /* The middle 32 bits out of 64 in the NTP timestamp */
rtp_session->stats.rtcp.last_recv_lsr_peer = htonl(lsr); /* Save it include it in the next SR */
rtp_session->stats.rtcp.last_recv_lsr_local = lsr_now; /* Save it to calculate DLSR when generating next SR */
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_DEBUG10,"Received a SR with %d report blocks, " \
/* Currently in passthru mode RTT will not be accurate, some work as to be done (something like mapping the NTP timestamp with a local one) to have RTT from both legs */
if (report_block->lsr && !rtp_session->flags[SWITCH_RTP_FLAG_RTCP_PASSTHRU]) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session),SWITCH_LOG_DEBUG10,"Received an RTCP packet of length %"SWITCH_SIZE_T_FMT" bytes\n",*bytes);
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session),SWITCH_LOG_DEBUG10,"RTCP packet type is %d\n",rtp_session->rtcp_recv_msg_p->header.type);