mirror of
https://github.com/pion/webrtc.git
synced 2025-10-07 08:01:27 +08:00
Add Header() method to Packet
Simplifies the API. Unmarshal can now return one Packet value instead of both a packet and a header. Relates to #119
This commit is contained in:

committed by
Woodrow Douglass

parent
5655d151b1
commit
0ef6602adb
@@ -30,14 +30,15 @@ func (g Goodbye) Marshal() ([]byte, error) {
|
||||
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||
*/
|
||||
|
||||
rawPacket := make([]byte, len(g.Sources)*ssrcLength)
|
||||
rawPacket := make([]byte, g.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
if len(g.Sources) > countMax {
|
||||
return nil, errTooManySources
|
||||
}
|
||||
|
||||
for i, s := range g.Sources {
|
||||
binary.BigEndian.PutUint32(rawPacket[i*ssrcLength:], s)
|
||||
binary.BigEndian.PutUint32(packetBody[i*ssrcLength:], s)
|
||||
}
|
||||
|
||||
if g.Reason != "" {
|
||||
@@ -47,25 +48,16 @@ func (g Goodbye) Marshal() ([]byte, error) {
|
||||
return nil, errReasonTooLong
|
||||
}
|
||||
|
||||
rawPacket = append(rawPacket, uint8(len(reason)))
|
||||
rawPacket = append(rawPacket, reason...)
|
||||
|
||||
// align to 32-bit boundary
|
||||
rawPacket = append(rawPacket, make([]byte, util.GetPadding(len(rawPacket)))...)
|
||||
reasonOffset := len(g.Sources) * ssrcLength
|
||||
packetBody[reasonOffset] = uint8(len(reason))
|
||||
copy(packetBody[reasonOffset+1:], reason)
|
||||
}
|
||||
|
||||
h := Header{
|
||||
Padding: false,
|
||||
Count: uint8(len(g.Sources)),
|
||||
Type: TypeGoodbye,
|
||||
Length: uint16(((headerLength + len(rawPacket)) / 4) - 1),
|
||||
}
|
||||
hData, err := h.Marshal()
|
||||
hData, err := g.Header().Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
rawPacket = append(hData, rawPacket...)
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return rawPacket, nil
|
||||
}
|
||||
@@ -126,3 +118,23 @@ func (g *Goodbye) Unmarshal(rawPacket []byte) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (g *Goodbye) Header() Header {
|
||||
return Header{
|
||||
Padding: false,
|
||||
Count: uint8(len(g.Sources)),
|
||||
Type: TypeGoodbye,
|
||||
Length: uint16((g.len() / 4) - 1),
|
||||
}
|
||||
}
|
||||
|
||||
func (g *Goodbye) len() int {
|
||||
srcsLength := len(g.Sources) * ssrcLength
|
||||
reasonLength := len(g.Reason) + 1
|
||||
|
||||
l := headerLength + srcsLength + reasonLength
|
||||
|
||||
// align to 32-bit boundary
|
||||
return l + util.GetPadding(l)
|
||||
}
|
||||
|
@@ -2,6 +2,8 @@ package rtcp
|
||||
|
||||
// Packet represents an RTCP packet, a protocol used for out-of-band statistics and control information for an RTP session
|
||||
type Packet interface {
|
||||
Header() Header
|
||||
|
||||
Marshal() ([]byte, error)
|
||||
Unmarshal(rawPacket []byte) error
|
||||
}
|
||||
|
@@ -11,6 +11,8 @@ type PictureLossIndication struct {
|
||||
|
||||
// SSRC where the loss was experienced
|
||||
MediaSSRC uint32
|
||||
|
||||
header Header
|
||||
}
|
||||
|
||||
const (
|
||||
@@ -26,9 +28,11 @@ func (p PictureLossIndication) Marshal() ([]byte, error) {
|
||||
*
|
||||
* The semantics of this FB message is independent of the payload type.
|
||||
*/
|
||||
rawPacket := make([]byte, 8)
|
||||
binary.BigEndian.PutUint32(rawPacket, p.SenderSSRC)
|
||||
binary.BigEndian.PutUint32(rawPacket[4:], p.MediaSSRC)
|
||||
rawPacket := make([]byte, p.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
binary.BigEndian.PutUint32(packetBody, p.SenderSSRC)
|
||||
binary.BigEndian.PutUint32(packetBody[4:], p.MediaSSRC)
|
||||
|
||||
h := Header{
|
||||
Count: pliFMT,
|
||||
@@ -39,8 +43,9 @@ func (p PictureLossIndication) Marshal() ([]byte, error) {
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return append(hData, rawPacket...), nil
|
||||
return rawPacket, nil
|
||||
}
|
||||
|
||||
// Unmarshal decodes the PictureLossIndication from binary
|
||||
@@ -62,3 +67,12 @@ func (p *PictureLossIndication) Unmarshal(rawPacket []byte) error {
|
||||
p.MediaSSRC = binary.BigEndian.Uint32(rawPacket[headerLength+ssrcLength:])
|
||||
return nil
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (p *PictureLossIndication) Header() Header {
|
||||
return p.header
|
||||
}
|
||||
|
||||
func (p *PictureLossIndication) len() int {
|
||||
return headerLength + ssrcLength*2
|
||||
}
|
||||
|
@@ -16,6 +16,8 @@ type RapidResynchronizationRequest struct {
|
||||
const (
|
||||
rrrFMT = 5
|
||||
rrrLength = 2
|
||||
rrrHeaderLength = ssrcLength * 2
|
||||
rrrMediaOffset = 4
|
||||
)
|
||||
|
||||
// Marshal encodes the RapidResynchronizationRequest in binary
|
||||
@@ -26,21 +28,19 @@ func (p RapidResynchronizationRequest) Marshal() ([]byte, error) {
|
||||
*
|
||||
* The semantics of this FB message is independent of the payload type.
|
||||
*/
|
||||
rawPacket := make([]byte, 8)
|
||||
binary.BigEndian.PutUint32(rawPacket, p.SenderSSRC)
|
||||
binary.BigEndian.PutUint32(rawPacket[4:], p.MediaSSRC)
|
||||
rawPacket := make([]byte, p.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
h := Header{
|
||||
Count: rrrFMT,
|
||||
Type: TypeTransportSpecificFeedback,
|
||||
Length: rrrLength,
|
||||
}
|
||||
hData, err := h.Marshal()
|
||||
binary.BigEndian.PutUint32(packetBody, p.SenderSSRC)
|
||||
binary.BigEndian.PutUint32(packetBody[rrrMediaOffset:], p.MediaSSRC)
|
||||
|
||||
hData, err := p.Header().Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return append(hData, rawPacket...), nil
|
||||
return rawPacket, nil
|
||||
}
|
||||
|
||||
// Unmarshal decodes the RapidResynchronizationRequest from binary
|
||||
@@ -63,3 +63,16 @@ func (p *RapidResynchronizationRequest) Unmarshal(rawPacket []byte) error {
|
||||
p.MediaSSRC = binary.BigEndian.Uint32(rawPacket[headerLength+ssrcLength:])
|
||||
return nil
|
||||
}
|
||||
|
||||
func (p *RapidResynchronizationRequest) len() int {
|
||||
return headerLength + rrrHeaderLength
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (p *RapidResynchronizationRequest) Header() Header {
|
||||
return Header{
|
||||
Count: rrrFMT,
|
||||
Type: TypeTransportSpecificFeedback,
|
||||
Length: rrrLength,
|
||||
}
|
||||
}
|
||||
|
@@ -23,3 +23,12 @@ func (r *RawPacket) Unmarshal(b []byte) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (r RawPacket) Header() Header {
|
||||
var h Header
|
||||
if err := h.Unmarshal(r); err != nil {
|
||||
return Header{}
|
||||
}
|
||||
return h
|
||||
}
|
||||
|
@@ -49,33 +49,29 @@ func (r ReceiverReport) Marshal() ([]byte, error) {
|
||||
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||
*/
|
||||
|
||||
rawPacket := make([]byte, ssrcLength)
|
||||
rawPacket := make([]byte, r.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
binary.BigEndian.PutUint32(rawPacket, r.SSRC)
|
||||
binary.BigEndian.PutUint32(packetBody, r.SSRC)
|
||||
|
||||
for _, rp := range r.Reports {
|
||||
for i, rp := range r.Reports {
|
||||
data, err := rp.Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
rawPacket = append(rawPacket, data...)
|
||||
offset := ssrcLength + receptionReportLength*i
|
||||
copy(packetBody[offset:], data)
|
||||
}
|
||||
|
||||
if len(r.Reports) > countMax {
|
||||
return nil, errTooManyReports
|
||||
}
|
||||
|
||||
h := Header{
|
||||
Count: uint8(len(r.Reports)),
|
||||
Type: TypeReceiverReport,
|
||||
Length: uint16(((headerLength + len(rawPacket)) / 4) - 1),
|
||||
}
|
||||
hData, err := h.Marshal()
|
||||
hData, err := r.Header().Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
rawPacket = append(hData, rawPacket...)
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return rawPacket, nil
|
||||
}
|
||||
@@ -139,3 +135,20 @@ func (r *ReceiverReport) Unmarshal(rawPacket []byte) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (r *ReceiverReport) len() int {
|
||||
repsLength := 0
|
||||
for _, rep := range r.Reports {
|
||||
repsLength += rep.len()
|
||||
}
|
||||
return headerLength + ssrcLength + repsLength
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (r *ReceiverReport) Header() Header {
|
||||
return Header{
|
||||
Count: uint8(len(r.Reports)),
|
||||
Type: TypeReceiverReport,
|
||||
Length: uint16((r.len() / 4) - 1),
|
||||
}
|
||||
}
|
||||
|
@@ -124,3 +124,7 @@ func (r *ReceptionReport) Unmarshal(rawPacket []byte) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (r *ReceptionReport) len() int {
|
||||
return receptionReportLength
|
||||
}
|
||||
|
@@ -31,6 +31,8 @@ type SenderReport struct {
|
||||
// block conveys statistics on the reception of RTP packets from a
|
||||
// single synchronization source.
|
||||
Reports []ReceptionReport
|
||||
|
||||
header Header
|
||||
}
|
||||
|
||||
var (
|
||||
@@ -87,37 +89,33 @@ func (r SenderReport) Marshal() ([]byte, error) {
|
||||
* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|
||||
*/
|
||||
|
||||
rawPacket := make([]byte, srHeaderLength)
|
||||
rawPacket := make([]byte, r.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
binary.BigEndian.PutUint32(rawPacket[srSSRCOffset:], r.SSRC)
|
||||
binary.BigEndian.PutUint64(rawPacket[srNTPOffset:], r.NTPTime)
|
||||
binary.BigEndian.PutUint32(rawPacket[srRTPOffset:], r.RTPTime)
|
||||
binary.BigEndian.PutUint32(rawPacket[srPacketCountOffset:], r.PacketCount)
|
||||
binary.BigEndian.PutUint32(rawPacket[srOctetCountOffset:], r.OctetCount)
|
||||
binary.BigEndian.PutUint32(packetBody[srSSRCOffset:], r.SSRC)
|
||||
binary.BigEndian.PutUint64(packetBody[srNTPOffset:], r.NTPTime)
|
||||
binary.BigEndian.PutUint32(packetBody[srRTPOffset:], r.RTPTime)
|
||||
binary.BigEndian.PutUint32(packetBody[srPacketCountOffset:], r.PacketCount)
|
||||
binary.BigEndian.PutUint32(packetBody[srOctetCountOffset:], r.OctetCount)
|
||||
|
||||
for _, rp := range r.Reports {
|
||||
for i, rp := range r.Reports {
|
||||
data, err := rp.Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
rawPacket = append(rawPacket, data...)
|
||||
offset := srHeaderLength + receptionReportLength*i
|
||||
copy(packetBody[offset:], data)
|
||||
}
|
||||
|
||||
if len(r.Reports) > countMax {
|
||||
return nil, errTooManyReports
|
||||
}
|
||||
|
||||
h := Header{
|
||||
Count: uint8(len(r.Reports)),
|
||||
Type: TypeSenderReport,
|
||||
Length: uint16(((headerLength + len(rawPacket)) / 4) - 1),
|
||||
}
|
||||
hData, err := h.Marshal()
|
||||
hData, err := r.Header().Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
rawPacket = append(hData, rawPacket...)
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return rawPacket, nil
|
||||
}
|
||||
@@ -197,3 +195,20 @@ func (r *SenderReport) Unmarshal(rawPacket []byte) error {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (r *SenderReport) len() int {
|
||||
repsLength := 0
|
||||
for _, rep := range r.Reports {
|
||||
repsLength += rep.len()
|
||||
}
|
||||
return headerLength + srHeaderLength + repsLength
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (r *SenderReport) Header() Header {
|
||||
return Header{
|
||||
Count: uint8(len(r.Reports)),
|
||||
Type: TypeSenderReport,
|
||||
Length: uint16((r.len() / 4) - 1),
|
||||
}
|
||||
}
|
||||
|
@@ -82,30 +82,28 @@ func (s SourceDescription) Marshal() ([]byte, error) {
|
||||
* +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+
|
||||
*/
|
||||
|
||||
rawPacket := make([]byte, 0)
|
||||
rawPacket := make([]byte, s.len())
|
||||
packetBody := rawPacket[headerLength:]
|
||||
|
||||
chunkOffset := 0
|
||||
for _, c := range s.Chunks {
|
||||
data, err := c.Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
rawPacket = append(rawPacket, data...)
|
||||
copy(packetBody[chunkOffset:], data)
|
||||
chunkOffset += len(data)
|
||||
}
|
||||
|
||||
if len(s.Chunks) > countMax {
|
||||
return nil, errTooManyChunks
|
||||
}
|
||||
|
||||
h := Header{
|
||||
Count: uint8(len(s.Chunks)),
|
||||
Type: TypeSourceDescription,
|
||||
Length: uint16(((headerLength + len(rawPacket)) / 4) - 1),
|
||||
}
|
||||
hData, err := h.Marshal()
|
||||
hData, err := s.Header().Marshal()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
rawPacket = append(hData, rawPacket...)
|
||||
copy(rawPacket, hData)
|
||||
|
||||
return rawPacket, nil
|
||||
}
|
||||
@@ -156,6 +154,23 @@ func (s *SourceDescription) Unmarshal(rawPacket []byte) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *SourceDescription) len() int {
|
||||
chunksLength := 0
|
||||
for _, c := range s.Chunks {
|
||||
chunksLength += c.len()
|
||||
}
|
||||
return headerLength + chunksLength
|
||||
}
|
||||
|
||||
// Header returns the Header associated with this packet.
|
||||
func (s *SourceDescription) Header() Header {
|
||||
return Header{
|
||||
Count: uint8(len(s.Chunks)),
|
||||
Type: TypeSourceDescription,
|
||||
Length: uint16((s.len() / 4) - 1),
|
||||
}
|
||||
}
|
||||
|
||||
// A SourceDescriptionChunk contains items describing a single RTP source
|
||||
type SourceDescriptionChunk struct {
|
||||
// The source (ssrc) or contributing source (csrc) identifier this packet describes
|
||||
|
Reference in New Issue
Block a user