1/* 2 * Copyright (c) 2023 Shenzhen Kaihong Digital Industry Development Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16#ifndef OHOS_SHARING_RTCP_H 17#define OHOS_SHARING_RTCP_H 18 19#include <memory> 20#include <cstdint> 21#include <string> 22#include <sys/time.h> 23#include <vector> 24#include "rtcp_def.h" 25 26namespace OHOS { 27namespace Sharing { 28/* 29 RTCP Header 30 31 0 1 2 3 32 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 33 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 34 |V=2|P| RC | PT | length | 35 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 36*/ 37 38struct RtcpHeader { 39public: 40 void SetSize(int32_t size); 41 42 int32_t GetSize() const; 43 int32_t GetPaddingSize() const; 44 45public: 46 uint8_t pt_; 47 uint8_t padding_ : 1; 48 uint8_t version_ : 2; 49 uint8_t reportCount_ : 5; 50 51private: 52 uint16_t length_; 53}; 54 55// ReportBlock 56struct ReportItem { 57public: 58 // Highest sequence number received 59 uint16_t seqMax_; 60 // Sequence number cycles count 61 uint16_t seqCycles_; 62 63 uint32_t ssrc_; 64 // Interarrival jitter 65 uint32_t jitter_; 66 // Last SR timestamp, NTP timestamp,(ntpmsw & 0xFFFF) << 16 | (ntplsw >> 16) & 0xFFFF) 67 uint32_t lastSrStamp_; 68 // Cumulative number of packets lost 69 uint32_t cumulative_ : 24; 70 // Packet loss rate (percentage) * 256 71 uint32_t fractionLost_ : 8; 72 // Delay since last SR timestamp,expressed in units of 1/65536 seconds 73 uint32_t delaySinceLastSr_; 74}; 75 76//------------------------------ RtcpSR ------------------------------// 77 78/* 79 SR: Sender Report RTCP Packet 80 81 0 1 2 3 82 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 83 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 84header |V=2|P| RC | PT=SR=200 | length | 85 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 86 | SSRC of sender | 87 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 88sender | NTP timestamp, most significant word | 89info +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 90 | NTP timestamp, least significant word | 91 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 92 | RTP timestamp | 93 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 94 | sender's packet count | 95 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 96 | sender's octet count | 97 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 98report | SSRC_1 (SSRC of first source) | 99block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 100 1 | fraction lost | cumulative number of packets lost | 101 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 102 | extended highest sequence number received | 103 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 104 | interarrival jitter | 105 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 106 | last SR (LSR) | 107 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 108 | delay since last SR (DLSR) | 109 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 110report | SSRC_2 (SSRC of second source) | 111block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 112 2 : ... : 113 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 114 | profile-specific extensions | 115 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 116*/ 117 118// sender report 119struct RtcpSR : public RtcpHeader { 120public: 121 static std::shared_ptr<RtcpSR> Create(int32_t itemCount); 122 123 RtcpSR &SetSsrc(uint32_t ssrc); 124 RtcpSR &SetNtpStamp(timeval tv); 125 RtcpSR &SetPacketCount(uint32_t); 126 RtcpSR &SetNtpStamp(uint64_t unixStampMs); 127 128 uint32_t GetSsrc() const; 129 uint32_t GetPacketCount() const; 130 uint64_t GetNtpUnixStampMS() const; 131 132 std::string GetNtpStamp() const; 133 std::vector<ReportItem *> GetItemList(); 134 135public: 136 uint32_t ssrc_; 137 // rtp timestamp 138 uint32_t rtpts_; 139 // ntp timestamp MSW(in second) 140 uint32_t ntpmsw_; 141 // ntp timestamp LSW(in picosecond) 142 uint32_t ntplsw_; 143 // sender octet count 144 uint32_t octetCount_; 145 // sender packet count 146 uint32_t packetCount_; 147 148 ReportItem items_; 149}; 150 151//------------------------------ RtcpRR ------------------------------// 152 153/* 154 RR: Receiver Report RTCP Packet 155 156 0 1 2 3 157 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 158 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 159header |V=2|P| RC | PT=RR=201 | length | 160 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 161 | SSRC of packet sender | 162 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 163report | SSRC_1 (SSRC of first source) | 164block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 165 1 | fraction lost | cumulative number of packets lost | 166 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 167 | extended highest sequence number received | 168 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 169 | interarrival jitter | 170 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 171 | last SR (LSR) | 172 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 173 | delay since last SR (DLSR) | 174 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 175report | SSRC_2 (SSRC of second source) | 176block +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 177 2 : ... : 178 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 179 | profile-specific extensions | 180 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 181*/ 182 183// Receiver Report 184struct RtcpRR : public RtcpHeader { 185public: 186 std::vector<ReportItem *> GetItemList(); 187 static std::shared_ptr<RtcpRR> Create(size_t itemCount); 188 189public: 190 uint32_t ssrc_; 191 ReportItem items_; 192}; 193 194//------------------------------ RtcpSdes ------------------------------// 195 196/* 197 SDES: Source Description RTCP Packet 198 0 1 2 3 199 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 200 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 201header |V=2|P| SC | PT=SDES=202 | length | 202 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 203chunk | SSRC/CSRC_1 | 204 1 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 205 | SDES items | 206 | ... | 207 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 208chunk | SSRC/CSRC_2 | 209 2 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 210 | SDES items | 211 | ... | 212 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 213*/ 214 215/* 216 SDES items 217 0 1 2 3 218 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 219 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 220 | SdesType | length | user and domain name ... 221 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 222*/ 223 224// Source description Chunk 225struct SdesChunk { 226public: 227 static size_t MinSize(); 228 size_t TotalBytes() const; 229 230public: 231 char text_[1]; // variable length field 232 233 uint8_t end_; // placeholder 234 uint8_t txtLen_; 235 236 uint32_t ssrc_; 237 238 SdesType type_; // uint8_t 239}; 240 241// Source description 242struct RtcpSdes : public RtcpHeader { 243public: 244 std::vector<SdesChunk *> GetChunkList(); 245 static std::shared_ptr<RtcpSdes> Create(const std::vector<std::string> &itemText); 246 247public: 248 SdesChunk chunks_; 249}; 250 251//------------------------------ RtcpFB ------------------------------// 252 253/* Common Packet Format for Feedback Messages 254 255 All FB messages MUST use a common packet format that is depicted in 256 Figure 3: 257 258 0 1 2 3 259 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 260 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 261 |V=2|P| FMT | PT | length | 262 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 263 | SSRC of packet sender | 264 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 265 | SSRC of media source | 266 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 267 : Feedback Control Information (FCI) : 268 : : 269*/ 270 271// RtcpFB: Rtpfb or Psfb 272struct RtcpFB : public RtcpHeader { 273public: 274 int32_t GetFciSize() const; 275 const uint8_t *GetFciPtr() const; 276 // for psfb fb 277 static std::shared_ptr<RtcpFB> Create(PsfbType fmt, const void *fci = nullptr, size_t fci_len = 0); 278 // for rtpfb fb 279 static std::shared_ptr<RtcpFB> Create(RtpfbType fmt, const void *fci = nullptr, size_t fci_len = 0); 280 281private: 282 static std::shared_ptr<RtcpFB> CreateInner(RtcpType type, int32_t fmt, const void *fci, size_t fci_len); 283 284public: 285 uint32_t ssrc_; 286 uint32_t ssrcMedia_; 287}; 288 289//------------------------------ RtcpBye ------------------------------// 290 291/* 292 BYE 293 294 0 1 2 3 295 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 296 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 297 |V=2|P| SC | PT=BYE=203 | length | 298 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 299 | SSRC/CSRC | 300 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 301 : ... : 302 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 303(opt) | length | reason for leaving ... 304 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 305*/ 306 307struct RtcpBye : public RtcpHeader { 308public: 309 std::string GetReason() const; 310 std::vector<uint32_t> GetSSRC() const; 311 static std::shared_ptr<RtcpBye> Create(const std::vector<uint32_t> &ssrc, const std::string &reason); 312 313public: 314 char reason_[1]; 315 // optional 316 uint8_t reasonLen_; 317 // variable length for multiple ssrc 318 uint32_t ssrc_[1]; 319}; 320 321//------------------------------ XR - RtcpXRRRTR ------------------------------// 322 323/* 324 RTCP Extended Reports (RTCP XR) Packet Format 325 326 0 1 2 3 327 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 328 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 329 |V=2|P|reserved | PT=XR=207 | length | 330 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 331 | SSRC | 332 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 333 : report blocks : 334 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 335 336*/ 337/* 338 RTCP XR - Receiver Reference Time Report Block 339 340 0 1 2 3 341 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 342 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 343 | BT=4 | reserved | block length = 2 | 344 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 345 | NTP timestamp, most significant word | 346 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 347 | NTP timestamp, least significant word | 348 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 349 350*/ 351 352// XR - Receiver Reference Time Report 353struct RtcpXRRRTR : public RtcpHeader { 354public: 355 uint8_t bt_ = 4; 356 uint8_t reserved_; 357 uint16_t blockLength_ = 0x0200; // = htons(2) 358 359 uint32_t ssrc_; 360 // ntp timestamp MSW(in second) 361 uint32_t ntpmsw_; 362 // ntp timestamp LSW(in picosecond) 363 uint32_t ntplsw_; 364}; 365 366//------------------------------ XR - RtcpXRDLRR ------------------------------// 367 368/* 369 RTCP XR - Delay since the Last Receiver Report (DLRR) 370 371 0 1 2 3 372 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 373 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 374 | BT=5 | reserved | block length | 375 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 376 | SSRC_1 (SSRC of first receiver) | sub- 377 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ block 378 | last RR (LRR) | 1 379 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 380 | delay since last RR (DLRR) | 381 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 382 | SSRC_2 (SSRC of second receiver) | sub- 383 +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ block 384 : ... : 2 385 +=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+=+ 386*/ 387 388struct RtcpXRDLRRReportItem { 389public: 390 uint32_t lrr_; 391 uint32_t ssrc_; 392 uint32_t dlrr_; 393}; 394 395// RTCP XR - Delay since the Last Receiver Report (DLRR) 396struct RtcpXRDLRR : public RtcpHeader { 397public: 398 std::vector<RtcpXRDLRRReportItem *> GetItemList(); 399 static std::shared_ptr<RtcpXRDLRR> Create(size_t itemCount); 400 401public: 402 uint8_t bt_; 403 uint8_t reserved_; 404 uint16_t blockLength_; 405 uint32_t ssrc_; 406 407 RtcpXRDLRRReportItem items_; 408}; 409} // namespace Sharing 410} // namespace OHOS 411#endif