#include #include #include #include #include #include "ns3/core-module.h" #include "ns3/helper-module.h" #include "ns3/node-module.h" #include "ns3/global-route-manager.h" #include "ns3/simulator-module.h" using namespace ns3; void PrintNetDevInfo(std::ostream &os, Ptr nd) { os << "[" << "addr=<" << nd->GetAddress() << "> " << "bcastP=<" << nd->IsBroadcast() << "> " << "p2pP=<" << nd->IsPointToPoint() << ">]\n"; } void PrintSockInfo(std::ostream &os, String comment, Ptr sock) { return; os << comment << "Start" << std::endl; os << "sock=<" << sock << ">\n"; Ptr n = sock->GetNode(); os << "node=<" << n << ">\n"; int ndev = n->GetNDevices(); os << "ndev=<" << ndev << ">\n"; Ptr nd = n->GetDevice(0); PrintNetDevInfo(os << "node->dev(0)",nd); Ptr chan = nd->GetChannel(); os << "channel=<" << chan << ">\n"; os << "channel.ndev=<" << chan->GetNDevices() << ">\n"; for (int i = 0; i < int(chan->GetNDevices()); i++) PrintNetDevInfo(os << "nd->chan->dev(" << i << ")", chan->GetDevice(i)); os << comment << "End" << std::endl << std::endl ; } class Atag : public Tag { public: Atag(); Atag(uint32_t); static uint32_t GetUid (void); void Print (std::ostream &os) const; uint32_t GetSerializedSize (void) const; void Serialize (Buffer::Iterator) const; uint32_t Deserialize (Buffer::Iterator); uint32_t GetValue(void) const; void SetValue(uint32_t); private: uint32_t value; }; Atag::Atag() { value = 0; } Atag::Atag(uint32_t v_) { value = v_; } uint32_t Atag::GetUid (void) { static uint32_t uid = AllocateUid ("Atag.test"); return uid; } void Atag::SetValue(uint32_t v_) { value = v_; } uint32_t Atag::GetValue(void) const { return value; } void Atag::Print (std::ostream &os) const { os << "(tag=" << value << ")"; } uint32_t Atag::GetSerializedSize (void) const { return sizeof(value); } void Atag::Serialize (Buffer::Iterator i) const { i.WriteU32 (value); } uint32_t Atag::Deserialize (Buffer::Iterator i) { value = i.ReadU32 (); return sizeof(value); } class TalkerApp : public Application { public: TalkerApp(); virtual ~TalkerApp (); void ConfRecv(Ptr, const Address); void ConfSend(Ptr, const Address); protected: virtual void DoDispose (void); private: virtual void StartApplication (void); virtual void StartApplicationRecv (void); virtual void StartApplicationSend (void); virtual void StopApplication (void); virtual void Receive (Ptr socket, Ptr packet, const Address& from); void SendPacket(std::string,int,int); virtual void CloseConnection (Ptr socket); void ConnectionSucceeded(Ptr); void ConnectionFailed(Ptr); void ConnectionHalfClosed(Ptr); bool ConnectionRequested(Ptr, const Address &); void ConnectionCreated(Ptr, const Address &); void ConnectionCloseRequested(Ptr); Ptr m_socket; Ptr m_servsocket; Address m_local; Address m_remote; int i_am_listener; int recv_cnt; }; TalkerApp::TalkerApp () { m_socket = 0; m_servsocket = 0; recv_cnt = 0; } TalkerApp::~TalkerApp() {} void TalkerApp::DoDispose (void) { m_socket = 0; m_servsocket = 0; Application::DoDispose (); } void TalkerApp::ConnectionSucceeded(Ptr sock) { std::cout << "TalkerApp::ConnectionSucceeded(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionSucceeded"),sock); } void TalkerApp::ConnectionFailed(Ptr sock) { std::cout << "TalkerApp::ConnectionFailed(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionFailed"),sock); } void TalkerApp::ConnectionHalfClosed(Ptr sock) { std::cout << "TalkerApp::ConnectionHalfClosed(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionHalfClosed"),sock); } bool TalkerApp::ConnectionRequested(Ptr sock, const Address &addr) { std::cout << "TalkerApp::ConnectionRequested(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionRequested"),sock); return(1); } void TalkerApp::ConnectionCreated(Ptr sock, const Address &addr) { std::cout << "TalkerApp::ConnectionCreated(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionCreated"),sock); m_socket = sock; m_socket->SetRecvCallback (MakeCallback(&TalkerApp::Receive, this)); } void TalkerApp::ConnectionCloseRequested(Ptr sock) { std::cout << "TalkerApp::ConnectionCloseRequested(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::ConnectionCloseRequested"),sock); } void TalkerApp::StartApplication() { std::cout << "TalkerApp::StartApplication() " << (i_am_listener ? "Server" : "Client") << std::endl; if (i_am_listener) StartApplicationRecv(); else StartApplicationSend(); } void TalkerApp::ConfRecv(Ptr node, const Address addr) { i_am_listener = 1; std::cout << "TalkerApp::ConfRecv(" << node << "," << addr << ") " << (i_am_listener ? "Server" : "Client") << std::endl; m_local = addr; node->AddApplication(this); } void TalkerApp::StartApplicationRecv() { std::cout << "TalkerApp::StartApplicationRecv() " << (i_am_listener ? "Server" : "Client") << std::endl; if (!m_servsocket) { Ptr socketFactory = GetNode ()->GetObject (TypeId::LookupByName ("ns3::Tcp")); m_servsocket = socketFactory->CreateSocket (); m_servsocket->Bind (m_local); m_servsocket->Listen (0); } m_servsocket->SetAcceptCallback ( MakeCallback(&TalkerApp::ConnectionRequested,this), MakeCallback(&TalkerApp::ConnectionCreated,this), MakeCallback(&TalkerApp::ConnectionCloseRequested,this) ); } void TalkerApp::ConfSend(Ptr node, const Address addr) { i_am_listener = 0; std::cout << "TalkerApp::ConfSend(" << node << "," << addr << ") " << (i_am_listener ? "Server" : "Client") << std::endl; m_remote = addr; node->AddApplication(this); } void TalkerApp::StartApplicationSend() { std::cout << "TalkerApp::StartApplicationSend() " << (i_am_listener ? "Server" : "Client") << std::endl; if (!m_socket) { Ptr socketFactory = GetNode ()->GetObject (TypeId::LookupByName ("ns3::Tcp")); m_socket = socketFactory->CreateSocket (); m_socket->Bind (); } m_socket->Connect (m_remote); m_socket->SetConnectCallback ( MakeCallback(&TalkerApp::ConnectionSucceeded,this), MakeCallback(&TalkerApp::ConnectionFailed,this), MakeCallback(&TalkerApp::ConnectionHalfClosed,this) ); m_socket->SetRecvCallback (MakeCallback(&TalkerApp::Receive, this)); SendPacket(std::string("Hello"),'S',100); // mtu 537 } void TalkerApp::SendPacket(std::string label,int fill,int size) { #if USEPACKET Ptr mypac = Create(536); // mtu 537 mypac->AddTag(Atag(17)); PrintSockInfo(std::cout, String("TalkerApp::SendPacket"),m_socket); std::cout << "writing packet " << (i_am_listener ? "Server" : "Client") << std::endl; mypac->Print(std::cout << " "); mypac->PrintTags(std::cout); m_socket->Send (mypac); std::cout << std::endl; #else uint8_t *mybuf = (uint8_t *) malloc(size*sizeof(uint8_t)); char *mybufc = (char *)mybuf; memset(mybuf,fill,size); std::cout << "writing buffer " << "(" << label << ") " << (i_am_listener ? "Server" : "Client") << std::endl; snprintf(mybufc,size,"%s",label.c_str()); m_socket->Send (mybuf, size); #endif } void TalkerApp::StopApplication() { if (m_socket) { m_socket->SetRecvCallback (MakeNullCallback, Ptr, const Address &> ()); } } void TalkerApp::Receive(Ptr socket, Ptr packet, const Address &from) { if (InetSocketAddress::IsMatchingType (from)) { InetSocketAddress address = InetSocketAddress::ConvertFrom (from); PrintSockInfo(std::cout, String("TalkerApp::Receive"),m_socket); std::cout << "Received " << packet->GetSize() << " bytes from " << address.GetIpv4() << " [" << address << "]---'" << packet->PeekData() << "'" << std::endl; packet->Print(std::cout << " "); packet->PrintTags(std::cout); std::cout << std::endl; if (i_am_listener && recv_cnt++ == 0) { SendPacket(std::string("HelloBack"),'R',119529); // 119528 works. } } else { std::cout << "TalkerApp::Receive(): not matching." << std::endl; } } void TalkerApp::CloseConnection (Ptr socket) { std::cout << "TalkerApp::CloseConnection(): " << (i_am_listener ? "Server" : "Client") << std::endl; PrintSockInfo(std::cout, String("TalkerApp::CloseConnection"),socket); socket->Close (); } int main (int argc, char *argv[]) { RandomVariable::UseGlobalSeed (1, 1, 2, 3, 5, 8); Packet::EnableMetadata(); NodeContainer c0; c0.Create (2); // We create the channels first without any IP addressing information PointToPointHelper p2p; p2p.SetChannelParameter ("BitRate", DataRate(10000000)); p2p.SetChannelParameter ("Delay", MilliSeconds(10)); NetDeviceContainer dev0 = p2p.Install (c0); // add ip/tcp stack to nodes. InternetStackHelper internet; internet.Install (c0); // Later, we add IP addresses. Ipv4AddressHelper ipv4; ipv4.SetBase ("10.1.0.0", "255.255.255.0"); Ipv4InterfaceContainer ifaces = ipv4.Assign (dev0); // Configure the apps. uint16_t servPort = 32; TalkerApp source; source.ConfSend(c0.Get(0), InetSocketAddress (ifaces.GetAddress (1), servPort)); source.Start(Seconds(0.0)); TalkerApp sink; sink.ConfRecv(c0.Get(1), InetSocketAddress (Ipv4Address::GetAny(), servPort) ); sink.Start (Seconds (0.0)); #if 0 std::ofstream ascii; ascii.open ("tcp-tester.tr"); PointToPointHelper::EnableAscii (ascii); InternetStackHelper::EnablePcap ("tcp-tester"); #endif Simulator::StopAt (Seconds(10)); Simulator::Run (); Simulator::Destroy (); }