Bug 637

Summary: Tags with UDP cause Assert failure with Virtual-net-devices
Product: ns-3 Reporter: Antti Mäkelä <antti.makela>
Component: routingAssignee: ns-bugs <ns-bugs>
Status: RESOLVED WORKSFORME    
Severity: normal    
Priority: P5    
Version: ns-3-dev   
Hardware: All   
OS: All   

Description Antti Mäkelä 2009-07-13 09:30:35 UTC
If I have a scenario where I have

LAN #1
| 
|
Router
| Virtual-net-device
|
{Cloud}
|
| Virtual-net-device #1
Central Router 
| Virtual-net-device #2
|
{Cloud}
|
| Virtual-net-device
Router
|
|
LAN #2

and have set up routing so that packets from hosts in LAN #1 are sent via the tunnels (Central router has LAN#1 reachable via Virtual-Net-Device #1, LAN #2 via Virtual-Net-Device #2), and then send Udp traffic (Simply using Udp-echo-client and server) from one LAN to other, the simulator fails with

UdpSocketImpl:ForwardUp(0x89bcc58, 0x89ba3b8, 172.22.30.254, 49153)
Packet:AddPacketTag(0x89ba3b8, ns3::SocketAddressTag, 8)
PacketTagList:Add(0x89ba3d8, ns3::SocketAddressTag)
assert failed. file=../src/common/packet-tag-list.cc, line=139, cond="cur->tid != tag.GetInstanceTypeId ()"

when first UDP packet reaches the far-end-router.

It seems that when the inner packet is momentarily popped at the Central Router something weird happens with tags - the test condition is that some tag is already in.

My temporary fix for this was to change the NS_ASSERT to a if () { return; } and so far my simulation is working as expected - maybe some tags were added at the central node and the endpoint is not expecting them to exist. 

I can try cooking up a simpler test script than what I have brewing (should be possible to adapt virtual-net-device example to include a bit of routing so that the central node would simply send stuff back into the tunnel), but this might take a while.
Comment 1 Antti Mäkelä 2009-07-14 08:32:02 UTC
Ok, a more proper fix was to add

  packet->RemoveAllPacketTags ();
  packet->RemoveAllByteTags ();

to the virtual receiving functions. If not added, the "Address from" you get from a socket->RecvFrom() was pointing to the intermediate router as originator, not the original one.

Closing for now.