-
Notifications
You must be signed in to change notification settings - Fork 1.7k
/
rtpcodec.go
125 lines (104 loc) · 3.42 KB
/
rtpcodec.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
// SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
// SPDX-License-Identifier: MIT
package webrtc
import (
"strings"
"github.com/pion/webrtc/v4/internal/fmtp"
)
// RTPCodecType determines the type of a codec
type RTPCodecType int
const (
// RTPCodecTypeUnknown is the enum's zero-value
RTPCodecTypeUnknown RTPCodecType = iota
// RTPCodecTypeAudio indicates this is an audio codec
RTPCodecTypeAudio
// RTPCodecTypeVideo indicates this is a video codec
RTPCodecTypeVideo
)
func (t RTPCodecType) String() string {
switch t {
case RTPCodecTypeAudio:
return "audio" //nolint: goconst
case RTPCodecTypeVideo:
return "video" //nolint: goconst
default:
return ErrUnknownType.Error()
}
}
// NewRTPCodecType creates a RTPCodecType from a string
func NewRTPCodecType(r string) RTPCodecType {
switch {
case strings.EqualFold(r, RTPCodecTypeAudio.String()):
return RTPCodecTypeAudio
case strings.EqualFold(r, RTPCodecTypeVideo.String()):
return RTPCodecTypeVideo
default:
return RTPCodecType(0)
}
}
// RTPCodecCapability provides information about codec capabilities.
//
// https://w3c.github.io/webrtc-pc/#dictionary-rtcrtpcodeccapability-members
type RTPCodecCapability struct {
MimeType string
ClockRate uint32
Channels uint16
SDPFmtpLine string
RTCPFeedback []RTCPFeedback
}
// RTPHeaderExtensionCapability is used to define a RFC5285 RTP header extension supported by the codec.
//
// https://w3c.github.io/webrtc-pc/#dom-rtcrtpcapabilities-headerextensions
type RTPHeaderExtensionCapability struct {
URI string
}
// RTPHeaderExtensionParameter represents a negotiated RFC5285 RTP header extension.
//
// https://w3c.github.io/webrtc-pc/#dictionary-rtcrtpheaderextensionparameters-members
type RTPHeaderExtensionParameter struct {
URI string
ID int
}
// RTPCodecParameters is a sequence containing the media codecs that an RtpSender
// will choose from, as well as entries for RTX, RED and FEC mechanisms. This also
// includes the PayloadType that has been negotiated
//
// https://w3c.github.io/webrtc-pc/#rtcrtpcodecparameters
type RTPCodecParameters struct {
RTPCodecCapability
PayloadType PayloadType
statsID string
}
// RTPParameters is a list of negotiated codecs and header extensions
//
// https://w3c.github.io/webrtc-pc/#dictionary-rtcrtpparameters-members
type RTPParameters struct {
HeaderExtensions []RTPHeaderExtensionParameter
Codecs []RTPCodecParameters
}
type codecMatchType int
const (
codecMatchNone codecMatchType = 0
codecMatchPartial codecMatchType = 1
codecMatchExact codecMatchType = 2
)
// Do a fuzzy find for a codec in the list of codecs
// Used for lookup up a codec in an existing list to find a match
// Returns codecMatchExact, codecMatchPartial, or codecMatchNone
func codecParametersFuzzySearch(needle RTPCodecParameters, haystack []RTPCodecParameters) (RTPCodecParameters, codecMatchType) {
needleFmtp := fmtp.Parse(needle.RTPCodecCapability.MimeType, needle.RTPCodecCapability.SDPFmtpLine)
// First attempt to match on MimeType + SDPFmtpLine
for _, c := range haystack {
cfmtp := fmtp.Parse(c.RTPCodecCapability.MimeType, c.RTPCodecCapability.SDPFmtpLine)
if needleFmtp.Match(cfmtp) {
return c, codecMatchExact
}
}
// Fallback to just MimeType
for _, c := range haystack {
if strings.EqualFold(c.RTPCodecCapability.MimeType, needle.RTPCodecCapability.MimeType) {
return c, codecMatchPartial
}
}
return RTPCodecParameters{}, codecMatchNone
}