|
| 1 | +import NIOCore |
| 2 | +//===----------------------------------------------------------------------===// |
| 3 | +// |
| 4 | +// This source file is part of the SwiftRTC open source project |
| 5 | +// |
| 6 | +// Copyright (c) 2024 ngRTC and the SwiftRTC project authors |
| 7 | +// Licensed under MIT License |
| 8 | +// |
| 9 | +// See LICENSE.txt for license information |
| 10 | +// See CONTRIBUTORS.txt for the list of SwiftRTC project authors |
| 11 | +// |
| 12 | +// SPDX-License-Identifier: MIT |
| 13 | +// |
| 14 | +//===----------------------------------------------------------------------===// |
| 15 | +import XCTest |
| 16 | + |
| 17 | +@testable import RTCP |
| 18 | + |
| 19 | +func decodedPacket() -> ExtendedReport { |
| 20 | + ExtendedReport( |
| 21 | + senderSsrc: 0x0102_0304, |
| 22 | + reports: [ |
| 23 | + LossRLEReportBlock( |
| 24 | + isLossRLE: true, |
| 25 | + t: 12, |
| 26 | + |
| 27 | + ssrc: 0x1234_5689, |
| 28 | + beginSeq: 5, |
| 29 | + endSeq: 12, |
| 30 | + chunks: [ |
| 31 | + Chunk(rawValue: 0x4006), Chunk(rawValue: 0x0006), Chunk(rawValue: 0x8765), |
| 32 | + Chunk(rawValue: 0x0000), |
| 33 | + ] |
| 34 | + ), |
| 35 | + DuplicateRLEReportBlock( |
| 36 | + isLossRLE: false, |
| 37 | + t: 6, |
| 38 | + |
| 39 | + ssrc: 0x1234_5689, |
| 40 | + beginSeq: 5, |
| 41 | + endSeq: 12, |
| 42 | + chunks: [ |
| 43 | + Chunk(rawValue: 0x4123), Chunk(rawValue: 0x3FFF), Chunk(rawValue: 0xFFFF), |
| 44 | + Chunk(rawValue: 0x0000), |
| 45 | + ] |
| 46 | + ), |
| 47 | + PacketReceiptTimesReportBlock( |
| 48 | + t: 3, |
| 49 | + |
| 50 | + ssrc: 0x9876_5432, |
| 51 | + beginSeq: 15432, |
| 52 | + endSeq: 15577, |
| 53 | + receiptTime: [0x1111_1111, 0x2222_2222, 0x3333_3333, 0x4444_4444, 0x5555_5555] |
| 54 | + ), |
| 55 | + ReceiverReferenceTimeReportBlock( |
| 56 | + ntpTimestamp: 0x0102_0304_0506_0708 |
| 57 | + ), |
| 58 | + DLRRReportBlock( |
| 59 | + reports: [ |
| 60 | + DLRRReport( |
| 61 | + ssrc: 0x8888_8888, |
| 62 | + lastRr: 0x1234_5678, |
| 63 | + dlrr: 0x9999_9999 |
| 64 | + ), |
| 65 | + DLRRReport( |
| 66 | + ssrc: 0x0909_0909, |
| 67 | + lastRr: 0x1234_5678, |
| 68 | + dlrr: 0x9999_9999 |
| 69 | + ), |
| 70 | + DLRRReport( |
| 71 | + ssrc: 0x1122_3344, |
| 72 | + lastRr: 0x1234_5678, |
| 73 | + dlrr: 0x9999_9999 |
| 74 | + ), |
| 75 | + ] |
| 76 | + ), |
| 77 | + StatisticsSummaryReportBlock( |
| 78 | + lossReports: true, |
| 79 | + duplicateReports: true, |
| 80 | + jitterReports: true, |
| 81 | + ttlOrHopLimit: TTLorHopLimitType.ipv4, |
| 82 | + |
| 83 | + ssrc: 0xFEDC_BA98, |
| 84 | + beginSeq: 0x1234, |
| 85 | + endSeq: 0x5678, |
| 86 | + lostPackets: 0x1111_1111, |
| 87 | + dupPackets: 0x2222_2222, |
| 88 | + minJitter: 0x3333_3333, |
| 89 | + maxJitter: 0x4444_4444, |
| 90 | + meanJitter: 0x5555_5555, |
| 91 | + devJitter: 0x6666_6666, |
| 92 | + minTtlOrHl: 0x01, |
| 93 | + maxTtlOrHl: 0x02, |
| 94 | + meanTtlOrHl: 0x03, |
| 95 | + devTtlOrHl: 0x04 |
| 96 | + ), |
| 97 | + VoIPMetricsReportBlock( |
| 98 | + ssrc: 0x89AB_CDEF, |
| 99 | + lossRate: 0x05, |
| 100 | + discardRate: 0x06, |
| 101 | + burstDensity: 0x07, |
| 102 | + gapDensity: 0x08, |
| 103 | + burstDuration: 0x1111, |
| 104 | + gapDuration: 0x2222, |
| 105 | + roundTripDelay: 0x3333, |
| 106 | + endSystemDelay: 0x4444, |
| 107 | + signalLevel: 0x11, |
| 108 | + noiseLevel: 0x22, |
| 109 | + rerl: 0x33, |
| 110 | + gmin: 0x44, |
| 111 | + rfactor: 0x55, |
| 112 | + extRfactor: 0x66, |
| 113 | + mosLq: 0x77, |
| 114 | + mosCq: 0x88, |
| 115 | + rxConfig: 0x99, |
| 116 | + reserved: 0x00, |
| 117 | + jbNominal: 0x1122, |
| 118 | + jbMaximum: 0x3344, |
| 119 | + jbAbsMax: 0x5566 |
| 120 | + ), |
| 121 | + ] |
| 122 | + ) |
| 123 | +} |
| 124 | + |
| 125 | +func encodedPacket() -> ByteBuffer { |
| 126 | + ByteBuffer(bytes: [ |
| 127 | + // RTP Header |
| 128 | + 0x80, 0xCF, 0x00, 0x33, // byte 0 - 3 |
| 129 | + // Sender SSRC |
| 130 | + 0x01, 0x02, 0x03, 0x04, // Loss RLE Report Block |
| 131 | + 0x01, 0x0C, 0x00, 0x04, // byte 8 - 11 |
| 132 | + // Source SSRC |
| 133 | + 0x12, 0x34, 0x56, 0x89, // Begin & End Seq |
| 134 | + 0x00, 0x05, 0x00, 0x0C, // byte 16 - 19 |
| 135 | + // Chunks |
| 136 | + 0x40, 0x06, 0x00, 0x06, 0x87, 0x65, 0x00, 0x00, // byte 24 - 27 |
| 137 | + // Duplicate RLE Report Block |
| 138 | + 0x02, 0x06, 0x00, 0x04, // Source SSRC |
| 139 | + 0x12, 0x34, 0x56, 0x89, // byte 32 - 35 |
| 140 | + // Begin & End Seq |
| 141 | + 0x00, 0x05, 0x00, 0x0C, // Chunks |
| 142 | + 0x41, 0x23, 0x3F, 0xFF, // byte 40 - 43 |
| 143 | + 0xFF, 0xFF, 0x00, 0x00, // Packet Receipt Times Report Block |
| 144 | + 0x03, 0x03, 0x00, 0x07, // byte 48 - 51 |
| 145 | + // Source SSRC |
| 146 | + 0x98, 0x76, 0x54, 0x32, // Begin & End Seq |
| 147 | + 0x3C, 0x48, 0x3C, 0xD9, // byte 56 - 59 |
| 148 | + // Receipt times |
| 149 | + 0x11, 0x11, 0x11, 0x11, 0x22, 0x22, 0x22, 0x22, // byte 64 - 67 |
| 150 | + 0x33, 0x33, 0x33, 0x33, 0x44, 0x44, 0x44, 0x44, // byte 72 - 75 |
| 151 | + 0x55, 0x55, 0x55, 0x55, // Receiver Reference Time Report |
| 152 | + 0x04, 0x00, 0x00, 0x02, // byte 80 - 83 |
| 153 | + // Timestamp |
| 154 | + 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, // byte 88 - 91 |
| 155 | + // DLRR Report |
| 156 | + 0x05, 0x00, 0x00, 0x09, // SSRC 1 |
| 157 | + 0x88, 0x88, 0x88, 0x88, // byte 96 - 99 |
| 158 | + // LastRR 1 |
| 159 | + 0x12, 0x34, 0x56, 0x78, // DLRR 1 |
| 160 | + 0x99, 0x99, 0x99, 0x99, // byte 104 - 107 |
| 161 | + // SSRC 2 |
| 162 | + 0x09, 0x09, 0x09, 0x09, // LastRR 2 |
| 163 | + 0x12, 0x34, 0x56, 0x78, // byte 112 - 115 |
| 164 | + // DLRR 2 |
| 165 | + 0x99, 0x99, 0x99, 0x99, // SSRC 3 |
| 166 | + 0x11, 0x22, 0x33, 0x44, // byte 120 - 123 |
| 167 | + // LastRR 3 |
| 168 | + 0x12, 0x34, 0x56, 0x78, // DLRR 3 |
| 169 | + 0x99, 0x99, 0x99, 0x99, // byte 128 - 131 |
| 170 | + // Statistics Summary Report |
| 171 | + 0x06, 0xE8, 0x00, 0x09, // SSRC |
| 172 | + 0xFE, 0xDC, 0xBA, 0x98, // byte 136 - 139 |
| 173 | + // Various statistics |
| 174 | + 0x12, 0x34, 0x56, 0x78, 0x11, 0x11, 0x11, 0x11, // byte 144 - 147 |
| 175 | + 0x22, 0x22, 0x22, 0x22, 0x33, 0x33, 0x33, 0x33, // byte 152 - 155 |
| 176 | + 0x44, 0x44, 0x44, 0x44, 0x55, 0x55, 0x55, 0x55, // byte 160 - 163 |
| 177 | + 0x66, 0x66, 0x66, 0x66, 0x01, 0x02, 0x03, 0x04, // byte 168 - 171 |
| 178 | + // VoIP Metrics Report |
| 179 | + 0x07, 0x00, 0x00, 0x08, // SSRC |
| 180 | + 0x89, 0xAB, 0xCD, 0xEF, // byte 176 - 179 |
| 181 | + // Various statistics |
| 182 | + 0x05, 0x06, 0x07, 0x08, 0x11, 0x11, 0x22, 0x22, // byte 184 - 187 |
| 183 | + 0x33, 0x33, 0x44, 0x44, 0x11, 0x22, 0x33, 0x44, // byte 192 - 195 |
| 184 | + 0x55, 0x66, 0x77, 0x88, 0x99, 0x00, 0x11, 0x22, // byte 200 - 203 |
| 185 | + 0x33, 0x44, 0x55, 0x66, // byte 204 - 207 |
| 186 | + ]) |
| 187 | +} |
| 188 | + |
| 189 | +final class ExtendedReportTests: XCTestCase { |
| 190 | + func testEncode() throws { |
| 191 | + let expected = encodedPacket() |
| 192 | + let packet = decodedPacket() |
| 193 | + let actual = try packet.marshal() |
| 194 | + XCTAssertEqual(actual, expected) |
| 195 | + } |
| 196 | + |
| 197 | + func testDecode() throws { |
| 198 | + let encoded = encodedPacket() |
| 199 | + let expected = decodedPacket() |
| 200 | + let (actual, _) = try ExtendedReport.unmarshal(encoded) |
| 201 | + XCTAssertTrue(actual.equal(other: expected)) |
| 202 | + XCTAssertEqual(actual.description, expected.description) |
| 203 | + } |
| 204 | +} |
0 commit comments