5G-LENA nr-v4.0
The 5G/NR module for the ns-3 simulator
Loading...
Searching...
No Matches
traffic-generator-3gpp-generic-video.cc
1// Copyright (c) 2022 CTTC
2// Copyright (c) 2023 Centre Tecnologic de Telecomunicacions de Catalunya (CTTC)
3//
4// SPDX-License-Identifier: GPL-2.0-only
5
6#include "traffic-generator-3gpp-generic-video.h"
7
8#include "ns3/double.h"
9#include "ns3/enum.h"
10#include "ns3/inet-socket-address.h"
11#include "ns3/log.h"
12#include "ns3/nstime.h"
13#include "ns3/simulator.h"
14#include "ns3/tcp-socket-factory.h"
15#include "ns3/trace-source-accessor.h"
16#include "ns3/uinteger.h"
17
18namespace ns3
19{
20
21NS_LOG_COMPONENT_DEFINE("TrafficGenerator3gppGenericVideo");
22NS_OBJECT_ENSURE_REGISTERED(TrafficGenerator3gppGenericVideo);
23
24TypeId
26{
27 static TypeId tid =
28 TypeId("ns3::TrafficGenerator3gppGenericVideo")
29 .SetParent<TrafficGenerator>()
30 .SetGroupName("Applications")
31 .AddConstructor<TrafficGenerator3gppGenericVideo>()
32 .AddAttribute("DataRate",
33 "The desired data rate in Mbps.",
34 DoubleValue(5),
35 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_dataRate),
36 MakeDoubleChecker<double>())
37 .AddAttribute("MinDataRate",
38 "The minimum desired data rate in Mbps.",
39 DoubleValue(0.1),
40 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_minDataRate),
41 MakeDoubleChecker<double>())
42 .AddAttribute("MaxDataRate",
43 "The maximum desired data rate in Mbps.",
44 DoubleValue(10),
45 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_maxDataRate),
46 MakeDoubleChecker<double>())
47 .AddAttribute(
48 "LowerThresholdForDecreasingSlowly",
49 "The lower packet loss bound for decreasing the video traffic slowly.",
50 DoubleValue(0.10),
51 MakeDoubleAccessor(
52 &TrafficGenerator3gppGenericVideo::m_lowerThresholdForDecreasingSlowly),
53 MakeDoubleChecker<double>())
54 .AddAttribute(
55 "LowerThresholdForDecreasingQuickly",
56 "The lower packet loss bound for decreasing the video traffic quickly.",
57 DoubleValue(1),
58 MakeDoubleAccessor(
59 &TrafficGenerator3gppGenericVideo::m_lowerThresholdForDecreasingQuickly),
60 MakeDoubleChecker<double>())
61 .AddAttribute("UpperThresholdForIncreasing",
62 "The upper packet loss bound for increasing the video traffic.",
63 DoubleValue(0.02),
64 MakeDoubleAccessor(
65 &TrafficGenerator3gppGenericVideo::m_upperThresholdForIncreasing),
66 MakeDoubleChecker<double>())
67 .AddAttribute(
68 "IncreaseDataRateMultiplier",
69 "The multiplier when increasing the video traffic volume, e.g., 3 to increase 3 "
70 "times. Used to decrease fps or data rate.",
71 DoubleValue(1.1),
72 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_increaseDataRateMultiplier),
73 MakeDoubleChecker<double>())
74 .AddAttribute(
75 "DecreaseDataRateSlowlyMultiplier",
76 "The multiplier when decreasing the video traffic volume slowly, e.g, 0.75, to "
77 "decrease 25%. Used to decrease fps or data rate.",
78 DoubleValue(0.5),
79 MakeDoubleAccessor(
80 &TrafficGenerator3gppGenericVideo::m_decreaseDataRateSlowlyMultiplier),
81 MakeDoubleChecker<double>())
82 .AddAttribute(
83 "DecreaseDataRateQuicklyMultiplier",
84 "The multiplier when decreasing the video traffic volume quickly, e.g. 0.2 to "
85 "decrease 5 times. Used to decrease fps or data rate.",
86 DoubleValue(0.5),
87 MakeDoubleAccessor(
88 &TrafficGenerator3gppGenericVideo::m_decreaseDataRateQuicklyMultiplier),
89 MakeDoubleChecker<double>())
90 .AddAttribute("Fps",
91 "Frame generation rate (per second). E.g. typical value cold be 60fps.",
92 UintegerValue(60),
93 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_fps),
94 MakeUintegerChecker<uint32_t>())
95 .AddAttribute("MinFps",
96 "The minimum frame generation rate (per second). ",
97 UintegerValue(10),
98 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_minFps),
99 MakeUintegerChecker<uint32_t>())
100 .AddAttribute("MaxFps",
101 "The maximum frame generation rate (per second). ",
102 UintegerValue(240),
103 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_maxFps),
104 MakeUintegerChecker<uint32_t>())
105 .AddAttribute(
106 "StdRatioPacketSize",
107 "STD ratio wrt the mean packet size. "
108 "See Table 5.1.1.1-1 of 3GPP TR 38.838 V17.0.0 (2021-12)."
109 "Typical values are 10.5% and 3%.",
110 DoubleValue(0.105),
111 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_stdRatioPacketSize),
112 MakeDoubleChecker<double>(0, 1))
113 .AddAttribute(
114 "MinRatioPacketSize",
115 "Min ratio wrt the mean packet size. "
116 "See Table 5.1.1.1-1 of 3GPP TR 38.838 V17.0.0 (2021-12)."
117 "Typical values are 50% and 91%.",
118 DoubleValue(0.5),
119 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_minRatioPacketSize),
120 MakeDoubleChecker<double>(0, 1))
121 .AddAttribute(
122 "MaxRatioPacketSize",
123 "Max ratio wrt the mean packet size. "
124 "See Table 5.1.1.1-1 of 3GPP TR 38.838 V17.0.0 (2021-12)."
125 "Typical values are 150% and 109%.",
126 DoubleValue(1.5),
127 MakeDoubleAccessor(&TrafficGenerator3gppGenericVideo::m_maxRatioPacketSize),
128 MakeDoubleChecker<double>(1, 2))
129 .AddAttribute("MeanPacketArrivalJitter",
130 "The mean of packet arrival jitter in milliseconds.",
131 UintegerValue(0),
132 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_meanJitter),
133 MakeUintegerChecker<uint32_t>())
134 .AddAttribute("StdPacketArrivalJitter",
135 "The STD of packet arrival jitter in milliseconds.",
136 UintegerValue(2),
137 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_stdJitter),
138 MakeUintegerChecker<uint32_t>())
139 .AddAttribute("BoundJitter",
140 "The periodicity in milliseconds.",
141 UintegerValue(2),
142 MakeUintegerAccessor(&TrafficGenerator3gppGenericVideo::m_boundJitter),
143 MakeUintegerChecker<uint32_t>())
144 .AddAttribute("Remote",
145 "The address of the destination",
146 AddressValue(),
147 MakeAddressAccessor(&TrafficGenerator::SetRemote),
148 MakeAddressChecker())
149 .AddAttribute("Protocol",
150 "The type of protocol to use.",
151 TypeIdValue(TcpSocketFactory::GetTypeId()),
152 MakeTypeIdAccessor(&TrafficGenerator::SetProtocol),
153 MakeTypeIdChecker())
154 .AddAttribute(
155 "AlgType",
156 "Type of the algorithm for the codec adaptation",
157 EnumValue(LoopbackAlgType::ADJUST_IPA_TIME),
158 MakeEnumAccessor<LoopbackAlgType>(
160 &TrafficGenerator3gppGenericVideo::GetLoopbackAlgType),
161 MakeEnumChecker(TrafficGenerator3gppGenericVideo::ADJUST_IPA_TIME,
162 "AIPAT",
163 TrafficGenerator3gppGenericVideo::ADJUST_PACKET_SIZE,
164 "APS",
165 TrafficGenerator3gppGenericVideo::ADJUST_FPS,
166 "AFPS",
167 TrafficGenerator3gppGenericVideo::WO,
168 "WO",
169 TrafficGenerator3gppGenericVideo::ADJUST_PACKET_SIZE_UP_AGG,
170 "APS_UPAGG"))
171 .AddTraceSource("Tx",
172 "A new packet is created and is sent",
173 MakeTraceSourceAccessor(&TrafficGenerator::m_txTrace),
174 "ns3::TrafficGenerator::TxTracedCallback")
175 .AddTraceSource(
176 "Params",
177 "Traffic parameters have been updated accordingly "
178 "the loopback algorithm, and notified through this trace.",
179 MakeTraceSourceAccessor(&TrafficGenerator3gppGenericVideo::m_paramsTrace),
180 "ns3::TrafficGenerator3gppGenericVideo::ParamsTracedCallback");
181 return tid;
182}
183
185TrafficGenerator3gppGenericVideo::GetLoopbackAlgType() const
186{
187 return m_loopbackAlgType;
188}
189
190void
192{
193 m_loopbackAlgType = loopbackAlgType;
194}
195
196TrafficGenerator3gppGenericVideo::TrafficGenerator3gppGenericVideo()
198{
199 NS_LOG_FUNCTION(this);
200}
201
202TrafficGenerator3gppGenericVideo::~TrafficGenerator3gppGenericVideo()
203{
204 NS_LOG_FUNCTION(this);
205}
206
207void
208TrafficGenerator3gppGenericVideo::StartApplication()
209{
210 NS_LOG_FUNCTION(this);
211 // add the initial values to the trace
212
213 InetSocketAddress address = InetSocketAddress::ConvertFrom(GetPeer());
214 m_port = address.GetPort();
215
216 m_paramsTrace(Simulator::Now(),
217 m_port,
218 m_dataRate,
219 m_fps,
220 m_meanPacketSize,
221 0.0,
222 Seconds(0),
223 Seconds(0));
225}
226
227void
228TrafficGenerator3gppGenericVideo::PacketBurstSent()
229{
230 NS_LOG_FUNCTION(this);
231 // in 3GPP description of the Option 2 (video + audio/data) there is no notion of frames or
232 // packet bursts, just packets
233 NS_ABORT_MSG("This function should not be called for the video + audio/data traffic");
234}
235
236void
237TrafficGenerator3gppGenericVideo::GenerateNextPacketBurstSize()
238{
239 NS_LOG_FUNCTION(this);
240 SetPacketBurstSizeInPackets(1);
241}
242
243Time
244TrafficGenerator3gppGenericVideo::GetNextPacketTime() const
245{
246 NS_LOG_FUNCTION(this);
247 double packetJitter = 0;
248 while (true)
249 {
250 packetJitter = m_packetJitter->GetValue();
251 if (packetJitter <= m_boundJitter && packetJitter > -m_boundJitter)
252 {
253 break;
254 }
255 else
256 {
257 NS_LOG_DEBUG("Generated packet jitter is out of configured bounds. Generated value:"
258 << packetJitter);
259 }
260 }
261
262 double packetTimeMs = (1e3 * 1 / (double)m_fps) + packetJitter;
263 NS_ASSERT(packetTimeMs);
264 NS_LOG_DEBUG("Next packet time in Milliseconds: " << packetTimeMs);
265 return Seconds(1e-3 * packetTimeMs);
266}
267
268uint32_t
269TrafficGenerator3gppGenericVideo::GetNextPacketSize() const
270{
271 NS_LOG_FUNCTION(this);
272 uint32_t packetSize = 0;
273 while (true)
274 {
275 packetSize = m_packetSize->GetValue();
276 if (packetSize <= m_maxRatioPacketSize * m_meanPacketSize &&
277 packetSize > m_minRatioPacketSize * m_meanPacketSize)
278 {
279 break;
280 }
281 else
282 {
283 NS_LOG_DEBUG("Generated packet size is out of configured bounbds. Generated value:"
284 << packetSize);
285 }
286 }
287 return packetSize;
288}
289
290void
291TrafficGenerator3gppGenericVideo::DoInitialize()
292{
293 NS_LOG_FUNCTION(this);
294 m_meanPacketSize = (m_dataRate * 1e6) / (m_fps) / 8;
295 /* double max = m_maxRatio * mean;
296 double min = m_minRatio * mean;*/
297 m_packetSize = CreateObject<NormalRandomVariable>();
298 m_packetSize->SetAttribute("Mean", DoubleValue(m_meanPacketSize));
299 m_packetSize->SetAttribute("Variance", DoubleValue(m_stdRatioPacketSize * m_meanPacketSize));
300
301 m_packetJitter = CreateObject<NormalRandomVariable>();
302 m_packetJitter->SetAttribute("Mean", DoubleValue(m_meanJitter));
303 m_packetJitter->SetAttribute("Variance", DoubleValue(m_stdJitter));
304 m_packetJitter->SetAttribute("Bound", DoubleValue(m_boundJitter));
305 // chain up
306 TrafficGenerator::DoInitialize();
307}
308
309void
310TrafficGenerator3gppGenericVideo::ReceiveLoopbackInformation(double packetLoss,
311 uint32_t packetReceived,
312 double windowInSeconds,
313 Time packetDelay,
314 Time packetDelayJitter)
315{
316 NS_LOG_FUNCTION(this);
317
318 if (!m_stopEvent.IsPending())
319 {
320 NS_LOG_WARN("The application stopped working ignore this function call...");
321 return;
322 }
323
324 if (Simulator::Now() - m_startTime < Seconds(windowInSeconds))
325 {
326 return;
327 }
328
329 double tempDataRate = m_dataRate;
330 uint32_t tempFps = m_fps;
331 double tempMeanPacketSize = m_meanPacketSize;
332
333 // TX in the last window
334 double txPacketLossEstimation =
335 std::max(0.0, std::min(1.0, 1 - ((double)packetReceived / (m_fps * windowInSeconds))));
336
337 NS_LOG_INFO("Packets received:" << packetReceived
338 << ", packets expected: " << m_fps * windowInSeconds
339 << ", packet loss estimation:" << txPacketLossEstimation);
340
341 // TODO change later how we decide which packet loss we use in the algorithm
342 // the one that is reported by the XrLoopback, or this one calculated by
343 // the traffic generator
344 packetLoss = txPacketLossEstimation;
345
346 if (m_loopbackAlgType == ADJUST_IPA_TIME)
347 {
348 if (packetLoss > m_lowerThresholdForDecreasingSlowly)
349 {
350 // update data rate
351 m_dataRate = std::max(m_dataRate * m_decreaseDataRateSlowlyMultiplier, m_minDataRate);
352 m_fps = std::max(m_fps * m_decreaseDataRateSlowlyMultiplier, m_minFps);
353 }
354 else if (packetLoss < m_upperThresholdForIncreasing)
355 {
356 m_dataRate = std::min(m_dataRate * m_increaseDataRateMultiplier, m_maxDataRate);
357 m_fps = std::min(m_fps * m_increaseDataRateMultiplier, m_maxFps);
358 }
359 else
360 {
361 NS_LOG_INFO("Packet loss is in an accepted range to not change anything");
362 }
363 }
364 else if (m_loopbackAlgType == ADJUST_PACKET_SIZE)
365 {
366 if (packetLoss > m_lowerThresholdForDecreasingSlowly &&
367 packetLoss < m_lowerThresholdForDecreasingQuickly)
368 {
369 // decrease data rate "slowly"
370 m_dataRate = std::max(m_dataRate * m_decreaseDataRateSlowlyMultiplier, m_minDataRate);
371 }
372 else if (packetLoss >= m_lowerThresholdForDecreasingQuickly)
373 {
374 // update data rate
375 m_dataRate = std::max(m_dataRate * m_decreaseDataRateQuicklyMultiplier, m_minDataRate);
376 }
377 else if (packetLoss < m_upperThresholdForIncreasing)
378 {
379 // update data rate
380 m_dataRate = std::min(m_dataRate * m_increaseDataRateMultiplier, m_maxDataRate);
381 }
382 else
383 {
384 NS_LOG_INFO("Packet loss is in an acceptable range to not change anything");
385 }
386 }
387 else if (m_loopbackAlgType == ADJUST_PACKET_SIZE_UP_AGG)
388 {
389 if (packetLoss > m_lowerThresholdForDecreasingSlowly &&
390 packetLoss < m_lowerThresholdForDecreasingQuickly)
391 {
392 // decrease data rate "slowly"
393 m_dataRate = std::max(m_dataRate * m_decreaseDataRateSlowlyMultiplier, m_minDataRate);
394 }
395 else if (packetLoss >= m_lowerThresholdForDecreasingQuickly)
396 {
397 // update data rate
398 m_dataRate = std::max(m_dataRate * m_decreaseDataRateQuicklyMultiplier, m_minDataRate);
399 }
400 else if (packetLoss < m_upperThresholdForIncreasing)
401 {
402 // update data rate
403 m_dataRate = std::min(m_dataRate * 1.5, m_maxDataRate);
404 }
405 else
406 {
407 NS_LOG_INFO("Packet loss is in an acceptable range to not change anything");
408 }
409 }
410 else if (m_loopbackAlgType == ADJUST_FPS)
411 {
412 if (packetLoss > m_lowerThresholdForDecreasingSlowly)
413 {
414 // update data rate
415 m_fps = std::max(m_fps * m_decreaseDataRateSlowlyMultiplier, m_minFps);
416 }
417 else if (packetLoss < m_upperThresholdForIncreasing)
418 {
419 m_fps = std::min(m_fps * m_increaseDataRateMultiplier, m_maxFps);
420 }
421 else
422 {
423 NS_LOG_INFO("Packet loss is in an accepted range to not change anything");
424 }
425 }
426
427 /*
428 if (packetLoss > 0 && packetLoss < 0.1)
429 {
430 // update data rate
431 m_dataRate *= 1.1;
432 }
433 else if (packetLoss > 0.5 && packetLoss < 1)
434 {
435 m_dataRate = std::max (m_dataRate/2 ,m_minDataRate);
436 }
437 else if (packetLoss == 1)
438 {
439 m_dataRate = std::max (m_dataRate/2 ,m_minDataRate);
440 m_fps = std::min (m_fps * 2, m_maxFps);
441 }
442 else
443 {
444 NS_LOG_INFO ("Packet loss is in an accepted range to not change anything");
445 }
446 */
447 // update mean packet size
448 m_meanPacketSize = (m_dataRate * 1e6) / (m_fps) / 8;
449 // update packet size random generator parameters
450 m_packetSize->SetAttribute("Mean", DoubleValue(m_meanPacketSize));
451 m_packetSize->SetAttribute("Variance", DoubleValue(m_stdRatioPacketSize * m_meanPacketSize));
452
453 m_paramsTrace(Simulator::Now(),
454 m_port,
455 m_dataRate,
456 m_fps,
457 m_meanPacketSize,
458 packetLoss,
459 packetDelay,
460 packetDelayJitter);
461
462 if (tempDataRate != m_dataRate || tempFps != m_fps || tempMeanPacketSize != m_meanPacketSize)
463 {
464 // m_paramsTrace (Simulator::Now (), GetTgId (), m_dataRate, m_fps, m_meanPacketSize);
465 NS_LOG_DEBUG("Old data rate: " << tempDataRate << " new data rate: " << m_dataRate);
466 NS_LOG_DEBUG("Old fps: " << tempFps << " new fps: " << m_fps);
467 NS_LOG_DEBUG("Old mean packet size: "
468 << tempMeanPacketSize << " new mean packet size: " << m_meanPacketSize);
469 }
470}
471
472int64_t
474{
475 m_packetSize->SetStream(stream);
476 m_packetJitter->SetStream(stream + 1);
477 return 2;
478}
479
480} // Namespace ns3
void SetLoopbackAlgType(LoopbackAlgType loopbackAlgType)
Set loopback algorithm type.
void SetRemote(Address remote)
Sets the remote address.
bool SendPacketBurst()
Send another packet burst, which can be e.g., a file, or a video frame.
void SetProtocol(TypeId protocol)
Sets the protocol.