From a694ccb39ee9bd4d23368af180d3d3cb273e9f7a Mon Sep 17 00:00:00 2001 From: "Gustavo J. A. M. Carneiro" Date: Wed, 18 Jul 2007 11:43:39 +0100 Subject: [PATCH] WAF: add a --command-template option to e.g. allow running programs with valgrind, gdb, etc. --- doc/build.txt | 9 ++++ src/internet-node/arp-cache.cc | 2 + src/internet-node/arp-ipv4-interface.cc | 15 +++++- src/internet-node/arp-l3-protocol.cc | 22 ++++++++ src/internet-node/ipv4-l3-protocol.cc | 49 ++++++++++++------ src/node/ipv4-address.cc | 12 +++++ src/node/ipv4-address.h | 15 +++++- wscript | 68 ++++++++++++++++++------- 8 files changed, 157 insertions(+), 35 deletions(-) diff --git a/doc/build.txt b/doc/build.txt index 1e2f45cd3..bfb2b518d 100644 --- a/doc/build.txt +++ b/doc/build.txt @@ -60,6 +60,15 @@ with --enable-gcov) before running the program. Note: the "program [args]" string is parsed using POSIX shell rules. + 4.1 waf --run programname --command-template "... %s ..." + + Same as --run, but uses a command template with %s replaced by the + actual program (whose name is given by --run). This can be use to + run ns-3 programs with helper tools. For example, to run unit + tests with valgrind, use the command: + + waf --run run-tests --command-template "valgrind %s" + 5. waf --shell Starts a nested system shell with modified environment to run ns3 programs. diff --git a/src/internet-node/arp-cache.cc b/src/internet-node/arp-cache.cc index e9f48561d..92cb13af4 100644 --- a/src/internet-node/arp-cache.cc +++ b/src/internet-node/arp-cache.cc @@ -109,6 +109,8 @@ ArpCache::Lookup (Ipv4Address to) ArpCache::Entry * ArpCache::Add (Ipv4Address to) { + NS_ASSERT (m_arpCache.find (to) == m_arpCache.end ()); + ArpCache::Entry *entry = new ArpCache::Entry (this); m_arpCache[to] = entry; return entry; diff --git a/src/internet-node/arp-ipv4-interface.cc b/src/internet-node/arp-ipv4-interface.cc index 42d6af238..4ca7ebbb3 100644 --- a/src/internet-node/arp-ipv4-interface.cc +++ b/src/internet-node/arp-ipv4-interface.cc @@ -21,6 +21,7 @@ */ #include "ns3/packet.h" +#include "ns3/debug.h" #include "ns3/composite-trace-resolver.h" #include "ns3/node.h" #include "ns3/net-device.h" @@ -60,7 +61,19 @@ ArpIpv4Interface::SendTo (Packet p, Ipv4Address dest) { Ptr arp = m_node->QueryInterface (ArpPrivate::iid); MacAddress hardwareDestination; - bool found = arp->Lookup (p, dest, GetDevice (), &hardwareDestination); + bool found; + + if (dest.IsBroadcast ()) + { + hardwareDestination = GetDevice ()->GetBroadcast (); + found = true; + } + else + { + Ptr arp = m_node->QueryInterface (ArpPrivate::iid); + found = arp->Lookup (p, dest, GetDevice (), &hardwareDestination); + } + if (found) { GetDevice ()->Send (p, hardwareDestination, Ipv4L3Protocol::PROT_NUMBER); diff --git a/src/internet-node/arp-l3-protocol.cc b/src/internet-node/arp-l3-protocol.cc index f04a6aa25..b68995be3 100644 --- a/src/internet-node/arp-l3-protocol.cc +++ b/src/internet-node/arp-l3-protocol.cc @@ -87,6 +87,13 @@ ArpL3Protocol::Receive(Packet& packet, Ptr device) ArpCache *cache = FindCache (device); ArpHeader arp; packet.RemoveHeader (arp); + + NS_DEBUG ("ARP: received "<< (arp.IsRequest ()? "request" : "reply") << + " node="<GetId ()<<", got request from " << + arp.GetSourceIpv4Address () << " for address " << + arp.GetDestinationIpv4Address () << "; we have address " << + cache->GetInterface ()->GetAddress ()); + if (arp.IsRequest () && arp.GetDestinationIpv4Address () == cache->GetInterface ()->GetAddress ()) { @@ -128,6 +135,12 @@ ArpL3Protocol::Receive(Packet& packet, Ptr device) // XXX report packet as dropped. } } + else + { + NS_DEBUG ("node="<GetId ()<<", got request from " << + arp.GetSourceIpv4Address () << " for unknown address " << + arp.GetDestinationIpv4Address () << " -- drop"); + } } bool ArpL3Protocol::Lookup (Packet &packet, Ipv4Address destination, @@ -203,6 +216,11 @@ void ArpL3Protocol::SendArpRequest (ArpCache const *cache, Ipv4Address to) { ArpHeader arp; + NS_DEBUG ("ARP: sending request from node "<GetId ()<< + " || src: " << cache->GetDevice ()->GetAddress () << + " / " << cache->GetInterface ()->GetAddress () << + " || dst: " << cache->GetDevice ()->GetBroadcast () << + " / " << to); arp.SetRequest (cache->GetDevice ()->GetAddress (), cache->GetInterface ()->GetAddress (), cache->GetDevice ()->GetBroadcast (), @@ -216,6 +234,10 @@ void ArpL3Protocol::SendArpReply (ArpCache const *cache, Ipv4Address toIp, MacAddress toMac) { ArpHeader arp; + NS_DEBUG ("ARP: sending reply from node "<GetId ()<< + "|| src: " << cache->GetDevice ()->GetAddress () << + " / " << cache->GetInterface ()->GetAddress () << + " || dst: " << toMac << " / " << toIp); arp.SetReply (cache->GetDevice ()->GetAddress (), cache->GetInterface ()->GetAddress (), toMac, toIp); diff --git a/src/internet-node/ipv4-l3-protocol.cc b/src/internet-node/ipv4-l3-protocol.cc index 4a46290e6..ff3aef6cf 100644 --- a/src/internet-node/ipv4-l3-protocol.cc +++ b/src/internet-node/ipv4-l3-protocol.cc @@ -404,23 +404,40 @@ Ipv4L3Protocol::Send (Packet const &packet, m_identification ++; - // XXX Note here that in most ipv4 stacks in the world, - // the route calculation for an outgoing packet is not - // done in the ip layer. It is done within the application - // socket when the first packet is sent to avoid this - // costly lookup on a per-packet basis. - // That would require us to get the route from the packet, - // most likely with a packet tag. The higher layers do not - // do this yet for us. - Ipv4Route *route = Lookup (ipHeader.GetDestination ()); - if (route == 0) + if (destination.IsBroadcast ()) { - NS_DEBUG ("not for me -- forwarding but no route to host. drop."); - m_dropTrace (packet); - return; - } + uint32_t ifaceIndex = 0; + for (Ipv4InterfaceList::iterator ifaceIter = m_interfaces.begin (); + ifaceIter != m_interfaces.end (); ifaceIter++, ifaceIndex++) + { + Ipv4Interface *outInterface = *ifaceIter; + Packet packetCopy = packet; - SendRealOut (packet, ipHeader, *route); + NS_ASSERT (packetCopy.GetSize () <= outInterface->GetMtu ()); + packetCopy.AddHeader (ipHeader); + m_txTrace (packetCopy, ifaceIndex); + outInterface->Send (packetCopy, destination); + } + } + else + { + // XXX Note here that in most ipv4 stacks in the world, + // the route calculation for an outgoing packet is not + // done in the ip layer. It is done within the application + // socket when the first packet is sent to avoid this + // costly lookup on a per-packet basis. + // That would require us to get the route from the packet, + // most likely with a packet tag. The higher layers do not + // do this yet for us. + Ipv4Route *route = Lookup (ipHeader.GetDestination ()); + if (route == 0) + { + NS_DEBUG ("not for me -- forwarding but no route to host. drop."); + m_dropTrace (packet); + return; + } + SendRealOut (packet, ipHeader, *route); + } } void @@ -470,7 +487,7 @@ Ipv4L3Protocol::Forwarding (Packet const &packet, Ipv4Header &ipHeader, Ptr