1 /* 2 * Copyright (c) 2013 The WebRTC project authors. All Rights Reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11 #ifndef WEBRTC_MODULES_RTP_RTCP_INCLUDE_RTP_PAYLOAD_REGISTRY_H_ 12 #define WEBRTC_MODULES_RTP_RTCP_INCLUDE_RTP_PAYLOAD_REGISTRY_H_ 13 14 #include <map> 15 16 #include "webrtc/base/scoped_ptr.h" 17 #include "webrtc/modules/rtp_rtcp/source/rtp_receiver_strategy.h" 18 #include "webrtc/modules/rtp_rtcp/source/rtp_utility.h" 19 20 namespace webrtc { 21 22 // This strategy deals with the audio/video-specific aspects 23 // of payload handling. 24 class RTPPayloadStrategy { 25 public: ~RTPPayloadStrategy()26 virtual ~RTPPayloadStrategy() {} 27 28 virtual bool CodecsMustBeUnique() const = 0; 29 30 virtual bool PayloadIsCompatible(const RtpUtility::Payload& payload, 31 const uint32_t frequency, 32 const size_t channels, 33 const uint32_t rate) const = 0; 34 35 virtual void UpdatePayloadRate(RtpUtility::Payload* payload, 36 const uint32_t rate) const = 0; 37 38 virtual RtpUtility::Payload* CreatePayloadType( 39 const char payloadName[RTP_PAYLOAD_NAME_SIZE], 40 const int8_t payloadType, 41 const uint32_t frequency, 42 const size_t channels, 43 const uint32_t rate) const = 0; 44 45 virtual int GetPayloadTypeFrequency( 46 const RtpUtility::Payload& payload) const = 0; 47 48 static RTPPayloadStrategy* CreateStrategy(const bool handling_audio); 49 50 protected: RTPPayloadStrategy()51 RTPPayloadStrategy() {} 52 }; 53 54 class RTPPayloadRegistry { 55 public: 56 // The registry takes ownership of the strategy. 57 explicit RTPPayloadRegistry(RTPPayloadStrategy* rtp_payload_strategy); 58 ~RTPPayloadRegistry(); 59 60 int32_t RegisterReceivePayload( 61 const char payload_name[RTP_PAYLOAD_NAME_SIZE], 62 const int8_t payload_type, 63 const uint32_t frequency, 64 const size_t channels, 65 const uint32_t rate, 66 bool* created_new_payload_type); 67 68 int32_t DeRegisterReceivePayload( 69 const int8_t payload_type); 70 71 int32_t ReceivePayloadType( 72 const char payload_name[RTP_PAYLOAD_NAME_SIZE], 73 const uint32_t frequency, 74 const size_t channels, 75 const uint32_t rate, 76 int8_t* payload_type) const; 77 78 bool RtxEnabled() const; 79 80 void SetRtxSsrc(uint32_t ssrc); 81 82 bool GetRtxSsrc(uint32_t* ssrc) const; 83 84 void SetRtxPayloadType(int payload_type, int associated_payload_type); 85 86 bool IsRtx(const RTPHeader& header) const; 87 88 // DEPRECATED. Use RestoreOriginalPacket below that takes a uint8_t* 89 // restored_packet, instead of a uint8_t**. 90 // TODO(noahric): Remove this when all callers have been updated. 91 bool RestoreOriginalPacket(uint8_t** restored_packet, 92 const uint8_t* packet, 93 size_t* packet_length, 94 uint32_t original_ssrc, 95 const RTPHeader& header) const; 96 97 bool RestoreOriginalPacket(uint8_t* restored_packet, 98 const uint8_t* packet, 99 size_t* packet_length, 100 uint32_t original_ssrc, 101 const RTPHeader& header) const; 102 103 bool IsRed(const RTPHeader& header) const; 104 105 // Returns true if the media of this RTP packet is encapsulated within an 106 // extra header, such as RTX or RED. 107 bool IsEncapsulated(const RTPHeader& header) const; 108 109 bool GetPayloadSpecifics(uint8_t payload_type, PayloadUnion* payload) const; 110 111 int GetPayloadTypeFrequency(uint8_t payload_type) const; 112 113 // DEPRECATED. Use PayloadTypeToPayload below that returns const Payload* 114 // instead of taking output parameter. 115 // TODO(danilchap): Remove this when all callers have been updated. PayloadTypeToPayload(const uint8_t payload_type,RtpUtility::Payload * & payload)116 bool PayloadTypeToPayload(const uint8_t payload_type, 117 RtpUtility::Payload*& payload) const { // NOLINT 118 payload = 119 const_cast<RtpUtility::Payload*>(PayloadTypeToPayload(payload_type)); 120 return payload != nullptr; 121 } 122 const RtpUtility::Payload* PayloadTypeToPayload(uint8_t payload_type) const; 123 ResetLastReceivedPayloadTypes()124 void ResetLastReceivedPayloadTypes() { 125 CriticalSectionScoped cs(crit_sect_.get()); 126 last_received_payload_type_ = -1; 127 last_received_media_payload_type_ = -1; 128 } 129 130 // This sets the payload type of the packets being received from the network 131 // on the media SSRC. For instance if packets are encapsulated with RED, this 132 // payload type will be the RED payload type. 133 void SetIncomingPayloadType(const RTPHeader& header); 134 135 // Returns true if the new media payload type has not changed. 136 bool ReportMediaPayloadType(uint8_t media_payload_type); 137 red_payload_type()138 int8_t red_payload_type() const { 139 CriticalSectionScoped cs(crit_sect_.get()); 140 return red_payload_type_; 141 } ulpfec_payload_type()142 int8_t ulpfec_payload_type() const { 143 CriticalSectionScoped cs(crit_sect_.get()); 144 return ulpfec_payload_type_; 145 } last_received_payload_type()146 int8_t last_received_payload_type() const { 147 CriticalSectionScoped cs(crit_sect_.get()); 148 return last_received_payload_type_; 149 } set_last_received_payload_type(int8_t last_received_payload_type)150 void set_last_received_payload_type(int8_t last_received_payload_type) { 151 CriticalSectionScoped cs(crit_sect_.get()); 152 last_received_payload_type_ = last_received_payload_type; 153 } 154 last_received_media_payload_type()155 int8_t last_received_media_payload_type() const { 156 CriticalSectionScoped cs(crit_sect_.get()); 157 return last_received_media_payload_type_; 158 } 159 use_rtx_payload_mapping_on_restore()160 bool use_rtx_payload_mapping_on_restore() const { 161 CriticalSectionScoped cs(crit_sect_.get()); 162 return use_rtx_payload_mapping_on_restore_; 163 } 164 set_use_rtx_payload_mapping_on_restore(bool val)165 void set_use_rtx_payload_mapping_on_restore(bool val) { 166 CriticalSectionScoped cs(crit_sect_.get()); 167 use_rtx_payload_mapping_on_restore_ = val; 168 } 169 170 private: 171 // Prunes the payload type map of the specific payload type, if it exists. 172 void DeregisterAudioCodecOrRedTypeRegardlessOfPayloadType( 173 const char payload_name[RTP_PAYLOAD_NAME_SIZE], 174 const size_t payload_name_length, 175 const uint32_t frequency, 176 const size_t channels, 177 const uint32_t rate); 178 179 bool IsRtxInternal(const RTPHeader& header) const; 180 181 rtc::scoped_ptr<CriticalSectionWrapper> crit_sect_; 182 RtpUtility::PayloadTypeMap payload_type_map_; 183 rtc::scoped_ptr<RTPPayloadStrategy> rtp_payload_strategy_; 184 int8_t red_payload_type_; 185 int8_t ulpfec_payload_type_; 186 int8_t incoming_payload_type_; 187 int8_t last_received_payload_type_; 188 int8_t last_received_media_payload_type_; 189 bool rtx_; 190 // TODO(changbin): Remove rtx_payload_type_ once interop with old clients that 191 // only understand one RTX PT is no longer needed. 192 int rtx_payload_type_; 193 // Mapping rtx_payload_type_map_[rtx] = associated. 194 std::map<int, int> rtx_payload_type_map_; 195 // When true, use rtx_payload_type_map_ when restoring RTX packets to get the 196 // correct payload type. 197 bool use_rtx_payload_mapping_on_restore_; 198 uint32_t ssrc_rtx_; 199 }; 200 201 } // namespace webrtc 202 203 #endif // WEBRTC_MODULES_RTP_RTCP_INCLUDE_RTP_PAYLOAD_REGISTRY_H_ 204