Files
eden-sim/contrib/tsn/model/frer-sequence-recovery-function.cc

130 lines
4.7 KiB
C++

#include "frer-sequence-recovery-function.h"
#include "ns3/log.h"
#include "ns3/boolean.h"
#include "ns3/random-variable-stream.h"
namespace ns3
{
NS_LOG_COMPONENT_DEFINE("SequenceRecoveryFunction");
NS_OBJECT_ENSURE_REGISTERED(SequenceRecoveryFunction);
TypeId
SequenceRecoveryFunction::GetTypeId()
{
static TypeId tid =
TypeId("ns3::SequenceRecoveryFunction")
.SetParent<Object>()
.SetGroupName("tsn")
.AddConstructor<SequenceRecoveryFunction>()
.AddAttribute("Direction",
"A Boolean indicating whether the Sequence recovery or Individual recovery function is to be placed on the out-facing (True) or in-facing (False) side of the port.",
BooleanValue(false),
MakeBooleanAccessor(&SequenceRecoveryFunction::m_frerSeqRcvyDirection),
MakeBooleanChecker())
.AddAttribute("TakeNoSequence",
"A Boolean specifying whether packets with no sequence_number are to be accepted (True) or not (False).",
BooleanValue(false),
MakeBooleanAccessor(&SequenceRecoveryFunction::m_frerSeqRcvyTakeNoSequence),
MakeBooleanChecker())
.AddAttribute("IndividualRecovery",
"A Boolean specifying whether the function act as Individual recovery function (True) or Sequence recovery function (False)",
BooleanValue(false),
MakeBooleanAccessor(&SequenceRecoveryFunction::m_frerSeqRcvyIndividualRecovery),
MakeBooleanChecker())
.AddAttribute("MinLatencyOverhead",
"The minimum latency overhead cause by the recovery hardware implementation",
TimeValue(Seconds(0)),
MakeTimeAccessor(&SequenceRecoveryFunction::m_minLatencyOverhead),
MakeTimeChecker())
.AddAttribute("MaxLatencyOverhead",
"The maximun latency overhead cause by the recovery hardware implementation",
TimeValue(Seconds(0)),
MakeTimeAccessor(&SequenceRecoveryFunction::m_maxLatencyOverhead),
MakeTimeChecker());
return tid;
}
SequenceRecoveryFunction::SequenceRecoveryFunction()
{
NS_LOG_FUNCTION(this);
}
SequenceRecoveryFunction::~SequenceRecoveryFunction()
{
NS_LOG_FUNCTION(this);
}
void
SequenceRecoveryFunction::SetStreamHandle(std::vector<uint32_t> frerSeqRcvyStreamList)
{
NS_LOG_FUNCTION(this);
m_frerSeqRcvyStreamList = frerSeqRcvyStreamList;
}
void
SequenceRecoveryFunction::SetPorts(std::vector<Ptr<TsnNetDevice>> frerSeqRcvyPortList)
{
NS_LOG_FUNCTION(this);
m_frerSeqRcvyPortList = frerSeqRcvyPortList;
}
void
SequenceRecoveryFunction::SetRecoveryFunction(Ptr<BaseRecoveryFunction> frerSeqRcvyAlgorithm)
{
NS_LOG_FUNCTION(this);
m_frerSeqRcvyAlgorithm = frerSeqRcvyAlgorithm;
}
void
SequenceRecoveryFunction::SetLatentErrorDetectionFunction(Ptr<LatentErrorDetectionFunction> frerSeqRcvyLatentErrorDetection)
{
NS_LOG_FUNCTION(this);
m_frerSeqRcvyLatentErrorDetection = frerSeqRcvyLatentErrorDetection;
}
bool
SequenceRecoveryFunction::IsApplicable(uint32_t streamHandle, Ptr<TsnNetDevice> port, bool direction, bool hasSeqNumber, bool individualRecovery)
{
NS_LOG_FUNCTION(this);
if (std::find(m_frerSeqRcvyStreamList.begin(), m_frerSeqRcvyStreamList.end(), streamHandle) != m_frerSeqRcvyStreamList.end())
{
if (std::find(m_frerSeqRcvyPortList.begin(), m_frerSeqRcvyPortList.end(), port) != m_frerSeqRcvyPortList.end())
{
if (m_frerSeqRcvyDirection == direction && m_frerSeqRcvyIndividualRecovery == individualRecovery)
{
if (!hasSeqNumber && m_frerSeqRcvyTakeNoSequence)
{
return true;
}
if(hasSeqNumber)
{
return true;
}
}
}
}
return false;
}
bool
SequenceRecoveryFunction::Recovery(uint16_t seqNumber)
{
NS_LOG_FUNCTION(this);
NS_ASSERT_MSG(m_frerSeqRcvyAlgorithm!=nullptr, "Recovery function not set ... Can be set using SetRecoveryFunction(Ptr<BaseRecoveryFunction> recoveryFunction)");
return m_frerSeqRcvyAlgorithm->DoRecovery(seqNumber);
}
Time
SequenceRecoveryFunction::GetHardwareLatency()
{
NS_LOG_FUNCTION(this);
Ptr<UniformRandomVariable> randVar = CreateObject<UniformRandomVariable>();
return NanoSeconds(randVar->GetValue(m_minLatencyOverhead.GetNanoSeconds(), m_maxLatencyOverhead.GetNanoSeconds()));
}
}