However, this application schedule the sending at a certain time x but then it actually sends into the socket at a different time. Moreover, it does all the packets it is supposed to.
#include "ns3/core-module.h"
#include "ns3/applications-module.h"
#include "ns3/internet-module.h"
#include "ns3/address.h"
#include "ns3/socket.h"
#include "ns3/tcp-socket-base.h"
#include "ns3/inet-socket-address.h"
#include <utility>
#include "../helper_methods/HelperMethods.h"
#include "FlowParameters.h"
using namespace ns3;
using namespace std;
using namespace helper_methods;
class TcpFlowSender : public Application
{
public:
static TypeId GetTypeId (void);
TcpFlowSender ();
virtual ~TcpFlowSender ();
void Setup (Ptr<Node> node, InetSocketAddress address, const FlowParams& params);
//void Setup (Ptr<Socket> socket, Address address, const FlowParams& params); // Change to take FlowParams as parameter
private:
virtual void StartApplication ();
virtual void StopApplication ();
void SendPacket ();
void ScheduleNextSend();
Ptr<Socket> m_socket;
InetSocketAddress m_peer;
FlowParams m_params; // Store the FlowParams
int m_total = 0;
Time m_lastTime;
};
#include "Tcp_Application_Sender.h"
NS_LOG_COMPONENT_DEFINE ("TcpFlowSender");
NS_OBJECT_ENSURE_REGISTERED (TcpFlowSender);
TypeId TcpFlowSender::GetTypeId (void)
{
static TypeId tid = TypeId ("TcpFlowSender")
.SetParent<Application> ()
.AddConstructor<TcpFlowSender> ()
;
return tid;
}
TcpFlowSender::TcpFlowSender () : m_peer(InetSocketAddress (Ipv4Address::GetAny()))
{
//m_peer = InetSocketAddress (Ipv4Address::GetAny()); // Initialize m_peer with an empty InetSocketAddress object
m_socket = nullptr;
}
TcpFlowSender::~TcpFlowSender ()
{
m_socket = nullptr;
}
//void TcpFlowSender::Setup (Ptr<Socket> socket, Address address, const FlowParams& params)
void TcpFlowSender::Setup (Ptr<Node> node, InetSocketAddress address, const FlowParams& params)
{
//m_socket = socket;
m_peer = address;
m_params = params; // Store the FlowParams
m_socket = Socket::CreateSocket(node, TcpSocketFactory::GetTypeId());
NS_LOG_INFO("Flow Sender socket created");
// Bind to the specified local port
m_socket->SetSendCallback (MakeNullCallback<void, Ptr<Socket>, uint32_t>());
if(m_socket->Bind(InetSocketAddress(Ipv4Address::GetAny(), m_params.sourcePort)) == -1)
{
NS_FATAL_ERROR("Failed to bind socket!");
}
NS_LOG_INFO("Flow Sender socket bound to local port " << m_params.sourcePort);
}
void TcpFlowSender::StartApplication ()
{
m_peer.SetTos(Dscp2Tos(m_params.dscp));
NS_LOG_INFO ("socket Sender connected, with IpTos: " << unsigned(m_socket->GetIpTos()) << " and DSCP on receiver addr: " << unsigned(m_peer.GetTos()));
if(m_socket->Connect(m_peer) == -1)
{
NS_LOG_INFO("Failed to connect socket!");
}
NS_LOG_INFO("Flow Sender socket connected");
NS_LOG_INFO("Flow Sender starting scheduling packets");
// Send the first packet transmission
m_lastTime = Simulator::Now();
SendPacket();
NS_LOG_INFO("Packet sent to host at time " << Simulator::Now ().GetSeconds () << "s");
}
void TcpFlowSender::StopApplication ()
{
m_socket->Close ();
}
void TcpFlowSender::ScheduleNextSend ()
{
//not used
}
void TcpFlowSender::SendPacket ()
{
// Create packet
Ptr<Packet> packet = Create<Packet> (m_params.bytesPerFrame-54);
// Send packet
m_socket->Send (packet);
NS_LOG_INFO("Packet sent to host at time " << Simulator::Now ().GetSeconds () << "s");
// schedule next send
m_lastTime += m_params.timeBetweenFrames;
if(Simulator::Now() > m_params.endTime)
{
m_socket->Close ();
NS_LOG_INFO("Flow Sender finished sending packets, closing socket. " << endl);
}
else
{
Simulator::Schedule (m_lastTime, &TcpFlowSender::SendPacket, this);
NS_LOG_INFO("Packet scheduled for transmission at time " << m_lastTime.GetSeconds());
}
}