|
|
// Copyright 2020, Chef. All rights reserved.
|
|
|
// https://github.com/q191201771/lal
|
|
|
//
|
|
|
// Use of this source code is governed by a MIT-style license
|
|
|
// that can be found in the License file.
|
|
|
//
|
|
|
// Author: Chef (191201771@qq.com)
|
|
|
|
|
|
package rtprtcp
|
|
|
|
|
|
import (
|
|
|
"github.com/q191201771/naza/pkg/bele"
|
|
|
)
|
|
|
|
|
|
// -------------------------------------------
|
|
|
// rfc3550 6.4.1 SR: Sender Report RTCP Packet
|
|
|
// -------------------------------------------
|
|
|
//
|
|
|
// 0 1 2 3
|
|
|
// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// header |V=2|P| RC | PT=SR=200 | length |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | SSRC of sender |
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// sender | NTP timestamp, most significant word |
|
|
|
// info +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | NTP timestamp, least significant word |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | RTP timestamp |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | sender's packet count |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | sender's octet count |
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// report | SSRC_1 (SSRC of first source) |
|
|
|
// block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// 1 | fraction lost | cumulative number of packets lost |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | extended highest sequence number received |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | interarrival jitter |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | last SR (LSR) |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | delay since last SR (DLSR) |
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// report | SSRC_2 (SSRC of second source) |
|
|
|
// block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// 2 : ... :
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// | profile-specific extensions |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
|
|
|
// ---------------------------------------------
|
|
|
// rfc3550 6.4.2 RR: Receiver Report RTCP Packet
|
|
|
// ---------------------------------------------
|
|
|
//
|
|
|
// 0 1 2 3
|
|
|
// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// header |V=2|P| RC | PT=RR=201 | length |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | SSRC of packet sender |
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// report | SSRC_1 (SSRC of first source) |
|
|
|
// block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// 1 | fraction lost | cumulative number of packets lost |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | extended highest sequence number received |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | interarrival jitter |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | last SR (LSR) |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// | delay since last SR (DLSR) |
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// report | SSRC_2 (SSRC of second source) |
|
|
|
// block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
// 2 : ... :
|
|
|
// +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
|
|
// | profile-specific extensions |
|
|
|
// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
|
|
|
|
|
const (
|
|
|
RtcpPacketTypeSr = 200 // 0xc8 Sender Report
|
|
|
RtcpPacketTypeRr = 201 // 0xc9 Receiver Report
|
|
|
RtcpPacketTypeApp = 204
|
|
|
|
|
|
RtcpHeaderLength = 4
|
|
|
|
|
|
RtcpVersion = 2
|
|
|
)
|
|
|
|
|
|
type RtcpHeader struct {
|
|
|
Version uint8 // 2b
|
|
|
Padding uint8 // 1b
|
|
|
CountOrFormat uint8 // 5b
|
|
|
PacketType uint8 // 8b
|
|
|
Length uint16 // 16b, whole packet byte length = (Length+1) * 4
|
|
|
}
|
|
|
|
|
|
type Sr struct {
|
|
|
SenderSsrc uint32
|
|
|
Msw uint32 // NTP timestamp, most significant word
|
|
|
Lsw uint32 // NTP timestamp, least significant word
|
|
|
Timestamp uint32
|
|
|
PktCnt uint32
|
|
|
OctetCnt uint32
|
|
|
}
|
|
|
|
|
|
func ParseRtcpHeader(b []byte) RtcpHeader {
|
|
|
var h RtcpHeader
|
|
|
h.Version = b[0] >> 6
|
|
|
h.Padding = (b[0] >> 5) & 0x1
|
|
|
h.CountOrFormat = b[0] & 0x1F
|
|
|
h.PacketType = b[1]
|
|
|
h.Length = bele.BeUint16(b[2:])
|
|
|
return h
|
|
|
}
|
|
|
|
|
|
// rfc3550 6.4.1
|
|
|
//
|
|
|
// @param b rtcp包,包含包头
|
|
|
func ParseSr(b []byte) Sr {
|
|
|
var s Sr
|
|
|
s.SenderSsrc = bele.BeUint32(b[4:])
|
|
|
s.Msw = bele.BeUint32(b[8:])
|
|
|
s.Lsw = bele.BeUint32(b[12:])
|
|
|
s.Timestamp = bele.BeUint32(b[16:])
|
|
|
s.PktCnt = bele.BeUint32(b[20:])
|
|
|
s.OctetCnt = bele.BeUint32(b[24:])
|
|
|
return s
|
|
|
}
|
|
|
|
|
|
// @param out 传出参数,注意,调用方保证长度>=4
|
|
|
func (r *RtcpHeader) PackTo(out []byte) {
|
|
|
out[0] = r.Version<<6 | r.Padding<<5 | r.CountOrFormat
|
|
|
out[1] = r.PacketType
|
|
|
bele.BePutUint16(out[2:], r.Length)
|
|
|
}
|
|
|
|
|
|
func (s *Sr) GetMiddleNtp() uint32 {
|
|
|
return uint32(((uint64(s.Msw)<<32 | uint64(s.Lsw)) << 16) >> 32)
|
|
|
}
|