直播:后台 JWT 推流、前台画中画;WebRTC 服务与 Nginx WebSocket 代理
Made-with: Cursor
This commit is contained in:
353
server/vendor/github.com/pion/rtp/header_extension.go
generated
vendored
Normal file
353
server/vendor/github.com/pion/rtp/header_extension.go
generated
vendored
Normal file
@@ -0,0 +1,353 @@
|
||||
// SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
package rtp
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"fmt"
|
||||
"io"
|
||||
)
|
||||
|
||||
const (
|
||||
headerExtensionProfileOneByte = 0xBEDE
|
||||
headerExtensionProfileTwoByte = 0x1000
|
||||
headerExtensionIDReserved = 0xF
|
||||
)
|
||||
|
||||
// HeaderExtension represents an RTP extension header.
|
||||
type HeaderExtension interface {
|
||||
Set(id uint8, payload []byte) error
|
||||
GetIDs() []uint8
|
||||
Get(id uint8) []byte
|
||||
Del(id uint8) error
|
||||
|
||||
Unmarshal(buf []byte) (int, error)
|
||||
Marshal() ([]byte, error)
|
||||
MarshalTo(buf []byte) (int, error)
|
||||
MarshalSize() int
|
||||
}
|
||||
|
||||
// OneByteHeaderExtension is an RFC8285 one-byte header extension.
|
||||
type OneByteHeaderExtension struct {
|
||||
payload []byte
|
||||
}
|
||||
|
||||
// Set sets the extension payload for the specified ID.
|
||||
func (e *OneByteHeaderExtension) Set(id uint8, buf []byte) error {
|
||||
if id < 1 || id > 14 {
|
||||
return fmt.Errorf("%w actual(%d)", errRFC8285OneByteHeaderIDRange, id)
|
||||
}
|
||||
if len(buf) > 16 {
|
||||
return fmt.Errorf("%w actual(%d)", errRFC8285OneByteHeaderSize, len(buf))
|
||||
}
|
||||
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n] >> 4
|
||||
payloadLen := int(e.payload[n]&^0xF0 + 1)
|
||||
n++
|
||||
|
||||
if extid == id {
|
||||
e.payload = append(e.payload[:n+1], append(buf, e.payload[n+1+payloadLen:]...)...)
|
||||
return nil
|
||||
}
|
||||
n += payloadLen
|
||||
}
|
||||
e.payload = append(e.payload, (id<<4 | uint8(len(buf)-1)))
|
||||
e.payload = append(e.payload, buf...)
|
||||
binary.BigEndian.PutUint16(e.payload[2:4], binary.BigEndian.Uint16(e.payload[2:4])+1)
|
||||
return nil
|
||||
}
|
||||
|
||||
// GetIDs returns the available IDs.
|
||||
func (e *OneByteHeaderExtension) GetIDs() []uint8 {
|
||||
ids := make([]uint8, 0, binary.BigEndian.Uint16(e.payload[2:4]))
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n] >> 4
|
||||
payloadLen := int(e.payload[n]&^0xF0 + 1)
|
||||
n++
|
||||
|
||||
if extid == headerExtensionIDReserved {
|
||||
break
|
||||
}
|
||||
|
||||
ids = append(ids, extid)
|
||||
n += payloadLen
|
||||
}
|
||||
return ids
|
||||
}
|
||||
|
||||
// Get returns the payload of the extension with the given ID.
|
||||
func (e *OneByteHeaderExtension) Get(id uint8) []byte {
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n] >> 4
|
||||
payloadLen := int(e.payload[n]&^0xF0 + 1)
|
||||
n++
|
||||
|
||||
if extid == id {
|
||||
return e.payload[n : n+payloadLen]
|
||||
}
|
||||
n += payloadLen
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Del deletes the extension with the specified ID.
|
||||
func (e *OneByteHeaderExtension) Del(id uint8) error {
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n] >> 4
|
||||
payloadLen := int(e.payload[n]&^0xF0 + 1)
|
||||
|
||||
if extid == id {
|
||||
e.payload = append(e.payload[:n], e.payload[n+1+payloadLen:]...)
|
||||
return nil
|
||||
}
|
||||
n += payloadLen + 1
|
||||
}
|
||||
return errHeaderExtensionNotFound
|
||||
}
|
||||
|
||||
// Unmarshal parses the extension payload.
|
||||
func (e *OneByteHeaderExtension) Unmarshal(buf []byte) (int, error) {
|
||||
profile := binary.BigEndian.Uint16(buf[0:2])
|
||||
if profile != headerExtensionProfileOneByte {
|
||||
return 0, fmt.Errorf("%w actual(%x)", errHeaderExtensionNotFound, buf[0:2])
|
||||
}
|
||||
e.payload = buf
|
||||
return len(buf), nil
|
||||
}
|
||||
|
||||
// Marshal returns the extension payload.
|
||||
func (e OneByteHeaderExtension) Marshal() ([]byte, error) {
|
||||
return e.payload, nil
|
||||
}
|
||||
|
||||
// MarshalTo writes the extension payload to the given buffer.
|
||||
func (e OneByteHeaderExtension) MarshalTo(buf []byte) (int, error) {
|
||||
size := e.MarshalSize()
|
||||
if size > len(buf) {
|
||||
return 0, io.ErrShortBuffer
|
||||
}
|
||||
return copy(buf, e.payload), nil
|
||||
}
|
||||
|
||||
// MarshalSize returns the size of the extension payload.
|
||||
func (e OneByteHeaderExtension) MarshalSize() int {
|
||||
return len(e.payload)
|
||||
}
|
||||
|
||||
// TwoByteHeaderExtension is an RFC8285 two-byte header extension.
|
||||
type TwoByteHeaderExtension struct {
|
||||
payload []byte
|
||||
}
|
||||
|
||||
// Set sets the extension payload for the specified ID.
|
||||
func (e *TwoByteHeaderExtension) Set(id uint8, buf []byte) error {
|
||||
if id < 1 || id > 255 {
|
||||
return fmt.Errorf("%w actual(%d)", errRFC8285TwoByteHeaderIDRange, id)
|
||||
}
|
||||
if len(buf) > 255 {
|
||||
return fmt.Errorf("%w actual(%d)", errRFC8285TwoByteHeaderSize, len(buf))
|
||||
}
|
||||
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n]
|
||||
n++
|
||||
|
||||
payloadLen := int(e.payload[n])
|
||||
n++
|
||||
|
||||
if extid == id {
|
||||
e.payload = append(e.payload[:n+2], append(buf, e.payload[n+2+payloadLen:]...)...)
|
||||
return nil
|
||||
}
|
||||
n += payloadLen
|
||||
}
|
||||
e.payload = append(e.payload, id, uint8(len(buf)))
|
||||
e.payload = append(e.payload, buf...)
|
||||
binary.BigEndian.PutUint16(e.payload[2:4], binary.BigEndian.Uint16(e.payload[2:4])+1)
|
||||
return nil
|
||||
}
|
||||
|
||||
// GetIDs returns the available IDs.
|
||||
func (e *TwoByteHeaderExtension) GetIDs() []uint8 {
|
||||
ids := make([]uint8, 0, binary.BigEndian.Uint16(e.payload[2:4]))
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n]
|
||||
n++
|
||||
|
||||
payloadLen := int(e.payload[n])
|
||||
n++
|
||||
|
||||
ids = append(ids, extid)
|
||||
n += payloadLen
|
||||
}
|
||||
return ids
|
||||
}
|
||||
|
||||
// Get returns the payload of the extension with the given ID.
|
||||
func (e *TwoByteHeaderExtension) Get(id uint8) []byte {
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n]
|
||||
n++
|
||||
|
||||
payloadLen := int(e.payload[n])
|
||||
n++
|
||||
|
||||
if extid == id {
|
||||
return e.payload[n : n+payloadLen]
|
||||
}
|
||||
n += payloadLen
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Del deletes the extension with the specified ID.
|
||||
func (e *TwoByteHeaderExtension) Del(id uint8) error {
|
||||
for n := 4; n < len(e.payload); {
|
||||
if e.payload[n] == 0x00 { // padding
|
||||
n++
|
||||
continue
|
||||
}
|
||||
|
||||
extid := e.payload[n]
|
||||
|
||||
payloadLen := int(e.payload[n+1])
|
||||
|
||||
if extid == id {
|
||||
e.payload = append(e.payload[:n], e.payload[n+2+payloadLen:]...)
|
||||
return nil
|
||||
}
|
||||
n += payloadLen + 2
|
||||
}
|
||||
return errHeaderExtensionNotFound
|
||||
}
|
||||
|
||||
// Unmarshal parses the extension payload.
|
||||
func (e *TwoByteHeaderExtension) Unmarshal(buf []byte) (int, error) {
|
||||
profile := binary.BigEndian.Uint16(buf[0:2])
|
||||
if profile != headerExtensionProfileTwoByte {
|
||||
return 0, fmt.Errorf("%w actual(%x)", errHeaderExtensionNotFound, buf[0:2])
|
||||
}
|
||||
e.payload = buf
|
||||
return len(buf), nil
|
||||
}
|
||||
|
||||
// Marshal returns the extension payload.
|
||||
func (e TwoByteHeaderExtension) Marshal() ([]byte, error) {
|
||||
return e.payload, nil
|
||||
}
|
||||
|
||||
// MarshalTo marshals the extension to the given buffer.
|
||||
func (e TwoByteHeaderExtension) MarshalTo(buf []byte) (int, error) {
|
||||
size := e.MarshalSize()
|
||||
if size > len(buf) {
|
||||
return 0, io.ErrShortBuffer
|
||||
}
|
||||
return copy(buf, e.payload), nil
|
||||
}
|
||||
|
||||
// MarshalSize returns the size of the extension payload.
|
||||
func (e TwoByteHeaderExtension) MarshalSize() int {
|
||||
return len(e.payload)
|
||||
}
|
||||
|
||||
// RawExtension represents an RFC3550 header extension.
|
||||
type RawExtension struct {
|
||||
payload []byte
|
||||
}
|
||||
|
||||
// Set sets the extension payload for the specified ID.
|
||||
func (e *RawExtension) Set(id uint8, payload []byte) error {
|
||||
if id != 0 {
|
||||
return fmt.Errorf("%w actual(%d)", errRFC3550HeaderIDRange, id)
|
||||
}
|
||||
e.payload = payload
|
||||
return nil
|
||||
}
|
||||
|
||||
// GetIDs returns the available IDs.
|
||||
func (e *RawExtension) GetIDs() []uint8 {
|
||||
return []uint8{0}
|
||||
}
|
||||
|
||||
// Get returns the payload of the extension with the given ID.
|
||||
func (e *RawExtension) Get(id uint8) []byte {
|
||||
if id == 0 {
|
||||
return e.payload
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// Del deletes the extension with the specified ID.
|
||||
func (e *RawExtension) Del(id uint8) error {
|
||||
if id == 0 {
|
||||
e.payload = nil
|
||||
return nil
|
||||
}
|
||||
return fmt.Errorf("%w actual(%d)", errRFC3550HeaderIDRange, id)
|
||||
}
|
||||
|
||||
// Unmarshal parses the extension from the given buffer.
|
||||
func (e *RawExtension) Unmarshal(buf []byte) (int, error) {
|
||||
profile := binary.BigEndian.Uint16(buf[0:2])
|
||||
if profile == headerExtensionProfileOneByte || profile == headerExtensionProfileTwoByte {
|
||||
return 0, fmt.Errorf("%w actual(%x)", errHeaderExtensionNotFound, buf[0:2])
|
||||
}
|
||||
e.payload = buf
|
||||
return len(buf), nil
|
||||
}
|
||||
|
||||
// Marshal returns the raw extension payload.
|
||||
func (e RawExtension) Marshal() ([]byte, error) {
|
||||
return e.payload, nil
|
||||
}
|
||||
|
||||
// MarshalTo marshals the extension to the given buffer.
|
||||
func (e RawExtension) MarshalTo(buf []byte) (int, error) {
|
||||
size := e.MarshalSize()
|
||||
if size > len(buf) {
|
||||
return 0, io.ErrShortBuffer
|
||||
}
|
||||
return copy(buf, e.payload), nil
|
||||
}
|
||||
|
||||
// MarshalSize returns the size of the extension when marshaled.
|
||||
func (e RawExtension) MarshalSize() int {
|
||||
return len(e.payload)
|
||||
}
|
||||
Reference in New Issue
Block a user