A Discrete-Event Network Simulator
API
ipv6-l3-protocol.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2007-2009 Strasbourg University
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * Author: Sebastien Vincent <vincent@clarinet.u-strasbg.fr>
19  */
20 
21 #include "ns3/log.h"
22 #include "ns3/node.h"
23 #include "ns3/uinteger.h"
24 #include "ns3/vector.h"
25 #include "ns3/boolean.h"
26 #include "ns3/callback.h"
27 #include "ns3/trace-source-accessor.h"
28 #include "ns3/object-vector.h"
29 #include "ns3/ipv6-routing-protocol.h"
30 #include "ns3/ipv6-route.h"
31 #include "ns3/mac16-address.h"
32 #include "ns3/mac64-address.h"
33 #include "ns3/traffic-control-layer.h"
34 
35 #include "loopback-net-device.h"
36 #include "ipv6-l3-protocol.h"
37 #include "ipv6-interface.h"
38 #include "ipv6-raw-socket-impl.h"
40 #include "ipv6-extension-demux.h"
41 #include "ipv6-extension.h"
42 #include "ipv6-extension-header.h"
43 #include "ipv6-option-demux.h"
44 #include "ipv6-option.h"
45 #include "icmpv6-l4-protocol.h"
46 #include "ndisc-cache.h"
47 
49 #define IPV6_MIN_MTU 1280
50 
51 namespace ns3 {
52 
53 NS_LOG_COMPONENT_DEFINE ("Ipv6L3Protocol");
54 
55 NS_OBJECT_ENSURE_REGISTERED (Ipv6L3Protocol);
56 
57 const uint16_t Ipv6L3Protocol::PROT_NUMBER = 0x86DD;
58 
60 {
61  static TypeId tid = TypeId ("ns3::Ipv6L3Protocol")
62  .SetParent<Ipv6> ()
63  .SetGroupName ("Internet")
64  .AddConstructor<Ipv6L3Protocol> ()
65  .AddAttribute ("DefaultTtl",
66  "The TTL value set by default on all "
67  "outgoing packets generated on this node.",
68  UintegerValue (64),
70  MakeUintegerChecker<uint8_t> ())
71  .AddAttribute ("DefaultTclass",
72  "The TCLASS value set by default on all "
73  "outgoing packets generated on this node.",
74  UintegerValue (0),
76  MakeUintegerChecker<uint8_t> ())
77  .AddAttribute ("InterfaceList",
78  "The set of IPv6 interfaces associated to this IPv6 stack.",
81  MakeObjectVectorChecker<Ipv6Interface> ())
82  .AddAttribute ("SendIcmpv6Redirect",
83  "Send the ICMPv6 Redirect when appropriate.",
84  BooleanValue (true),
88  .AddAttribute ("StrongEndSystemModel",
89  "Reject packets for an address not configured on the interface they're coming from (RFC1222).",
90  BooleanValue (true),
93  .AddTraceSource ("Tx",
94  "Send IPv6 packet to outgoing interface.",
96  "ns3::Ipv6L3Protocol::TxRxTracedCallback")
97  .AddTraceSource ("Rx",
98  "Receive IPv6 packet from incoming interface.",
100  "ns3::Ipv6L3Protocol::TxRxTracedCallback")
101  .AddTraceSource ("Drop",
102  "Drop IPv6 packet",
104  "ns3::Ipv6L3Protocol::DropTracedCallback")
105 
106  .AddTraceSource ("SendOutgoing",
107  "A newly-generated packet by this node is "
108  "about to be queued for transmission",
110  "ns3::Ipv6L3Protocol::SentTracedCallback")
111  .AddTraceSource ("UnicastForward",
112  "A unicast IPv6 packet was received by this node "
113  "and is being forwarded to another node",
115  "ns3::Ipv6L3Protocol::SentTracedCallback")
116  .AddTraceSource ("LocalDeliver",
117  "An IPv6 packet was received by/for this node, "
118  "and it is being forward up the stack",
120  "ns3::Ipv6L3Protocol::SentTracedCallback")
121  ;
122  return tid;
123 }
124 
126  : m_nInterfaces (0)
127 {
129  m_pmtuCache = CreateObject<Ipv6PmtuCache> ();
130 }
131 
133 {
135 }
136 
138 {
140 
141  /* clear protocol and interface list */
142  for (L4List_t::iterator it = m_protocols.begin (); it != m_protocols.end (); ++it)
143  {
144  it->second = 0;
145  }
146  m_protocols.clear ();
147 
148  /* remove interfaces */
149  for (Ipv6InterfaceList::iterator it = m_interfaces.begin (); it != m_interfaces.end (); ++it)
150  {
151  *it = 0;
152  }
153  m_interfaces.clear ();
155 
156  /* remove raw sockets */
157  for (SocketList::iterator it = m_sockets.begin (); it != m_sockets.end (); ++it)
158  {
159  *it = 0;
160  }
161  m_sockets.clear ();
162 
163  /* remove list of prefix */
164  for (Ipv6AutoconfiguredPrefixListI it = m_prefixes.begin (); it != m_prefixes.end (); ++it)
165  {
166  (*it)->StopValidTimer ();
167  (*it)->StopPreferredTimer ();
168  (*it) = 0;
169  }
170  m_prefixes.clear ();
171 
172  m_node = 0;
173  m_routingProtocol = 0;
174  m_pmtuCache = 0;
176 }
177 
179 {
180  NS_LOG_FUNCTION (this << routingProtocol);
181  m_routingProtocol = routingProtocol;
182  m_routingProtocol->SetIpv6 (this);
183 }
184 
186 {
188  return m_routingProtocol;
189 }
190 
192 {
193  NS_LOG_FUNCTION (this << device);
195 
197 
198  NS_ASSERT (tc != 0);
199 
202 
203  tc->RegisterProtocolHandler (MakeCallback (&Ipv6L3Protocol::Receive, this),
205 
206  interface->SetNode (m_node);
207  interface->SetDevice (device);
208  interface->SetTrafficControl (tc);
209  interface->SetForwarding (m_ipForward);
210  return AddIpv6Interface (interface);
211 }
212 
214 {
215  NS_LOG_FUNCTION (this << interface);
216  uint32_t index = m_nInterfaces;
217 
218  m_interfaces.push_back (interface);
219  m_reverseInterfacesContainer[interface->GetDevice ()] = index;
220  m_nInterfaces++;
221  return index;
222 }
223 
225 {
226  NS_LOG_FUNCTION (this << index);
227 
228  if (index < m_interfaces.size ())
229  {
230  return m_interfaces[index];
231  }
232  return 0;
233 }
234 
236 {
238  return m_nInterfaces;
239 }
240 
242 {
243  NS_LOG_FUNCTION (this << address);
244  int32_t index = 0;
245 
246  for (Ipv6InterfaceList::const_iterator it = m_interfaces.begin (); it != m_interfaces.end (); it++)
247  {
248  uint32_t j = 0;
249  uint32_t max = (*it)->GetNAddresses ();
250 
251  for (j = 0; j < max; j++)
252  {
253  if ((*it)->GetAddress (j).GetAddress () == address)
254  {
255  return index;
256  }
257  }
258  index++;
259  }
260  return -1;
261 }
262 
264 {
265  NS_LOG_FUNCTION (this << address << mask);
266  int32_t index = 0;
267 
268  for (Ipv6InterfaceList::const_iterator it = m_interfaces.begin (); it != m_interfaces.end (); it++)
269  {
270  uint32_t j = 0;
271  for (j = 0; j < (*it)->GetNAddresses (); j++)
272  {
273  if ((*it)->GetAddress (j).GetAddress ().CombinePrefix (mask) == address.CombinePrefix (mask))
274  {
275  return index;
276  }
277  }
278  index++;
279  }
280  return -1;
281 }
282 
284 {
285  NS_LOG_FUNCTION (this << i);
286  return GetInterface (i)->GetDevice ();
287 }
288 
290 {
291  NS_LOG_FUNCTION (this << device);
292 
293  Ipv6InterfaceReverseContainer::const_iterator iter = m_reverseInterfacesContainer.find (device);
294  if (iter != m_reverseInterfacesContainer.end ())
295  {
296  return (*iter).second;
297  }
298 
299  return -1;
300 }
301 
302 void Ipv6L3Protocol::AddAutoconfiguredAddress (uint32_t interface, Ipv6Address network, Ipv6Prefix mask, uint8_t flags, uint32_t validTime, uint32_t preferredTime, Ipv6Address defaultRouter)
303 {
304  NS_LOG_FUNCTION (this << interface << network << mask << (uint32_t)flags << validTime << preferredTime);
306 
307  Address addr = GetInterface (interface)->GetDevice ()->GetAddress ();
308 
309  if (flags & (1 << 6)) /* auto flag */
310  {
311  // In case of new MacAddress types, remember to change Ipv6L3Protocol::RemoveAutoconfiguredAddress as well
312  if (Mac64Address::IsMatchingType (addr))
313  {
315  }
316  else if (Mac48Address::IsMatchingType (addr))
317  {
319  }
320  else if (Mac16Address::IsMatchingType (addr))
321  {
323  }
324  else
325  {
326  NS_FATAL_ERROR ("Unknown method to make autoconfigured address for this kind of device.");
327  return;
328  }
329 
330  /* see if we have already the prefix */
331  for (Ipv6AutoconfiguredPrefixListI it = m_prefixes.begin (); it != m_prefixes.end (); ++it)
332  {
333  if ((*it)->GetInterface () == interface && (*it)->GetPrefix () == network && (*it)->GetMask () == mask)
334  {
335  (*it)->StopPreferredTimer ();
336  (*it)->StopValidTimer ();
337  (*it)->StartPreferredTimer ();
338  return;
339  }
340  }
341 
342  /* no prefix found, add autoconfigured address and the prefix */
343  NS_LOG_INFO ("Autoconfigured address is :" << address.GetAddress ());
344  AddAddress (interface, address);
345 
346  /* add default router
347  * if a previous default route exists, the new ones is simply added
348  */
349  if (!defaultRouter.IsAny())
350  {
351  GetRoutingProtocol ()->NotifyAddRoute (Ipv6Address::GetAny (), Ipv6Prefix ((uint8_t)0), defaultRouter, interface, network);
352  }
353 
354  Ptr<Ipv6AutoconfiguredPrefix> aPrefix = CreateObject<Ipv6AutoconfiguredPrefix> (m_node, interface, network, mask, preferredTime, validTime, defaultRouter);
355  aPrefix->StartPreferredTimer ();
356 
357  m_prefixes.push_back (aPrefix);
358  }
359 }
360 
361 void Ipv6L3Protocol::RemoveAutoconfiguredAddress (uint32_t interface, Ipv6Address network, Ipv6Prefix mask, Ipv6Address defaultRouter)
362 {
363  NS_LOG_FUNCTION (this << interface << network << mask);
364  Ptr<Ipv6Interface> iface = GetInterface (interface);
365  Address addr = iface->GetDevice ()->GetAddress ();
366  uint32_t max = iface->GetNAddresses ();
367  uint32_t i = 0;
368  Ipv6Address toFound;
369 
370  if (Mac64Address::IsMatchingType (addr))
371  {
373  }
374  else if (Mac48Address::IsMatchingType (addr))
375  {
377  }
378  else if (Mac16Address::IsMatchingType (addr))
379  {
381  }
382  else
383  {
384  NS_FATAL_ERROR ("Unknown method to make autoconfigured address for this kind of device.");
385  return;
386  }
387 
388  for (i = 0; i < max; i++)
389  {
390  if (iface->GetAddress (i).GetAddress () == toFound)
391  {
392  RemoveAddress (interface, i);
393  break;
394  }
395  }
396 
397  /* remove from list of autoconfigured address */
398  for (Ipv6AutoconfiguredPrefixListI it = m_prefixes.begin (); it != m_prefixes.end (); ++it)
399  {
400  if ((*it)->GetInterface () == interface && (*it)->GetPrefix () == network && (*it)->GetMask () == mask)
401  {
402  *it = 0;
403  m_prefixes.erase (it);
404  break;
405  }
406  }
407 
408  GetRoutingProtocol ()->NotifyRemoveRoute (Ipv6Address::GetAny (), Ipv6Prefix ((uint8_t)0), defaultRouter, interface, network);
409 }
410 
412 {
413  NS_LOG_FUNCTION (this << i << address);
414  Ptr<Ipv6Interface> interface = GetInterface (i);
415  bool ret = interface->AddAddress (address);
416 
417  if (m_routingProtocol != 0)
418  {
419  m_routingProtocol->NotifyAddAddress (i, address);
420  }
421  return ret;
422 }
423 
424 uint32_t Ipv6L3Protocol::GetNAddresses (uint32_t i) const
425 {
426  NS_LOG_FUNCTION (this << i);
427  Ptr<Ipv6Interface> interface = GetInterface (i);
428  return interface->GetNAddresses ();
429 }
430 
431 Ipv6InterfaceAddress Ipv6L3Protocol::GetAddress (uint32_t i, uint32_t addressIndex) const
432 {
433  NS_LOG_FUNCTION (this << i << addressIndex);
434  Ptr<Ipv6Interface> interface = GetInterface (i);
435  return interface->GetAddress (addressIndex);
436 }
437 
438 bool Ipv6L3Protocol::RemoveAddress (uint32_t i, uint32_t addressIndex)
439 {
440  NS_LOG_FUNCTION (this << i << addressIndex);
441  Ptr<Ipv6Interface> interface = GetInterface (i);
442  Ipv6InterfaceAddress address = interface->RemoveAddress (addressIndex);
443 
444  if (address != Ipv6InterfaceAddress ())
445  {
446  if (m_routingProtocol != 0)
447  {
448  m_routingProtocol->NotifyRemoveAddress (i, address);
449  }
450  return true;
451  }
452  return false;
453 }
454 
455 bool
457 {
458  NS_LOG_FUNCTION (this << i << address);
459 
461  {
462  NS_LOG_WARN ("Cannot remove loopback address.");
463  return false;
464  }
465  Ptr<Ipv6Interface> interface = GetInterface (i);
466  Ipv6InterfaceAddress ifAddr = interface->RemoveAddress (address);
467  if (ifAddr != Ipv6InterfaceAddress ())
468  {
469  if (m_routingProtocol != 0)
470  {
471  m_routingProtocol->NotifyRemoveAddress (i, ifAddr);
472  }
473  return true;
474  }
475  return false;
476 }
477 
478 void Ipv6L3Protocol::SetMetric (uint32_t i, uint16_t metric)
479 {
480  NS_LOG_FUNCTION (this << i << metric);
481  Ptr<Ipv6Interface> interface = GetInterface (i);
482  interface->SetMetric (metric);
483 }
484 
485 uint16_t Ipv6L3Protocol::GetMetric (uint32_t i) const
486 {
487  NS_LOG_FUNCTION (this << i);
488  Ptr<Ipv6Interface> interface = GetInterface (i);
489  return interface->GetMetric ();
490 }
491 
492 uint16_t Ipv6L3Protocol::GetMtu (uint32_t i) const
493 {
494  NS_LOG_FUNCTION (this << i);
495 
496  // RFC 1981, if PMTU is disabled, return the minimum MTU
497  if (!m_mtuDiscover)
498  {
499  return IPV6_MIN_MTU;
500  }
501 
502  Ptr<Ipv6Interface> interface = GetInterface (i);
503  return interface->GetDevice ()->GetMtu ();
504 }
505 
506 void Ipv6L3Protocol::SetPmtu (Ipv6Address dst, uint32_t pmtu)
507 {
508  NS_LOG_FUNCTION (this << dst << int(pmtu));
509  m_pmtuCache->SetPmtu (dst, pmtu);
510 }
511 
512 
513 bool Ipv6L3Protocol::IsUp (uint32_t i) const
514 {
515  NS_LOG_FUNCTION (this << i);
516  Ptr<Ipv6Interface> interface = GetInterface (i);
517  return interface->IsUp ();
518 }
519 
520 void Ipv6L3Protocol::SetUp (uint32_t i)
521 {
522  NS_LOG_FUNCTION (this << i);
523  Ptr<Ipv6Interface> interface = GetInterface (i);
524 
525  // RFC 2460, Section 5, pg. 24:
526  // IPv6 requires that every link in the internet have an MTU of 1280
527  // octets or greater. On any link that cannot convey a 1280-octet
528  // packet in one piece, link-specific fragmentation and reassembly must
529  // be provided at a layer below IPv6.
530  if (interface->GetDevice ()->GetMtu () >= 1280)
531  {
532  interface->SetUp ();
533 
534  if (m_routingProtocol != 0)
535  {
536  m_routingProtocol->NotifyInterfaceUp (i);
537  }
538  }
539  else
540  {
541  NS_LOG_LOGIC ("Interface " << int(i) << " is set to be down for IPv6. Reason: not respecting minimum IPv6 MTU (1280 octets)");
542  }
543 }
544 
545 void Ipv6L3Protocol::SetDown (uint32_t i)
546 {
547  NS_LOG_FUNCTION (this << i);
548  Ptr<Ipv6Interface> interface = GetInterface (i);
549 
550  interface->SetDown ();
551 
552  if (m_routingProtocol != 0)
553  {
554  m_routingProtocol->NotifyInterfaceDown (i);
555  }
556 }
557 
559 {
562  Ptr<LoopbackNetDevice> device = 0;
563  uint32_t i = 0;
564 
565  /* see if we have already an loopback NetDevice */
566  for (i = 0; i < m_node->GetNDevices (); i++)
567  {
568  if ((device = DynamicCast<LoopbackNetDevice> (m_node->GetDevice (i))))
569  {
570  break;
571  }
572  }
573 
574  if (device == 0)
575  {
576  device = CreateObject<LoopbackNetDevice> ();
577  m_node->AddDevice (device);
578  }
579 
580  interface->SetDevice (device);
581  interface->SetNode (m_node);
583  interface->AddAddress (ifaceAddr);
584  uint32_t index = AddIpv6Interface (interface);
585  Ptr<Node> node = GetObject<Node> ();
587  interface->SetUp ();
588 
589  if (m_routingProtocol != 0)
590  {
591  m_routingProtocol->NotifyInterfaceUp (index);
592  }
593 }
594 
595 bool Ipv6L3Protocol::IsForwarding (uint32_t i) const
596 {
597  NS_LOG_FUNCTION (this << i);
598  Ptr<Ipv6Interface> interface = GetInterface (i);
599 
600  NS_LOG_LOGIC ("Forwarding state: " << interface->IsForwarding ());
601  return interface->IsForwarding ();
602 }
603 
604 void Ipv6L3Protocol::SetForwarding (uint32_t i, bool val)
605 {
606  NS_LOG_FUNCTION (this << i << val);
607  Ptr<Ipv6Interface> interface = GetInterface (i);
608  interface->SetForwarding (val);
609 }
610 
612 {
613  NS_LOG_FUNCTION (this << interface << dest);
614  Ipv6Address ret;
615 
616  if (dest.IsLinkLocal () || dest.IsLinkLocalMulticast ())
617  {
618  for (uint32_t i = 0; i < GetNAddresses (interface); i++)
619  {
620  Ipv6InterfaceAddress test = GetAddress (interface, i);
621  if (test.GetScope () == Ipv6InterfaceAddress::LINKLOCAL)
622  {
623  return test.GetAddress ();
624  }
625  }
626  NS_ASSERT_MSG (false, "No link-local address found on interface " << interface);
627  }
628 
629  for (uint32_t i = 0; i < GetNAddresses (interface); i++)
630  {
631  Ipv6InterfaceAddress test = GetAddress (interface, i);
632 
633  if (test.GetScope () == Ipv6InterfaceAddress::GLOBAL)
634  {
635  if (test.IsInSameSubnet (dest))
636  {
637  return test.GetAddress ();
638  }
639  else
640  {
641  ret = test.GetAddress ();
642  }
643  }
644  }
645 
646  // no specific match found. Use a global address (any useful is fine).
647  return ret;
648 }
649 
650 void Ipv6L3Protocol::SetIpForward (bool forward)
651 {
652  NS_LOG_FUNCTION (this << forward);
653  m_ipForward = forward;
654 
655  for (Ipv6InterfaceList::const_iterator it = m_interfaces.begin (); it != m_interfaces.end (); it++)
656  {
657  (*it)->SetForwarding (forward);
658  }
659 }
660 
662 {
664  return m_ipForward;
665 }
666 
667 void Ipv6L3Protocol::SetMtuDiscover (bool mtuDiscover)
668 {
669  NS_LOG_FUNCTION (this << int(mtuDiscover));
670  m_mtuDiscover = mtuDiscover;
671 }
672 
674 {
675  NS_LOG_FUNCTION (this);
676  return m_mtuDiscover;
677 }
678 
679 void Ipv6L3Protocol::SetSendIcmpv6Redirect (bool sendIcmpv6Redirect)
680 {
681  NS_LOG_FUNCTION (this << sendIcmpv6Redirect);
682  m_sendIcmpv6Redirect = sendIcmpv6Redirect;
683 }
684 
686 {
688  return m_sendIcmpv6Redirect;
689 }
690 
692 {
694 
695  if (m_node == 0)
696  {
697  Ptr<Node> node = this->GetObject<Node> ();
698  // verify that it's a valid node and that
699  // the node has not been set before
700  if (node != 0)
701  {
702  this->SetNode (node);
703  }
704  }
706 }
707 
709 {
710  NS_LOG_FUNCTION (this << node);
711  m_node = node;
712  /* add LoopbackNetDevice if needed, and an Ipv6Interface on top of it */
713  SetupLoopback ();
714 }
715 
717 {
718  NS_LOG_FUNCTION (this << protocol);
719  L4ListKey_t key = std::make_pair (protocol->GetProtocolNumber (), -1);
720  if (m_protocols.find (key) != m_protocols.end ())
721  {
722  NS_LOG_WARN ("Overwriting default protocol " << int(protocol->GetProtocolNumber ()));
723  }
724  m_protocols[key] = protocol;
725 }
726 
727 void Ipv6L3Protocol::Insert (Ptr<IpL4Protocol> protocol, uint32_t interfaceIndex)
728 {
729  NS_LOG_FUNCTION (this << protocol << interfaceIndex);
730 
731  L4ListKey_t key = std::make_pair (protocol->GetProtocolNumber (), interfaceIndex);
732  if (m_protocols.find (key) != m_protocols.end ())
733  {
734  NS_LOG_WARN ("Overwriting protocol " << int(protocol->GetProtocolNumber ()) << " on interface " << int(interfaceIndex));
735  }
736  m_protocols[key] = protocol;
737 }
738 
740 {
741  NS_LOG_FUNCTION (this << protocol);
742 
743  L4ListKey_t key = std::make_pair (protocol->GetProtocolNumber (), -1);
744  L4List_t::iterator iter = m_protocols.find (key);
745  if (iter == m_protocols.end ())
746  {
747  NS_LOG_WARN ("Trying to remove an non-existent default protocol " << int(protocol->GetProtocolNumber ()));
748  }
749  else
750  {
751  m_protocols.erase (key);
752  }
753 }
754 
755 void Ipv6L3Protocol::Remove (Ptr<IpL4Protocol> protocol, uint32_t interfaceIndex)
756 {
757  NS_LOG_FUNCTION (this << protocol << interfaceIndex);
758 
759  L4ListKey_t key = std::make_pair (protocol->GetProtocolNumber (), interfaceIndex);
760  L4List_t::iterator iter = m_protocols.find (key);
761  if (iter == m_protocols.end ())
762  {
763  NS_LOG_WARN ("Trying to remove an non-existent protocol " << int(protocol->GetProtocolNumber ()) << " on interface " << int(interfaceIndex));
764  }
765  else
766  {
767  m_protocols.erase (key);
768  }
769 }
770 
772 {
773  NS_LOG_FUNCTION (this << protocolNumber);
774 
775  return GetProtocol (protocolNumber, -1);
776 }
777 
778 Ptr<IpL4Protocol> Ipv6L3Protocol::GetProtocol (int protocolNumber, int32_t interfaceIndex) const
779 {
780  NS_LOG_FUNCTION (this << protocolNumber << interfaceIndex);
781 
782  L4ListKey_t key;
783  L4List_t::const_iterator i;
784  if (interfaceIndex >= 0)
785  {
786  // try the interface-specific protocol.
787  key = std::make_pair (protocolNumber, interfaceIndex);
788  i = m_protocols.find (key);
789  if (i != m_protocols.end ())
790  {
791  return i->second;
792  }
793  }
794  // try the generic protocol.
795  key = std::make_pair (protocolNumber, -1);
796  i = m_protocols.find (key);
797  if (i != m_protocols.end ())
798  {
799  return i->second;
800  }
801 
802  return 0;
803 }
804 
806 {
808  Ptr<Ipv6RawSocketImpl> sock = CreateObject<Ipv6RawSocketImpl> ();
809  sock->SetNode (m_node);
810  m_sockets.push_back (sock);
811  return sock;
812 }
813 
815 {
816  NS_LOG_FUNCTION (this << socket);
817 
818  for (SocketList::iterator it = m_sockets.begin (); it != m_sockets.end (); ++it)
819  {
820  if ((*it) == socket)
821  {
822  m_sockets.erase (it);
823  return;
824  }
825  }
826 }
827 
829 {
832 
833  if (protocol)
834  {
835  return protocol->GetObject<Icmpv6L4Protocol> ();
836  }
837  else
838  {
839  return 0;
840  }
841 }
842 
844 {
845  NS_LOG_FUNCTION (this << ttl);
846  m_defaultTtl = ttl;
847 }
848 
849 void Ipv6L3Protocol::SetDefaultTclass (uint8_t tclass)
850 {
851  NS_LOG_FUNCTION (this << tclass);
852  m_defaultTclass = tclass;
853 }
854 
855 void Ipv6L3Protocol::Send (Ptr<Packet> packet, Ipv6Address source, Ipv6Address destination, uint8_t protocol, Ptr<Ipv6Route> route)
856 {
857  NS_LOG_FUNCTION (this << packet << source << destination << (uint32_t)protocol << route);
858  Ipv6Header hdr;
859  uint8_t ttl = m_defaultTtl;
861  bool found = packet->RemovePacketTag (tag);
862 
863  if (found)
864  {
865  ttl = tag.GetHopLimit ();
866  }
867 
868  SocketIpv6TclassTag tclassTag;
869  uint8_t tclass = m_defaultTclass;
870  found = packet->RemovePacketTag (tclassTag);
871 
872  if (found)
873  {
874  tclass = tclassTag.GetTclass ();
875  }
876 
877  /* Handle 3 cases:
878  * 1) Packet is passed in with a route entry
879  * 2) Packet is passed in with a route entry but route->GetGateway is not set (e.g., same network)
880  * 3) route is NULL (e.g., a raw socket call or ICMPv6)
881  */
882 
883  /* 1) */
884  if (route && route->GetGateway () != Ipv6Address::GetZero ())
885  {
886  NS_LOG_LOGIC ("Ipv6L3Protocol::Send case 1: passed in with a route");
887  hdr = BuildHeader (source, destination, protocol, packet->GetSize (), ttl, tclass);
888  int32_t interface = GetInterfaceForDevice (route->GetOutputDevice ());
889  m_sendOutgoingTrace (hdr, packet, interface);
890  SendRealOut (route, packet, hdr);
891  return;
892  }
893 
894  /* 2) */
895  if (route && route->GetGateway () == Ipv6Address::GetZero ())
896  {
897  NS_LOG_LOGIC ("Ipv6L3Protocol::Send case 2: probably sent to machine on same IPv6 network");
898  hdr = BuildHeader (source, destination, protocol, packet->GetSize (), ttl, tclass);
899  int32_t interface = GetInterfaceForDevice (route->GetOutputDevice ());
900  m_sendOutgoingTrace (hdr, packet, interface);
901  SendRealOut (route, packet, hdr);
902  return;
903  }
904 
905  /* 3) */
906  NS_LOG_LOGIC ("Ipv6L3Protocol::Send case 3: passed in with no route " << destination);
908  Ptr<NetDevice> oif (0);
909  Ptr<Ipv6Route> newRoute = 0;
910 
911  hdr = BuildHeader (source, destination, protocol, packet->GetSize (), ttl, tclass);
912 
913  //for link-local traffic, we need to determine the interface
914  if (source.IsLinkLocal ()
915  || destination.IsLinkLocal ()
916  || destination.IsLinkLocalMulticast ())
917  {
918  int32_t index = GetInterfaceForAddress (source);
919  NS_ASSERT_MSG (index >= 0, "Can not find an outgoing interface for a packet with src " << source << " and dst " << destination);
920  oif = GetNetDevice (index);
921  }
922 
923  newRoute = m_routingProtocol->RouteOutput (packet, hdr, oif, err);
924 
925  if (newRoute)
926  {
927  int32_t interface = GetInterfaceForDevice (newRoute->GetOutputDevice ());
928  m_sendOutgoingTrace (hdr, packet, interface);
929  SendRealOut (newRoute, packet, hdr);
930  }
931  else
932  {
933  NS_LOG_WARN ("No route to host, drop!");
935  }
936 }
937 
938 void Ipv6L3Protocol::Receive (Ptr<NetDevice> device, Ptr<const Packet> p, uint16_t protocol, const Address &from, const Address &to, NetDevice::PacketType packetType)
939 {
940  NS_LOG_FUNCTION (this << device << p << protocol << from << to << packetType);
941  NS_LOG_LOGIC ("Packet from " << from << " received on node " << m_node->GetId ());
942 
943  NS_ASSERT_MSG (GetInterfaceForDevice(device) != -1, "Received a packet from an interface that is not known to IPv6");
944  uint32_t interface = GetInterfaceForDevice(device);
945 
946  Ptr<Ipv6Interface> ipv6Interface = m_interfaces[interface];
947  Ptr<Packet> packet = p->Copy ();
948 
949  if (ipv6Interface->IsUp ())
950  {
951  m_rxTrace (packet, m_node->GetObject<Ipv6> (), interface);
952  }
953  else
954  {
955  NS_LOG_LOGIC ("Dropping received packet-- interface is down");
956  Ipv6Header hdr;
957  packet->RemoveHeader (hdr);
958  m_dropTrace (hdr, packet, DROP_INTERFACE_DOWN, m_node->GetObject<Ipv6> (), interface);
959  return;
960  }
961 
962  Ipv6Header hdr;
963  packet->RemoveHeader (hdr);
964 
965  // Trim any residual frame padding from underlying devices
966  if (hdr.GetPayloadLength () < packet->GetSize ())
967  {
968  packet->RemoveAtEnd (packet->GetSize () - hdr.GetPayloadLength ());
969  }
970 
971  // the packet is valid, we update the NDISC cache entry (if present)
972  Ptr<NdiscCache> ndiscCache = ipv6Interface->GetNdiscCache ();
973  if (ndiscCache)
974  {
975  // case one, it's a a direct routing.
976  NdiscCache::Entry *entry = ndiscCache->Lookup (hdr.GetSourceAddress ());
977  if (entry)
978  {
979  entry->UpdateReachableTimer ();
980  }
981  else
982  {
983  // It's not in the direct routing, so it's the router, and it could have multiple IP addresses.
984  // In doubt, update all of them.
985  // Note: it's a confirmed behavior for Linux routers.
986  std::list<NdiscCache::Entry *> entryList = ndiscCache->LookupInverse (from);
987  std::list<NdiscCache::Entry *>::iterator iter;
988  for (iter = entryList.begin (); iter != entryList.end (); iter ++)
989  {
990  (*iter)->UpdateReachableTimer ();
991  }
992  }
993  }
994 
995 
996 
997  /* forward up to IPv6 raw sockets */
998  for (SocketList::iterator it = m_sockets.begin (); it != m_sockets.end (); ++it)
999  {
1000  Ptr<Ipv6RawSocketImpl> socket = *it;
1001  socket->ForwardUp (packet, hdr, device);
1002  }
1003 
1004  Ptr<Ipv6ExtensionDemux> ipv6ExtensionDemux = m_node->GetObject<Ipv6ExtensionDemux> ();
1005  Ptr<Ipv6Extension> ipv6Extension = 0;
1006  uint8_t nextHeader = hdr.GetNextHeader ();
1007  bool stopProcessing = false;
1008  bool isDropped = false;
1009  DropReason dropReason;
1010 
1011  if (nextHeader == Ipv6Header::IPV6_EXT_HOP_BY_HOP)
1012  {
1013  ipv6Extension = ipv6ExtensionDemux->GetExtension (nextHeader);
1014 
1015  if (ipv6Extension)
1016  {
1017  ipv6Extension->Process (packet, 0, hdr, hdr.GetDestinationAddress (), (uint8_t *)0, stopProcessing, isDropped, dropReason);
1018  }
1019 
1020  if (isDropped)
1021  {
1022  m_dropTrace (hdr, packet, dropReason, m_node->GetObject<Ipv6> (), interface);
1023  }
1024 
1025  if (stopProcessing)
1026  {
1027  return;
1028  }
1029  }
1030 
1032  {
1033  LocalDeliver (packet, hdr, interface);
1034  return;
1035  }
1036  else if (hdr.GetDestinationAddress ().IsAllRoutersMulticast() && ipv6Interface->IsForwarding ())
1037  {
1038  LocalDeliver (packet, hdr, interface);
1039  return;
1040  }
1041  else if (hdr.GetDestinationAddress ().IsMulticast ())
1042  {
1043  bool isSolicited = ipv6Interface->IsSolicitedMulticastAddress (hdr.GetDestinationAddress ());
1044  bool isRegisteredOnInterface = IsRegisteredMulticastAddress (hdr.GetDestinationAddress (), interface);
1045  bool isRegisteredGlobally = IsRegisteredMulticastAddress (hdr.GetDestinationAddress ());
1046  if (isSolicited || isRegisteredGlobally || isRegisteredOnInterface)
1047  {
1048  LocalDeliver (packet, hdr, interface);
1049  // do not return, the packet could be handled by a routing protocol
1050  }
1051  }
1052 
1053 
1054  for (uint32_t j = 0; j < GetNInterfaces (); j++)
1055  {
1056  if (j == interface || !m_strongEndSystemModel)
1057  {
1058  for (uint32_t i = 0; i < GetNAddresses (j); i++)
1059  {
1060  Ipv6InterfaceAddress iaddr = GetAddress (j, i);
1061  Ipv6Address addr = iaddr.GetAddress ();
1062  if (addr.IsEqual (hdr.GetDestinationAddress ()))
1063  {
1064  if (j == interface)
1065  {
1066  NS_LOG_LOGIC ("For me (destination " << addr << " match)");
1067  }
1068  else
1069  {
1070  NS_LOG_LOGIC ("For me (destination " << addr << " match) on another interface " << hdr.GetDestinationAddress ());
1071  }
1072  LocalDeliver (packet, hdr, interface);
1073  return;
1074  }
1075  NS_LOG_LOGIC ("Address " << addr << " not a match");
1076  }
1077  }
1078  }
1079 
1080  if (!m_routingProtocol->RouteInput (packet, hdr, device,
1085  {
1086  NS_LOG_WARN ("No route found for forwarding packet. Drop.");
1087  // Drop trace and ICMPs are courtesy of RouteInputError
1088  }
1089 }
1090 
1091 void
1093  Ptr<Ipv6> ipv6, uint32_t interface)
1094 {
1095  Ptr<Packet> packetCopy = packet->Copy ();
1096  packetCopy->AddHeader (ipHeader);
1097  m_txTrace (packetCopy, ipv6, interface);
1098 }
1099 
1101 {
1102  NS_LOG_FUNCTION (this << route << packet << ipHeader);
1103 
1104  if (!route)
1105  {
1106  NS_LOG_LOGIC ("No route to host, drop!.");
1107  return;
1108  }
1109 
1110  Ptr<NetDevice> dev = route->GetOutputDevice ();
1111  int32_t interface = GetInterfaceForDevice (dev);
1112  NS_ASSERT (interface >= 0);
1113 
1114  Ptr<Ipv6Interface> outInterface = GetInterface (interface);
1115  NS_LOG_LOGIC ("Send via NetDevice ifIndex " << dev->GetIfIndex () << " Ipv6InterfaceIndex " << interface);
1116 
1117  // Check packet size
1118  std::list<Ipv6ExtensionFragment::Ipv6PayloadHeaderPair> fragments;
1119 
1120  // Check if we have a Path MTU stored. If so, use it. Else, use the link MTU.
1121  size_t targetMtu = (size_t)(m_pmtuCache->GetPmtu (ipHeader.GetDestinationAddress()));
1122  if (targetMtu == 0)
1123  {
1124  targetMtu = dev->GetMtu ();
1125  }
1126 
1127  if (packet->GetSize () > targetMtu + 40) /* 40 => size of IPv6 header */
1128  {
1129  // Router => drop
1130 
1131  bool fromMe = false;
1132  for (uint32_t i=0; i<GetNInterfaces(); i++ )
1133  {
1134  for (uint32_t j=0; j<GetNAddresses(i); j++ )
1135  {
1136  if (GetAddress(i,j).GetAddress() == ipHeader.GetSourceAddress())
1137  {
1138  fromMe = true;
1139  break;
1140  }
1141  }
1142  }
1143  if (!fromMe)
1144  {
1145  Ptr<Icmpv6L4Protocol> icmpv6 = GetIcmpv6 ();
1146  if ( icmpv6 )
1147  {
1148  packet->AddHeader(ipHeader);
1149  icmpv6->SendErrorTooBig (packet, ipHeader.GetSourceAddress (), dev->GetMtu ());
1150  }
1151  return;
1152  }
1153 
1154  Ptr<Ipv6ExtensionDemux> ipv6ExtensionDemux = m_node->GetObject<Ipv6ExtensionDemux> ();
1155 
1156  // To get specific method GetFragments from Ipv6ExtensionFragmentation
1157  Ipv6ExtensionFragment *ipv6Fragment = dynamic_cast<Ipv6ExtensionFragment *> (PeekPointer (ipv6ExtensionDemux->GetExtension (Ipv6Header::IPV6_EXT_FRAGMENTATION)));
1158  NS_ASSERT (ipv6Fragment != 0);
1159  ipv6Fragment->GetFragments (packet, ipHeader, targetMtu, fragments);
1160  }
1161 
1162  if (!route->GetGateway ().IsEqual (Ipv6Address::GetAny ()))
1163  {
1164  if (outInterface->IsUp ())
1165  {
1166  NS_LOG_LOGIC ("Send to gateway " << route->GetGateway ());
1167 
1168  if (fragments.size () != 0)
1169  {
1170  std::ostringstream oss;
1171 
1172  for (std::list<Ipv6ExtensionFragment::Ipv6PayloadHeaderPair>::const_iterator it = fragments.begin (); it != fragments.end (); it++)
1173  {
1174  CallTxTrace (it->second, it->first, m_node->GetObject<Ipv6> (), interface);
1175  outInterface->Send (it->first, it->second, route->GetGateway ());
1176  }
1177  }
1178  else
1179  {
1180  CallTxTrace (ipHeader, packet, m_node->GetObject<Ipv6> (), interface);
1181  outInterface->Send (packet, ipHeader, route->GetGateway ());
1182  }
1183  }
1184  else
1185  {
1186  NS_LOG_LOGIC ("Dropping-- outgoing interface is down: " << route->GetGateway ());
1187  m_dropTrace (ipHeader, packet, DROP_INTERFACE_DOWN, m_node->GetObject<Ipv6> (), interface);
1188  }
1189  }
1190  else
1191  {
1192  if (outInterface->IsUp ())
1193  {
1194  NS_LOG_LOGIC ("Send to destination " << ipHeader.GetDestinationAddress ());
1195 
1196  if (fragments.size () != 0)
1197  {
1198  std::ostringstream oss;
1199 
1200  for (std::list<Ipv6ExtensionFragment::Ipv6PayloadHeaderPair>::const_iterator it = fragments.begin (); it != fragments.end (); it++)
1201  {
1202  CallTxTrace (it->second, it->first, m_node->GetObject<Ipv6> (), interface);
1203  outInterface->Send (it->first, it->second, ipHeader.GetDestinationAddress ());
1204  }
1205  }
1206  else
1207  {
1208  CallTxTrace (ipHeader, packet, m_node->GetObject<Ipv6> (), interface);
1209  outInterface->Send (packet, ipHeader, ipHeader.GetDestinationAddress ());
1210  }
1211  }
1212  else
1213  {
1214  NS_LOG_LOGIC ("Dropping-- outgoing interface is down: " << ipHeader.GetDestinationAddress ());
1215  m_dropTrace (ipHeader, packet, DROP_INTERFACE_DOWN, m_node->GetObject<Ipv6> (), interface);
1216  }
1217  }
1218 }
1219 
1221 {
1222  NS_LOG_FUNCTION (this << rtentry << p << header);
1223  NS_LOG_LOGIC ("Forwarding logic for node: " << m_node->GetId ());
1224 
1225  // Drop RFC 3849 packets: 2001:db8::/32
1226  if (header.GetDestinationAddress().IsDocumentation ())
1227  {
1228  NS_LOG_WARN ("Received a packet for 2001:db8::/32 (documentation class). Drop.");
1229  m_dropTrace (header, p, DROP_ROUTE_ERROR, m_node->GetObject<Ipv6> (), 0);
1230  return;
1231  }
1232 
1233  // Forwarding
1234  Ipv6Header ipHeader = header;
1235  Ptr<Packet> packet = p->Copy ();
1236  ipHeader.SetHopLimit (ipHeader.GetHopLimit () - 1);
1237 
1238  if (ipHeader.GetSourceAddress ().IsLinkLocal ())
1239  {
1240  /* no forward for link-local address */
1241  return;
1242  }
1243 
1244  if (ipHeader.GetHopLimit () == 0)
1245  {
1246  NS_LOG_WARN ("TTL exceeded. Drop.");
1247  m_dropTrace (ipHeader, packet, DROP_TTL_EXPIRED, m_node->GetObject<Ipv6> (), 0);
1248  // Do not reply to multicast IPv6 address
1249  if (ipHeader.GetDestinationAddress ().IsMulticast () == false)
1250  {
1251  packet->AddHeader (ipHeader);
1252  GetIcmpv6 ()->SendErrorTimeExceeded (packet, ipHeader.GetSourceAddress (), Icmpv6Header::ICMPV6_HOPLIMIT);
1253  }
1254  return;
1255  }
1256 
1257  /* ICMPv6 Redirect */
1258 
1259  /* if we forward to a machine on the same network as the source,
1260  * we send him an ICMPv6 redirect message to notify him that a short route
1261  * exists.
1262  */
1263 
1264  /* Theoretically we should also check if the redirect target is on the same network
1265  * as the source node. On the other hand, we are sure that the router we're redirecting to
1266  * used a link-local address. As a consequence, they MUST be on the same network, the link-local net.
1267  */
1268 
1269  if (m_sendIcmpv6Redirect && (rtentry->GetOutputDevice ()==idev))
1270  {
1271  NS_LOG_LOGIC ("ICMPv6 redirect!");
1272  Ptr<Icmpv6L4Protocol> icmpv6 = GetIcmpv6 ();
1273  Address hardwareTarget;
1274  Ipv6Address dst = header.GetDestinationAddress ();
1275  Ipv6Address src = header.GetSourceAddress ();
1276  Ipv6Address target = rtentry->GetGateway ();
1277  Ptr<Packet> copy = p->Copy ();
1278 
1279  if (target.IsAny ())
1280  {
1281  target = dst;
1282  }
1283 
1284  copy->AddHeader (header);
1285  Ipv6Address linkLocal = GetInterface (GetInterfaceForDevice (rtentry->GetOutputDevice ()))->GetLinkLocalAddress ().GetAddress ();
1286 
1287  if (icmpv6->Lookup (target, rtentry->GetOutputDevice (), 0, &hardwareTarget))
1288  {
1289  icmpv6->SendRedirection (copy, linkLocal, src, target, dst, hardwareTarget);
1290  }
1291  else
1292  {
1293  icmpv6->SendRedirection (copy, linkLocal, src, target, dst, Address ());
1294  }
1295  }
1296  // in case the packet still has a priority tag attached, remove it
1297  SocketPriorityTag priorityTag;
1298  packet->RemovePacketTag (priorityTag);
1299  int32_t interface = GetInterfaceForDevice (rtentry->GetOutputDevice ());
1300  m_unicastForwardTrace (ipHeader, packet, interface);
1301  SendRealOut (rtentry, packet, ipHeader);
1302 }
1303 
1305 {
1306  NS_LOG_FUNCTION (this << mrtentry << p << header);
1307  NS_LOG_LOGIC ("Multicast forwarding logic for node: " << m_node->GetId ());
1308 
1309  std::map<uint32_t, uint32_t> ttlMap = mrtentry->GetOutputTtlMap ();
1310  std::map<uint32_t, uint32_t>::iterator mapIter;
1311 
1312  for (mapIter = ttlMap.begin (); mapIter != ttlMap.end (); mapIter++)
1313  {
1314  uint32_t interfaceId = mapIter->first;
1315  //uint32_t outputTtl = mapIter->second; // Unused for now
1316  Ptr<Packet> packet = p->Copy ();
1317  Ipv6Header h = header;
1318  h.SetHopLimit (header.GetHopLimit () - 1);
1319  if (h.GetHopLimit () == 0)
1320  {
1321  NS_LOG_WARN ("TTL exceeded. Drop.");
1322  m_dropTrace (header, packet, DROP_TTL_EXPIRED, m_node->GetObject<Ipv6> (), interfaceId);
1323  return;
1324  }
1325  NS_LOG_LOGIC ("Forward multicast via interface " << interfaceId);
1326  Ptr<Ipv6Route> rtentry = Create<Ipv6Route> ();
1327  rtentry->SetSource (h.GetSourceAddress ());
1328  rtentry->SetDestination (h.GetDestinationAddress ());
1329  rtentry->SetGateway (Ipv6Address::GetAny ());
1330  rtentry->SetOutputDevice (GetNetDevice (interfaceId));
1331  SendRealOut (rtentry, packet, h);
1332  continue;
1333  }
1334 }
1335 
1336 void Ipv6L3Protocol::LocalDeliver (Ptr<const Packet> packet, Ipv6Header const& ip, uint32_t iif)
1337 {
1338  NS_LOG_FUNCTION (this << packet << ip << iif);
1339  Ptr<Packet> p = packet->Copy ();
1340  Ptr<IpL4Protocol> protocol = 0;
1341  Ptr<Ipv6ExtensionDemux> ipv6ExtensionDemux = m_node->GetObject<Ipv6ExtensionDemux> ();
1342  Ptr<Ipv6Extension> ipv6Extension = 0;
1343  Ipv6Address src = ip.GetSourceAddress ();
1344  Ipv6Address dst = ip.GetDestinationAddress ();
1345  uint8_t nextHeader = ip.GetNextHeader ();
1346  uint8_t nextHeaderPosition = 0;
1347  bool isDropped = false;
1348  bool stopProcessing = false;
1349  DropReason dropReason;
1350 
1351  // check for a malformed hop-by-hop extension
1352  // this is a common case when forging IPv6 raw packets
1353  if (nextHeader == Ipv6Header::IPV6_EXT_HOP_BY_HOP)
1354  {
1355  uint8_t buf;
1356  p->CopyData (&buf, 1);
1358  {
1359  NS_LOG_WARN("Double Ipv6Header::IPV6_EXT_HOP_BY_HOP in packet, dropping packet");
1360  return;
1361  }
1362  }
1363 
1364  /* process all the extensions found and the layer 4 protocol */
1365  do
1366  {
1367  /* it return 0 for non-extension (i.e. layer 4 protocol) */
1368  ipv6Extension = ipv6ExtensionDemux->GetExtension (nextHeader);
1369 
1370  if (ipv6Extension)
1371  {
1372  uint8_t nextHeaderStep = 0;
1373  uint8_t curHeader = nextHeader;
1374  nextHeaderStep = ipv6Extension->Process (p, nextHeaderPosition, ip, dst, &nextHeader, stopProcessing, isDropped, dropReason);
1375  nextHeaderPosition += nextHeaderStep;
1376 
1377  if (isDropped)
1378  {
1379  m_dropTrace (ip, packet, dropReason, m_node->GetObject<Ipv6> (), iif);
1380  }
1381 
1382  if (stopProcessing)
1383  {
1384  return;
1385  }
1386  NS_ASSERT_MSG (nextHeaderStep != 0 || curHeader == Ipv6Header::IPV6_EXT_FRAGMENTATION,
1387  "Zero-size IPv6 Option Header, aborting" << *packet );
1388  }
1389  else
1390  {
1391  protocol = GetProtocol (nextHeader, iif);
1392 
1393  if (!protocol)
1394  {
1395  NS_LOG_LOGIC ("Unknown Next Header. Drop!");
1396 
1397  // For ICMPv6 Error packets
1398  Ptr<Packet> malformedPacket = packet->Copy ();
1399  malformedPacket->AddHeader (ip);
1400 
1401  if (nextHeaderPosition == 0)
1402  {
1403  GetIcmpv6 ()->SendErrorParameterError (malformedPacket, dst, Icmpv6Header::ICMPV6_UNKNOWN_NEXT_HEADER, 40);
1404  }
1405  else
1406  {
1407  GetIcmpv6 ()->SendErrorParameterError (malformedPacket, dst, Icmpv6Header::ICMPV6_UNKNOWN_NEXT_HEADER, ip.GetSerializedSize () + nextHeaderPosition);
1408  }
1410  break;
1411  }
1412  else
1413  {
1414  p->RemoveAtStart (nextHeaderPosition);
1415  /* protocol->Receive (p, src, dst, incomingInterface); */
1416 
1417  /* L4 protocol */
1418  Ptr<Packet> copy = p->Copy ();
1419 
1420  m_localDeliverTrace (ip, p, iif);
1421 
1422  enum IpL4Protocol::RxStatus status = protocol->Receive (p, ip, GetInterface (iif));
1423 
1424  switch (status)
1425  {
1426  case IpL4Protocol::RX_OK:
1427  break;
1429  break;
1431  break;
1433  if (ip.GetDestinationAddress ().IsMulticast ())
1434  {
1435  /* do not rely on multicast address */
1436  break;
1437  }
1438 
1439  copy->AddHeader (ip);
1440  GetIcmpv6 ()->SendErrorDestinationUnreachable (copy, ip.GetSourceAddress (), Icmpv6Header::ICMPV6_PORT_UNREACHABLE);
1441  }
1442  }
1443  }
1444  }
1445  while (ipv6Extension);
1446 }
1447 
1449 {
1450  NS_LOG_FUNCTION (this << p << ipHeader << sockErrno);
1451  NS_LOG_LOGIC ("Route input failure-- dropping packet to " << ipHeader << " with errno " << sockErrno);
1452 
1453  m_dropTrace (ipHeader, p, DROP_ROUTE_ERROR, m_node->GetObject<Ipv6> (), 0);
1454 
1455  if (!ipHeader.GetDestinationAddress ().IsMulticast ())
1456  {
1457  Ptr<Packet> packet = p->Copy ();
1458  packet->AddHeader (ipHeader);
1459  GetIcmpv6 ()->SendErrorDestinationUnreachable (packet, ipHeader.GetSourceAddress (), Icmpv6Header::ICMPV6_NO_ROUTE);
1460  }
1461 }
1462 
1463 Ipv6Header Ipv6L3Protocol::BuildHeader (Ipv6Address src, Ipv6Address dst, uint8_t protocol, uint16_t payloadSize, uint8_t ttl, uint8_t tclass)
1464 {
1465  NS_LOG_FUNCTION (this << src << dst << (uint32_t)protocol << (uint32_t)payloadSize << (uint32_t)ttl << (uint32_t)tclass);
1466  Ipv6Header hdr;
1467 
1468  hdr.SetSourceAddress (src);
1469  hdr.SetDestinationAddress (dst);
1470  hdr.SetNextHeader (protocol);
1471  hdr.SetPayloadLength (payloadSize);
1472  hdr.SetHopLimit (ttl);
1473  hdr.SetTrafficClass (tclass);
1474  return hdr;
1475 }
1476 
1478 {
1479  Ptr<Ipv6ExtensionDemux> ipv6ExtensionDemux = CreateObject<Ipv6ExtensionDemux> ();
1480  ipv6ExtensionDemux->SetNode (m_node);
1481 
1482  Ptr<Ipv6ExtensionHopByHop> hopbyhopExtension = CreateObject<Ipv6ExtensionHopByHop> ();
1483  hopbyhopExtension->SetNode (m_node);
1484  Ptr<Ipv6ExtensionDestination> destinationExtension = CreateObject<Ipv6ExtensionDestination> ();
1485  destinationExtension->SetNode (m_node);
1486  Ptr<Ipv6ExtensionFragment> fragmentExtension = CreateObject<Ipv6ExtensionFragment> ();
1487  fragmentExtension->SetNode (m_node);
1488  Ptr<Ipv6ExtensionRouting> routingExtension = CreateObject<Ipv6ExtensionRouting> ();
1489  routingExtension->SetNode (m_node);
1490  // Ptr<Ipv6ExtensionESP> espExtension = CreateObject<Ipv6ExtensionESP> ();
1491  // Ptr<Ipv6ExtensionAH> ahExtension = CreateObject<Ipv6ExtensionAH> ();
1492 
1493  ipv6ExtensionDemux->Insert (hopbyhopExtension);
1494  ipv6ExtensionDemux->Insert (destinationExtension);
1495  ipv6ExtensionDemux->Insert (fragmentExtension);
1496  ipv6ExtensionDemux->Insert (routingExtension);
1497  // ipv6ExtensionDemux->Insert (espExtension);
1498  // ipv6ExtensionDemux->Insert (ahExtension);
1499 
1500  Ptr<Ipv6ExtensionRoutingDemux> routingExtensionDemux = CreateObject<Ipv6ExtensionRoutingDemux> ();
1501  routingExtensionDemux->SetNode (m_node);
1502  Ptr<Ipv6ExtensionLooseRouting> looseRoutingExtension = CreateObject<Ipv6ExtensionLooseRouting> ();
1503  looseRoutingExtension->SetNode (m_node);
1504  routingExtensionDemux->Insert (looseRoutingExtension);
1505 
1506  m_node->AggregateObject (routingExtensionDemux);
1507  m_node->AggregateObject (ipv6ExtensionDemux);
1508 }
1509 
1511 {
1512  Ptr<Ipv6OptionDemux> ipv6OptionDemux = CreateObject<Ipv6OptionDemux> ();
1513  ipv6OptionDemux->SetNode (m_node);
1514 
1515  Ptr<Ipv6OptionPad1> pad1Option = CreateObject<Ipv6OptionPad1> ();
1516  pad1Option->SetNode (m_node);
1517  Ptr<Ipv6OptionPadn> padnOption = CreateObject<Ipv6OptionPadn> ();
1518  padnOption->SetNode (m_node);
1519  Ptr<Ipv6OptionJumbogram> jumbogramOption = CreateObject<Ipv6OptionJumbogram> ();
1520  jumbogramOption->SetNode (m_node);
1521  Ptr<Ipv6OptionRouterAlert> routerAlertOption = CreateObject<Ipv6OptionRouterAlert> ();
1522  routerAlertOption->SetNode (m_node);
1523 
1524  ipv6OptionDemux->Insert (pad1Option);
1525  ipv6OptionDemux->Insert (padnOption);
1526  ipv6OptionDemux->Insert (jumbogramOption);
1527  ipv6OptionDemux->Insert (routerAlertOption);
1528 
1529  m_node->AggregateObject (ipv6OptionDemux);
1530 }
1531 
1533 {
1534  m_dropTrace (ipHeader, p, dropReason, m_node->GetObject<Ipv6> (), 0);
1535 }
1536 
1538 {
1539  NS_LOG_FUNCTION (address << interface);
1540 
1541  if (!address.IsMulticast ())
1542  {
1543  NS_LOG_WARN ("Not adding a non-multicast address " << address);
1544  return;
1545  }
1546 
1547  Ipv6RegisteredMulticastAddressKey_t key = std::make_pair (address, interface);
1548  m_multicastAddresses[key]++;
1549 }
1550 
1552 {
1554 
1555  if (!address.IsMulticast ())
1556  {
1557  NS_LOG_WARN ("Not adding a non-multicast address " << address);
1558  return;
1559  }
1560 
1562 }
1563 
1565 {
1566  NS_LOG_FUNCTION (address << interface);
1567 
1568  Ipv6RegisteredMulticastAddressKey_t key = std::make_pair (address, interface);
1569 
1570  m_multicastAddresses[key]--;
1571  if (m_multicastAddresses[key] == 0)
1572  {
1573  m_multicastAddresses.erase (key);
1574  }
1575 }
1576 
1578 {
1580 
1583  {
1585  }
1586 }
1587 
1589 {
1590  NS_LOG_FUNCTION (address << interface);
1591 
1592  Ipv6RegisteredMulticastAddressKey_t key = std::make_pair (address, interface);
1594 
1595  if (iter == m_multicastAddresses.end ())
1596  {
1597  return false;
1598  }
1599  return true;
1600 }
1601 
1603 {
1605 
1607 
1608  if (iter == m_multicastAddressesNoInterface.end ())
1609  {
1610  return false;
1611  }
1612  return true;
1613 }
1614 
1615 } /* namespace ns3 */
1616 
void SetNode(Ptr< Node > node)
Set the node associated with this socket.
uint16_t GetMtu(uint32_t i) const
Get MTU for an interface.
std::pair< int, int32_t > L4ListKey_t
Container of the IPv6 L4 keys: protocol number, interface index.
uint32_t RemoveHeader(Header &header)
Deserialize and remove the header from the internal buffer.
Definition: packet.cc:280
static bool IsMatchingType(const Address &address)
void SetPayloadLength(uint16_t len)
Set the "Payload length" field.
Definition: ipv6-header.cc:65
static Ipv6Address GetLoopback()
Get the loopback address.
Ipv6Header BuildHeader(Ipv6Address src, Ipv6Address dst, uint8_t protocol, uint16_t payloadSize, uint8_t hopLimit, uint8_t tclass)
Construct an IPv6 header.
uint16_t GetPayloadLength(void) const
Get the "Payload length" field.
Definition: ipv6-header.cc:70
void SetForwarding(uint32_t i, bool val)
Enable or disable forwarding on interface.
Ipv6Address GetAddress() const
Get the IPv6 address.
Packet header for IPv6.
Definition: ipv6-header.h:34
bool AddAddress(Ipv6InterfaceAddress iface)
Add an IPv6 address.
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:73
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by "...
uint16_t GetMetric(uint32_t i) const
Get metric for an interface.
std::map< Ipv6RegisteredMulticastAddressKey_t, uint32_t >::const_iterator Ipv6RegisteredMulticastAddressCIter_t
Container Const Iterator of the IPv6 multicast addresses.
virtual ~Ipv6L3Protocol()
Destructor.
Ptr< Ipv6RoutingProtocol > GetRoutingProtocol() const
Get current routing protocol used.
void SetUp()
Enable this interface.
AttributeValue implementation for Boolean.
Definition: boolean.h:36
Ipv6InterfaceAddress GetLinkLocalAddress() const
Get link-local address from IPv6 interface.
Ipv6L3Protocol()
Constructor.
virtual void SetPmtu(Ipv6Address dst, uint32_t pmtu)
Set the Path MTU for the specified IPv6 destination address.
bool IsUp(uint32_t i) const
Is specified interface up ?
uint32_t GetId(void) const
Definition: node.cc:107
This class implements a tag that carries the socket-specific HOPLIMIT of a packet to the IPv6 layer...
Definition: socket.h:1163
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:45
Ptr< NetDevice > GetNetDevice(uint32_t i)
Get device by index.
bool AddAddress(uint32_t i, Ipv6InterfaceAddress address)
Add an address on interface.
Ptr< Ipv6RoutingProtocol > m_routingProtocol
Routing protocol.
uint32_t GetSize(void) const
Returns the the size in bytes of the packet (including the zero-filled initial payload).
Definition: packet.h:852
NS_ASSERT_MSG(false, "Ipv4AddressGenerator::MaskToIndex(): Impossible")
Access to the IPv6 forwarding table, interfaces, and configuration.
Definition: ipv6.h:81
bool IsRegisteredMulticastAddress(Ipv6Address address) const
Checks if the address has been registered.
Introspection did not find any typical Config paths.
static Mac16Address ConvertFrom(const Address &address)
std::map< Ipv6Address, uint32_t >::const_iterator Ipv6RegisteredMulticastAddressNoInterfaceCIter_t
Container Const Iterator of the IPv6 multicast addresses.
static bool IsMatchingType(const Address &address)
Ptr< NetDevice > GetDevice(uint32_t index) const
Retrieve the index-th NetDevice associated to this node.
Definition: node.cc:142
uint32_t AddIpv6Interface(Ptr< Ipv6Interface > interface)
Add an IPv6 interface to the stack.
virtual void Send(Ptr< Packet > packet, Ipv6Address source, Ipv6Address destination, uint8_t protocol, Ptr< Ipv6Route > route)
Higher-level layers call this method to send a packet down the stack to the MAC and PHY layers...
IPv6 layer implementation.
Ptr< const AttributeAccessor > MakeBooleanAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: boolean.h:84
Demultiplexes IPv6 extensions.
void AggregateObject(Ptr< Object > other)
Aggregate two Objects together.
Definition: object.cc:252
uint8_t GetTclass(void) const
Get the tag&#39;s Tclass.
Definition: socket.cc:906
Interface is down so can not send packet.
Ptr< const AttributeAccessor > MakeObjectVectorAccessor(U T::*memberVariable)
MakeAccessorHelper implementation for ObjectVector.
Definition: object-vector.h:81
void SetNode(Ptr< Node > node)
Set the node.
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file...
Definition: assert.h:67
U * PeekPointer(const Ptr< U > &p)
Definition: ptr.h:564
static Ipv6Address GetAny()
Get the "any" (::) Ipv6Address.
static Ipv6Address MakeAutoconfiguredAddress(Mac16Address addr, Ipv6Address prefix)
Make the autoconfigured IPv6 address with Mac16Address.
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:204
IPv6 address associated with an interface.
Link-local address (fe80::/64)
void SetNextHeader(uint8_t next)
Set the "Next header" field.
Definition: ipv6-header.cc:75
void Receive(Ptr< NetDevice > device, Ptr< const Packet > p, uint16_t protocol, const Address &from, const Address &to, NetDevice::PacketType packetType)
Receive method when a packet arrive in the stack.
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:280
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
Definition: fatal-error.h:162
virtual Ptr< NetDevice > GetDevice() const
Get the NetDevice.
int32_t GetInterfaceForPrefix(Ipv6Address addr, Ipv6Prefix mask) const
Get interface index which match specified address/prefix.
virtual void DoDispose(void)
Destructor implementation.
Definition: object.cc:346
#define NS_LOG_FUNCTION_NOARGS()
Output the name of the function.
virtual void Receive(Ptr< NetDevice > device, Ptr< const Packet > p, uint16_t protocol, const Address &from, const Address &to, NetDevice::PacketType packetType)
Called by NetDevices, incoming packet.
Ptr< Ipv6Interface > GetInterface(uint32_t i) const
Get an interface.
virtual void DoDispose()
Dispose object.
void SetMetric(uint32_t i, uint16_t metric)
Set metric for an interface.
virtual int GetProtocolNumber(void) const =0
Returns the protocol number of this protocol.
bool ForwardUp(Ptr< const Packet > p, Ipv6Header hdr, Ptr< NetDevice > device)
Forward up to receive method.
uint32_t AddInterface(Ptr< NetDevice > device)
Add IPv6 interface for a device.
SocketErrno
Enumeration of the possible errors returned by a socket.
Definition: socket.h:82
Ptr< Node > m_node
Node attached to stack.
TracedCallback< const Ipv6Header &, Ptr< const Packet >, uint32_t > m_localDeliverTrace
Trace of locally delivered packets.
std::pair< Ipv6Address, uint64_t > Ipv6RegisteredMulticastAddressKey_t
IPv6 multicast addresses / interface key.
void CallTxTrace(const Ipv6Header &ipHeader, Ptr< Packet > packet, Ptr< Ipv6 > ipv6, uint32_t interface)
Make a copy of the packet, add the header and invoke the TX trace callback.
void AddMulticastAddress(Ipv6Address address)
Adds a multicast address to the list of addresses to pass to local deliver.
a polymophic address class
Definition: address.h:90
virtual void SetIpForward(bool forward)
Set IPv6 forwarding state.
Ptr< const TraceSourceAccessor > MakeTraceSourceAccessor(T a)
Create a TraceSourceAccessor which will control access to the underlying trace source.
virtual void NotifyNewAggregate()
Notify other components connected to the node that a new stack member is now connected.
Ptr< Icmpv6L4Protocol > GetIcmpv6() const
Get ICMPv6 protocol.
uint32_t m_nInterfaces
Number of IPv6 interfaces managed by the stack.
void SetDefaultTclass(uint8_t tclass)
Set the default TCLASS.
The IPv6 representation of a network interface.
void Send(Ptr< Packet > p, const Ipv6Header &hdr, Ipv6Address dest)
Send a packet through this interface.
bool m_strongEndSystemModel
Rejects packets directed to an interface with wrong address (RFC 1222).
void SetMetric(uint16_t metric)
Set the metric.
void RemoveAtStart(uint32_t size)
Remove size bytes from the start of the current packet.
Definition: packet.cc:362
bool IsEqual(const Ipv6Address &other) const
Comparison operation between two Ipv6Addresses.
virtual bool GetSendIcmpv6Redirect() const
Get the ICMPv6 Redirect sending state.
virtual Ptr< IpL4Protocol > GetProtocol(int protocolNumber) const
Get L4 protocol by protocol number.
bool IsDocumentation() const
If the IPv6 address is a documentation address (2001:DB8::/32).
Ptr< Socket > CreateRawSocket()
Create raw IPv6 socket.
#define IPV6_MIN_MTU
Minimum IPv6 MTU, as defined by RFC 2460
Hold an unsigned integer type.
Definition: uinteger.h:44
L4List_t m_protocols
List of transport protocol.
Ipv6InterfaceAddress GetAddress(uint32_t interfaceIndex, uint32_t addressIndex) const
Get an address.
void SetDefaultTtl(uint8_t ttl)
Set the default TTL.
static Ipv6Address GetZero()
Get the 0 (::) Ipv6Address.
bool IsUp() const
Is the interface UP ?
void IpMulticastForward(Ptr< const NetDevice > idev, Ptr< Ipv6MulticastRoute > mrtentry, Ptr< const Packet > p, const Ipv6Header &header)
Forward a multicast packet.
void RemoveMulticastAddress(Ipv6Address address)
Removes a multicast address from the list of addresses to pass to local deliver.
virtual uint32_t GetSerializedSize(void) const
Get the serialized size of the packet.
Definition: ipv6-header.cc:143
indicates whether the socket has a priority set.
Definition: socket.h:1307
bool IsLinkLocal() const
If the IPv6 address is a link-local address (fe80::/64).
void SetUp(uint32_t i)
Set an interface up.
An implementation of the ICMPv6 protocol.
Callback< R > MakeCallback(R(T::*memPtr)(void), OBJ objPtr)
Definition: callback.h:1489
virtual enum RxStatus Receive(Ptr< Packet > p, Ipv4Header const &header, Ptr< Ipv4Interface > incomingInterface)=0
Called from lower-level layers to send the packet up in the stack.
virtual void ReportDrop(Ipv6Header ipHeader, Ptr< Packet > p, DropReason dropReason)
Report a packet drop.
static TypeId GetTypeId()
Get the type ID of this class.
Ipv6InterfaceList m_interfaces
List of IPv6 interfaces.
Ipv6Address GetSourceAddress(void) const
Get the "Source address" field.
Definition: ipv6-header.cc:100
bool m_ipForward
Forwarding packets (i.e.
TracedCallback< const Ipv6Header &, Ptr< const Packet >, uint32_t > m_unicastForwardTrace
Trace of unicast forwarded packets.
static Mac48Address ConvertFrom(const Address &address)
void SetForwarding(bool forward)
Set forwarding enabled or not.
Ptr< T > GetObject(void) const
Get a pointer to the requested aggregated Object.
Definition: object.h:459
std::list< Ptr< Ipv6AutoconfiguredPrefix > >::iterator Ipv6AutoconfiguredPrefixListI
Iterator of the container of the IPv6 Autoconfigured addresses.
Ipv6RegisteredMulticastAddress_t m_multicastAddresses
List of multicast IP addresses of interest, divided per interface.
bool IsAllRoutersMulticast() const
If the IPv6 address is "all routers multicast" (ff02::2/8).
Ipv6AutoconfiguredPrefixList m_prefixes
List of IPv6 prefix received from RA.
bool IsMulticast() const
If the IPv6 address is multicast (ff00::/8).
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void LocalDeliver(Ptr< const Packet > p, Ipv6Header const &ip, uint32_t iif)
Deliver a packet.
bool IsAllNodesMulticast() const
If the IPv6 address is "all nodes multicast" (ff02::1/8).
void DeleteRawSocket(Ptr< Socket > socket)
Remove raw IPv6 socket.
address
Definition: first.py:37
Ptr< const AttributeChecker > MakeBooleanChecker(void)
Definition: boolean.cc:121
static uint16_t GetStaticProtocolNumber()
Get ICMPv6 protocol number.
Ipv6Address SourceAddressSelection(uint32_t interface, Ipv6Address dest)
Choose the source address to use with destination address.
void IpForward(Ptr< const NetDevice > idev, Ptr< Ipv6Route > rtentry, Ptr< const Packet > p, const Ipv6Header &header)
Forward a packet.
Ptr< Packet > Copy(void) const
performs a COW copy of the packet.
Definition: packet.cc:121
void RemoveAtEnd(uint32_t size)
Remove size bytes from the end of the current packet.
Definition: packet.cc:355
uint8_t m_defaultTtl
Default TTL for outgoing packets.
indicates whether the socket has IPV6_TCLASS set.
Definition: socket.h:1354
TracedCallback< const Ipv6Header &, Ptr< const Packet >, DropReason, Ptr< Ipv6 >, uint32_t > m_dropTrace
Callback to trace drop packets.
TracedCallback< Ptr< const Packet >, Ptr< Ipv6 >, uint32_t > m_rxTrace
Callback to trace RX (reception) packets.
uint8_t GetNextHeader(void) const
Get the next header.
Definition: ipv6-header.cc:80
uint32_t GetNAddresses(void) const
Get number of addresses on this IPv6 interface.
Ipv6InterfaceAddress GetAddress(uint32_t index) const
Get an address from IPv6 interface.
void SetNode(Ptr< Node > node)
Set node associated with this stack.
Ipv6InterfaceReverseContainer m_reverseInterfacesContainer
Container of NetDevice / Interface index associations.
uint32_t GetNInterfaces() const
Get current number of interface on this stack.
NS_LOG_LOGIC("Net device "<< nd<< " is not bridged")
void RemoveAutoconfiguredAddress(uint32_t interface, Ipv6Address network, Ipv6Prefix mask, Ipv6Address defaultRouter)
Remove an autoconfigured address.
void SendRealOut(Ptr< Ipv6Route > route, Ptr< Packet > packet, Ipv6Header const &ipHeader)
Send packet with route.
void RegisterProtocolHandler(ProtocolHandler handler, uint16_t protocolType, Ptr< NetDevice > device, bool promiscuous=false)
Definition: node.cc:227
void UpdateReachableTimer()
Update the reachable timer.
Definition: ndisc-cache.cc:431
bool IsLinkLocalMulticast() const
If the IPv6 address is link-local multicast (ff02::/16).
void SetupLoopback()
Setup loopback interface.
std::list< NdiscCache::Entry * > LookupInverse(Address dst)
Lookup in the cache for a MAC address.
Definition: ndisc-cache.cc:107
void SetSourceAddress(Ipv6Address src)
Set the "Source address" field.
Definition: ipv6-header.cc:95
IPv6 Extension Fragment.
double max(double x, double y)
virtual void RegisterExtensions()
Register the IPv6 Extensions.
virtual bool GetMtuDiscover(void) const
Get IPv6 MTU discover state.
Describes an IPv6 address.
Definition: ipv6-address.h:49
void SetRoutingProtocol(Ptr< Ipv6RoutingProtocol > routingProtocol)
Set routing protocol for this stack.
uint16_t GetMetric() const
Get the metric.
bool IsForwarding(uint32_t i) const
Is interface allows forwarding ?
NdiscCache::Entry * Lookup(Ipv6Address dst)
Lookup in the cache.
Definition: ndisc-cache.cc:93
void SetHopLimit(uint8_t limit)
Set the "Hop limit" field (TTL).
Definition: ipv6-header.cc:85
uint32_t AddDevice(Ptr< NetDevice > device)
Associate a NetDevice to this node.
Definition: node.cc:128
static Mac64Address ConvertFrom(const Address &address)
#define NS_LOG_WARN(msg)
Use NS_LOG to output a message of level LOG_WARN.
Definition: log.h:264
uint32_t CopyData(uint8_t *buffer, uint32_t size) const
Copy the packet contents to a byte buffer.
Definition: packet.cc:378
bool RemovePacketTag(Tag &tag)
Remove a packet tag.
Definition: packet.cc:870
virtual void Insert(Ptr< IpL4Protocol > protocol)
Add a L4 protocol.
Ipv6RegisteredMulticastAddressNoInterface_t m_multicastAddressesNoInterface
List of multicast IP addresses of interest for all the interfaces.
virtual bool GetIpForward() const
Get IPv6 forwarding state.
bool m_sendIcmpv6Redirect
Allow ICMPv6 Redirect sending state.
int32_t GetInterfaceForDevice(Ptr< const NetDevice > device) const
Get interface index which is on a specified net device.
virtual void RegisterOptions()
Register the IPv6 Options.
TracedCallback< const Ipv6Header &, Ptr< const Packet >, uint32_t > m_sendOutgoingTrace
Trace of sent packets.
Describes an IPv6 prefix.
Definition: ipv6-address.h:428
void SetDown(uint32_t i)
set an interface down.
Ptr< T > CreateObject(void)
Create an object by type, with varying number of constructor parameters.
Definition: object.h:528
void SetTrafficClass(uint8_t traffic)
Set the "Traffic class" field.
Definition: ipv6-header.cc:45
A record that holds information about a NdiscCache entry.
Definition: ndisc-cache.h:156
uint32_t GetNAddresses(uint32_t interface) const
Get number of address for an interface.
RxStatus
Rx status codes.
bool m_mtuDiscover
MTU Discover (i.e.
virtual void NotifyNewAggregate(void)
Notify all Objects aggregated to this one of a new Object being aggregated.
Definition: object.cc:325
bool RemoveAddress(uint32_t interfaceIndex, uint32_t addressIndex)
Remove an address from an interface.
PacketType
Packet types are used as they are in Linux.
Definition: net-device.h:296
Container for a set of ns3::Object pointers.
Ptr< Ipv6PmtuCache > m_pmtuCache
Path MTU Cache.
uint8_t GetHopLimit(void) const
Get the "Hop limit" field (TTL).
Definition: ipv6-header.cc:90
static bool IsMatchingType(const Address &address)
Ipv6Address GetDestinationAddress(void) const
Get the "Destination address" field.
Definition: ipv6-header.cc:110
int32_t GetInterfaceForAddress(Ipv6Address addr) const
Get interface index which has specified IPv6 address.
TracedCallback< Ptr< const Packet >, Ptr< Ipv6 >, uint32_t > m_txTrace
Callback to trace TX (transmission) packets.
virtual void SetMtuDiscover(bool mtuDiscover)
Set IPv6 MTU discover state.
uint8_t m_defaultTclass
Default TCLASS for outgoing packets.
Ptr< const AttributeAccessor > MakeUintegerAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: uinteger.h:45
void SetDown()
Disable this interface.
a unique identifier for an interface.
Definition: type-id.h:58
void StartPreferredTimer()
Start the preferred timer.
uint8_t GetHopLimit(void) const
Get the tag&#39;s Hop Limit.
Definition: socket.cc:671
void SetDestinationAddress(Ipv6Address dst)
Set the "Destination address" field.
Definition: ipv6-header.cc:105
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:915
SocketList m_sockets
List of IPv6 raw sockets.
static const uint16_t PROT_NUMBER
The protocol number for IPv6 (0x86DD).
void AddHeader(const Header &header)
Add header to this packet.
Definition: packet.cc:256
uint32_t GetNDevices(void) const
Definition: node.cc:150
bool IsAny() const
If the IPv6 address is the "Any" address.
virtual void Remove(Ptr< IpL4Protocol > protocol)
Remove a L4 protocol.
void AddAutoconfiguredAddress(uint32_t interface, Ipv6Address network, Ipv6Prefix mask, uint8_t flags, uint32_t validTime, uint32_t preferredTime, Ipv6Address defaultRouter=Ipv6Address::GetZero())
Add an autoconfigured address with RA information.
DropReason
Reason why a packet has been dropped.
virtual void SetSendIcmpv6Redirect(bool sendIcmpv6Redirect)
Set the ICMPv6 Redirect sending state.
void RouteInputError(Ptr< const Packet > p, const Ipv6Header &ipHeader, Socket::SocketErrno sockErrno)
Fallback when no route is found.