Index: webrtc/media/engine/payload_type_mapper.cc |
diff --git a/webrtc/media/engine/payload_type_mapper.cc b/webrtc/media/engine/payload_type_mapper.cc |
new file mode 100644 |
index 0000000000000000000000000000000000000000..ae304036a697502f7f667f1af49ff04035bdb827 |
--- /dev/null |
+++ b/webrtc/media/engine/payload_type_mapper.cc |
@@ -0,0 +1,130 @@ |
+/* |
+ * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved. |
+ * |
+ * Use of this source code is governed by a BSD-style license |
+ * that can be found in the LICENSE file in the root of the source |
+ * tree. An additional intellectual property rights grant can be found |
+ * in the file PATENTS. All contributing project authors may |
+ * be found in the AUTHORS file in the root of the source tree. |
+ */ |
+ |
+#include "webrtc/media/engine/payload_type_mapper.h" |
+ |
+#include "webrtc/media/base/mediaconstants.h" |
+ |
+namespace cricket { |
+ |
+PayloadTypeMapper::PayloadTypeMapper() |
+ : next_unused_payload_type_(96), |
+ max_payload_type_(127) { |
+ // Static payload type assignments according to RFC 3551. |
+ mappings_[{"PCMU", 8000, 1}] = 0; |
+ mappings_[{"GSM", 8000, 1}] = 3; |
+ mappings_[{"G723", 8000, 1}] = 4; |
+ mappings_[{"DVI4", 8000, 1}] = 5; |
+ mappings_[{"DVI4", 16000, 1}] = 6; |
+ mappings_[{"LPC", 8000, 1}] = 7; |
+ mappings_[{"PCMA", 8000, 1}] = 8; |
+ mappings_[{"G722", 8000, 1}] = 9; |
+ mappings_[{"L16", 44100, 2}] = 10; |
+ mappings_[{"L16", 44100, 1}] = 11; |
+ mappings_[{"QCELP", 8000, 1}] = 12; |
+ mappings_[{"CN", 8000, 1}] = 13; |
+ // RFC 4566 is a bit ambiguous on the contents of the "encoding parameters" |
+ // field, which, for audio, encodes the number of channels. It is "optional |
+ // and may be omitted if the number of channels is one". Does that |
+ // necessarily imply that an omitted encoding parameter means one channel? |
+ // Since RFC 3551 doesn't specify a value for this parameter for MPA, I've |
+ // included both 0 and 1 here, to increase the chances it will be correctly |
+ // used if someone implements an MPEG audio encoder/decoder. |
+ mappings_[{"MPA", 90000, 0}] = 14; |
+ mappings_[{"MPA", 90000, 1}] = 14; |
+ mappings_[{"G728", 8000, 1}] = 15; |
+ mappings_[{"DVI4", 11025, 1}] = 16; |
+ mappings_[{"DVI4", 22050, 1}] = 17; |
+ mappings_[{"G729", 8000, 1}] = 18; |
+ |
+ // Payload type assignments currently used by WebRTC. |
+ // Includes video, to reduce collisions (and thus reassignments) |
+ const auto& apt = kCodecParamAssociatedPayloadType; |
+ mappings_[{kRtxCodecName, 90000, 0, |
+ {{apt, std::to_string(kDefaultVp8PlType)}}}] |
+ = kDefaultRtxVp8PlType; |
+ mappings_[{kRtxCodecName, 90000, 0, |
+ {{apt, std::to_string(kDefaultVp9PlType)}}}] |
+ = kDefaultRtxVp9PlType; |
+ mappings_[{kRtxCodecName, 90000, 0, |
+ {{apt, std::to_string(kDefaultRedPlType)}}}] |
+ = kDefaultRtxRedPlType; |
+ mappings_[{kRtxCodecName, 90000, 0, |
+ {{apt, std::to_string(kDefaultH264PlType)}}}] |
+ = kDefaultRtxH264PlType; |
+ mappings_[{kVp8CodecName, 90000, 0}] = kDefaultVp8PlType; |
+ mappings_[{kVp9CodecName, 90000, 0}] = kDefaultVp9PlType; |
+ mappings_[{kIlbcCodecName, 8000, 1}] = 102; |
+ mappings_[{kIsacCodecName, 16000, 1}] = 103; |
+ mappings_[{kIsacCodecName, 32000, 1}] = 104; |
+ mappings_[{kCnCodecName, 16000, 1}] = 105; |
+ mappings_[{kCnCodecName, 32000, 1}] = 106; |
+ mappings_[{kH264CodecName, 90000, 0}] = kDefaultH264PlType; |
+ mappings_[{kOpusCodecName, 48000, 2, |
+ {{"minptime", "10"}, {"useinbandfec", "1"}}}] = 111; |
+ mappings_[{kRedCodecName, 90000, 0}] = kDefaultRedPlType; |
+ mappings_[{kUlpfecCodecName, 90000, 0}] = kDefaultUlpfecType; |
+ mappings_[{kDtmfCodecName, 8000, 1}] = 126; |
+ |
+ // TODO(ossu): Try to keep this as change-proof as possible until we're able |
+ // to remove the payload type constants from everywhere in the code. |
+ for (const auto& mapping : mappings_) { |
+ used_payload_types_.insert(mapping.second); |
+ } |
+} |
+ |
+PayloadTypeMapper::~PayloadTypeMapper() = default; |
+ |
+rtc::Optional<int> PayloadTypeMapper::GetMappingFor( |
+ const webrtc::SdpAudioFormat& format) { |
+ auto iter = mappings_.find(format); |
+ if (iter != mappings_.end()) { |
+ return rtc::Optional<int>(iter->second); |
+ } |
+ |
+ int payload_type = next_unused_payload_type_; |
ivoc
2016/07/05 14:43:51
Shouldn't the value of next_unused_payload_type_ b
ossu
2016/07/05 15:31:57
Yup!
ivoc
2016/07/06 15:24:51
So... why isn't it? :-)
ossu
2016/07/06 16:23:26
Just wanted to check if you were awake. :)
But rea
|
+ while (used_payload_types_.find(payload_type) != used_payload_types_.end()) |
+ ++payload_type; |
+ if (payload_type <= max_payload_type_) { |
+ used_payload_types_.insert(payload_type); |
+ mappings_[format] = payload_type; |
+ return rtc::Optional<int>(payload_type); |
+ } |
+ |
+ return rtc::Optional<int>(); |
+} |
+ |
+rtc::Optional<int> PayloadTypeMapper::FindMappingFor( |
+ const webrtc::SdpAudioFormat& format) const { |
+ auto iter = mappings_.find(format); |
+ if (iter != mappings_.end()) |
+ return rtc::Optional<int>(iter->second); |
+ |
+ return rtc::Optional<int>(); |
+} |
+ |
+rtc::Optional<AudioCodec> PayloadTypeMapper::ToAudioCodec( |
+ const webrtc::SdpAudioFormat& format) { |
+ // TODO(ossu): We can safely set bitrate to zero here, since that field is |
+ // not presented in the SDP. It is used to ferry around some target bitrate |
+ // values for certain codecs (ISAC and Opus) and in ways it really |
+ // shouldn't. It should be removed once we no longer use CodecInsts in the |
+ // ACM or NetEq. |
+ auto opt_payload_type = GetMappingFor(format); |
+ if (opt_payload_type) { |
+ AudioCodec codec(*opt_payload_type, format.name, format.clockrate_hz, 0, |
+ format.num_channels); |
+ codec.params = format.parameters; |
+ return rtc::Optional<AudioCodec>(std::move(codec)); |
+ } |
+ |
+ return rtc::Optional<AudioCodec>(); |
+} |
+} // namespace cricket |