Add TapNetDevice (formerly known as VirtualNetDevice)
authorGustavo J. A. M. Carneiro <gjc@inescporto.pt>
Sun May 24 16:18:20 2009 +0100 (8 months ago)
changeset 4551dee7215f0334
parent 4457 1b45505f9a52
child 4552 118338cd9f61
Add TapNetDevice (formerly known as VirtualNetDevice)
src/devices/tap-net-device/tap-net-device.cc
src/devices/tap-net-device/tap-net-device.h
src/devices/tap-net-device/waf
src/devices/tap-net-device/wscript
src/wscript
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/src/devices/tap-net-device/tap-net-device.cc	Sun May 24 16:18:20 2009 +0100
     1.3 @@ -0,0 +1,271 @@
     1.4 +/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
     1.5 +/*
     1.6 + * Copyright (c) 2008,2009 INESC Porto
     1.7 + *
     1.8 + * This program is free software; you can redistribute it and/or modify
     1.9 + * it under the terms of the GNU General Public License version 2 as
    1.10 + * published by the Free Software Foundation;
    1.11 + *
    1.12 + * This program is distributed in the hope that it will be useful,
    1.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    1.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    1.15 + * GNU General Public License for more details.
    1.16 + *
    1.17 + * You should have received a copy of the GNU General Public License
    1.18 + * along with this program; if not, write to the Free Software
    1.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    1.20 + *
    1.21 + * Author:  Gustavo J. A. M. Carneiro  <gjc@inescporto.pt>
    1.22 + */
    1.23 +
    1.24 +#include "ns3/log.h"
    1.25 +#include "ns3/queue.h"
    1.26 +#include "ns3/simulator.h"
    1.27 +#include "ns3/mac48-address.h"
    1.28 +#include "ns3/llc-snap-header.h"
    1.29 +#include "ns3/error-model.h"
    1.30 +#include "tap-net-device.h"
    1.31 +#include "ns3/channel.h"
    1.32 +#include "ns3/trace-source-accessor.h"
    1.33 +
    1.34 +
    1.35 +NS_LOG_COMPONENT_DEFINE ("TapNetDevice");
    1.36 +
    1.37 +namespace ns3 {
    1.38 +
    1.39 +NS_OBJECT_ENSURE_REGISTERED (TapNetDevice);
    1.40 +
    1.41 +TypeId
    1.42 +TapNetDevice::GetTypeId (void)
    1.43 +{
    1.44 +  static TypeId tid = TypeId ("ns3::TapNetDevice")
    1.45 +    .SetParent<NetDevice> ()
    1.46 +    .AddConstructor<TapNetDevice> ()
    1.47 +    .AddTraceSource ("Rx", "Received payload from the MAC layer.",
    1.48 +                     MakeTraceSourceAccessor (&TapNetDevice::m_rxTrace))
    1.49 +    .AddTraceSource ("Tx", "Send payload to the MAC layer.",
    1.50 +                     MakeTraceSourceAccessor (&TapNetDevice::m_txTrace))
    1.51 +    ;
    1.52 +  return tid;
    1.53 +}
    1.54 +
    1.55 +TapNetDevice::TapNetDevice ()
    1.56 +{
    1.57 +  m_needsArp = false;
    1.58 +  m_supportsSendFrom = true;
    1.59 +  m_mtu = 65535;
    1.60 +}
    1.61 +
    1.62 +
    1.63 +void
    1.64 +TapNetDevice::SetSendFromCallback (SendFromCallback sendCb)
    1.65 +{
    1.66 +  m_sendCb = sendCb;
    1.67 +}
    1.68 +
    1.69 +void
    1.70 +TapNetDevice::SetNeedsArp (bool needsArp)
    1.71 +{
    1.72 +  m_needsArp = needsArp;
    1.73 +}
    1.74 +
    1.75 +void
    1.76 +TapNetDevice::SetSupportsSendFrom (bool supportsSendFrom)
    1.77 +{
    1.78 +  m_supportsSendFrom = supportsSendFrom;
    1.79 +}
    1.80 +
    1.81 +bool
    1.82 +TapNetDevice::SetMtu (const uint16_t mtu)
    1.83 +{
    1.84 +  m_mtu = mtu;
    1.85 +  return true;
    1.86 +}
    1.87 +
    1.88 +
    1.89 +TapNetDevice::~TapNetDevice()
    1.90 +{
    1.91 +  NS_LOG_FUNCTION_NOARGS ();
    1.92 +}
    1.93 +
    1.94 +
    1.95 +void TapNetDevice::DoDispose()
    1.96 +{
    1.97 +  NS_LOG_FUNCTION_NOARGS ();
    1.98 +  NetDevice::DoDispose ();
    1.99 +}
   1.100 +
   1.101 +bool
   1.102 +TapNetDevice::Receive (Ptr<Packet> packet, uint16_t protocol, const Address &address)
   1.103 +{
   1.104 +  if (m_rxCallback (this, packet, protocol, address))
   1.105 +    {
   1.106 +      m_rxTrace (packet);
   1.107 +      return true;
   1.108 +    }
   1.109 +  return false;
   1.110 +}
   1.111 +
   1.112 +bool
   1.113 +TapNetDevice::PromiscReceive (Ptr<Packet> packet, uint16_t protocol,
   1.114 +                              const Address &source, const Address &destination,
   1.115 +                              PacketType packetType)
   1.116 +{
   1.117 +  if (m_promiscRxCallback (this, packet, protocol, source, destination, packetType))
   1.118 +    {
   1.119 +      m_rxTrace (packet);
   1.120 +      return true;
   1.121 +    }
   1.122 +  return false;
   1.123 +}
   1.124 +
   1.125 +
   1.126 +void
   1.127 +TapNetDevice::SetName (const std::string name)
   1.128 +{
   1.129 +  m_name = name;
   1.130 +}
   1.131 +
   1.132 +std::string
   1.133 +TapNetDevice::GetName (void) const
   1.134 +{
   1.135 +  return m_name;
   1.136 +}
   1.137 +
   1.138 +void
   1.139 +TapNetDevice::SetIfIndex (const uint32_t index)
   1.140 +{
   1.141 +  m_index = index;
   1.142 +}
   1.143 +
   1.144 +uint32_t
   1.145 +TapNetDevice::GetIfIndex (void) const
   1.146 +{
   1.147 +  return m_index;
   1.148 +}
   1.149 +
   1.150 +Ptr<Channel>
   1.151 +TapNetDevice::GetChannel (void) const
   1.152 +{
   1.153 +  return Ptr<Channel> ();
   1.154 +}
   1.155 +
   1.156 +Address
   1.157 +TapNetDevice::GetAddress (void) const
   1.158 +{
   1.159 +  return Mac48Address ();
   1.160 +}
   1.161 +
   1.162 +uint16_t
   1.163 +TapNetDevice::GetMtu (void) const
   1.164 +{
   1.165 +  return m_mtu;
   1.166 +}
   1.167 +
   1.168 +bool
   1.169 +TapNetDevice::IsLinkUp (void) const
   1.170 +{
   1.171 +  return true;
   1.172 +}
   1.173 +
   1.174 +void
   1.175 +TapNetDevice::SetLinkChangeCallback (Callback<void> callback)
   1.176 +{
   1.177 +}
   1.178 +
   1.179 +bool
   1.180 +TapNetDevice::IsBroadcast (void) const
   1.181 +{
   1.182 +  return m_needsArp;
   1.183 +}
   1.184 +
   1.185 +Address
   1.186 +TapNetDevice::GetBroadcast (void) const
   1.187 +{
   1.188 +  return Mac48Address ("ff:ff:ff:ff:ff:ff");
   1.189 +}
   1.190 +
   1.191 +bool
   1.192 +TapNetDevice::IsMulticast (void) const
   1.193 +{
   1.194 +  return false;
   1.195 +}
   1.196 +
   1.197 +Address TapNetDevice::GetMulticast (Ipv4Address multicastGroup) const
   1.198 +{
   1.199 +  return Mac48Address ("ff:ff:ff:ff:ff:ff");
   1.200 +}
   1.201 +
   1.202 +Address TapNetDevice::GetMulticast (Ipv6Address addr) const
   1.203 +{
   1.204 +  return Mac48Address ("ff:ff:ff:ff:ff:ff");  
   1.205 +}
   1.206 +
   1.207 +
   1.208 +bool
   1.209 +TapNetDevice::IsPointToPoint (void) const
   1.210 +{
   1.211 +  return true;
   1.212 +}
   1.213 +
   1.214 +bool
   1.215 +TapNetDevice::Send (Ptr<Packet> packet, const Address& dest, uint16_t protocolNumber)
   1.216 +{
   1.217 +  return SendFrom (packet, GetAddress (), dest, protocolNumber);
   1.218 +}
   1.219 +
   1.220 +bool
   1.221 +TapNetDevice::SendFrom (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber)
   1.222 +{
   1.223 +  NS_FATAL_ERROR ("not implemented");
   1.224 +  if (m_sendCb (packet, source, dest, protocolNumber))
   1.225 +    {
   1.226 +      m_txTrace (packet);
   1.227 +      return true;
   1.228 +    }
   1.229 +  return false;
   1.230 +}
   1.231 +
   1.232 +Ptr<Node>
   1.233 +TapNetDevice::GetNode (void) const
   1.234 +{
   1.235 +  return m_node;
   1.236 +}
   1.237 +
   1.238 +void
   1.239 +TapNetDevice::SetNode (Ptr<Node> node)
   1.240 +{
   1.241 +  m_node = node;
   1.242 +}
   1.243 +
   1.244 +bool
   1.245 +TapNetDevice::NeedsArp (void) const
   1.246 +{
   1.247 +  return m_needsArp;
   1.248 +}
   1.249 +
   1.250 +void
   1.251 +TapNetDevice::SetReceiveCallback (NetDevice::ReceiveCallback cb)
   1.252 +{
   1.253 +  m_rxCallback = cb;
   1.254 +}
   1.255 +
   1.256 +void
   1.257 +TapNetDevice::SetPromiscReceiveCallback (NetDevice::PromiscReceiveCallback cb)
   1.258 +{
   1.259 +  m_promiscRxCallback = cb;
   1.260 +}
   1.261 +
   1.262 +bool
   1.263 +TapNetDevice::SupportsSendFrom () const
   1.264 +{
   1.265 +  return m_supportsSendFrom;
   1.266 +}
   1.267 +
   1.268 +bool TapNetDevice::IsBridge (void) const
   1.269 +{
   1.270 +  return false;
   1.271 +}
   1.272 +
   1.273 +
   1.274 +} // namespace ns3
     2.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     2.2 +++ b/src/devices/tap-net-device/tap-net-device.h	Sun May 24 16:18:20 2009 +0100
     2.3 @@ -0,0 +1,166 @@
     2.4 +/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
     2.5 +/*
     2.6 + * Copyright (c) 2008,2009 INESC Porto
     2.7 + *
     2.8 + * This program is free software; you can redistribute it and/or modify
     2.9 + * it under the terms of the GNU General Public License version 2 as
    2.10 + * published by the Free Software Foundation;
    2.11 + *
    2.12 + * This program is distributed in the hope that it will be useful,
    2.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
    2.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    2.15 + * GNU General Public License for more details.
    2.16 + *
    2.17 + * You should have received a copy of the GNU General Public License
    2.18 + * along with this program; if not, write to the Free Software
    2.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
    2.20 + *
    2.21 + * Author: Gustavo J. A. M. Carneiro  <gjc@inescporto.pt>
    2.22 + */
    2.23 +
    2.24 +#ifndef TAP_NET_DEVICE_H
    2.25 +#define TAP_NET_DEVICE_H
    2.26 +
    2.27 +#include "ns3/address.h"
    2.28 +#include "ns3/node.h"
    2.29 +#include "ns3/net-device.h"
    2.30 +#include "ns3/callback.h"
    2.31 +#include "ns3/packet.h"
    2.32 +#include "ns3/ptr.h"
    2.33 +#include "ns3/traced-callback.h"
    2.34 +
    2.35 +namespace ns3 {
    2.36 +
    2.37 +
    2.38 +/**
    2.39 + * \class TapNetDevice
    2.40 + * \brief A virtual device, similar to Linux TAP interfaces.
    2.41 + *
    2.42 + * A TapNetDevice is a "virtual" NetDevice implementation which
    2.43 + * delegates to a user callback (see method SetSendFromCallback()) the
    2.44 + * task of actually transmitting a packet.  It also allows the user
    2.45 + * code to inject the packet as if it had been received by the
    2.46 + * TapNetDevice.  Together, these features allow one to build tunnels.
    2.47 + * For instance, by transmitting packets into a UDP socket we end up
    2.48 + * building an IP-over-UDP-over-IP tunnel.
    2.49 + *
    2.50 + * The same thing could be accomplished by subclassing NetDevice
    2.51 + * directly.  However, TapNetDevice is usually much simpler to program
    2.52 + * than a NetDevice subclass.
    2.53 + */
    2.54 +class TapNetDevice : public NetDevice
    2.55 +{
    2.56 +public:
    2.57 +  typedef Callback<bool, Ptr<Packet>, const Address&, const Address&, uint16_t> SendFromCallback;
    2.58 +
    2.59 +  static TypeId GetTypeId (void);
    2.60 +  TapNetDevice ();
    2.61 +
    2.62 +  virtual ~TapNetDevice ();
    2.63 +
    2.64 +  /**
    2.65 +   * \brief Set the user callback to be called when a L2 packet is to be transmitted
    2.66 +   * \param transmitCb the new transmit callback
    2.67 +   */
    2.68 +  void SetSendFromCallback (SendFromCallback transmitCb);
    2.69 +
    2.70 +  /**
    2.71 +   * \brief Configure whether the virtual device needs ARP
    2.72 +   *
    2.73 +   * \param needsArp the the 'needs arp' value that will be returned
    2.74 +   * by the NeedsArp() method.  The method IsBroadcast() will also
    2.75 +   * return this value.
    2.76 +   */
    2.77 +  void SetNeedsArp (bool needsArp);
    2.78 +
    2.79 +  /**
    2.80 +   * \brief Configure whether the virtual device supports SendFrom
    2.81 +   */
    2.82 +  void SetSupportsSendFrom (bool supportsSendFrom);
    2.83 +
    2.84 +  /**
    2.85 +   * \brief Configure the reported MTU for the virtual device. The
    2.86 +   * default value is 65535.
    2.87 +   * \return whether the MTU value was within legal bounds
    2.88 +   */
    2.89 +  bool SetMtu (const uint16_t mtu);
    2.90 +
    2.91 +
    2.92 +  /**
    2.93 +   * \param p packet sent from below up to Network Device
    2.94 +   * \param protocol Protocol type
    2.95 +   * \param source the address of the sender of this packet.
    2.96 +   * \returns true if the packet was forwarded successfully,
    2.97 +   *          false otherwise.
    2.98 +   *
    2.99 +   * Forward a "virtually received" packet up the node's protocol
   2.100 +   * stack.
   2.101 +   */
   2.102 +  bool Receive (Ptr<Packet> packet, uint16_t protocol, const Address &source);
   2.103 +
   2.104 +
   2.105 +  /**
   2.106 +   * \param p packet sent from below up to Network Device
   2.107 +   * \param protocol Protocol type
   2.108 +   * \param source the address of the sender of this packet.
   2.109 +   * \param destination the address of the receiver of this packet.
   2.110 +   * \param packetType type of packet received (broadcast/multicast/unicast/otherhost)
   2.111 +   * \returns true if the packet was forwarded successfully, false otherwise.
   2.112 +   *
   2.113 +   * Forward a "virtually received (in promiscuous mode)" packet up
   2.114 +   * the node's protocol stack.
   2.115 +   */
   2.116 +  bool PromiscReceive (Ptr<Packet> packet, uint16_t protocol,
   2.117 +                       const Address &source, const Address &destination,
   2.118 +                       PacketType packetType);
   2.119 +
   2.120 +
   2.121 +  // inherited from NetDevice base class.
   2.122 +  virtual void SetName(const std::string name);
   2.123 +  virtual std::string GetName(void) const;
   2.124 +  virtual void SetIfIndex(const uint32_t index);
   2.125 +  virtual uint32_t GetIfIndex(void) const;
   2.126 +  virtual Ptr<Channel> GetChannel (void) const;
   2.127 +  virtual Address GetAddress (void) const;
   2.128 +  virtual uint16_t GetMtu (void) const;
   2.129 +  virtual bool IsLinkUp (void) const;
   2.130 +  virtual void SetLinkChangeCallback (Callback<void> callback);
   2.131 +  virtual bool IsBroadcast (void) const;
   2.132 +  virtual Address GetBroadcast (void) const;
   2.133 +  virtual bool IsMulticast (void) const;
   2.134 +  virtual Address GetMulticast (Ipv4Address multicastGroup) const;
   2.135 +  virtual Address GetMulticast (Ipv6Address addr) const;
   2.136 +  virtual bool IsPointToPoint (void) const;
   2.137 +  virtual bool Send (Ptr<Packet> packet, const Address& dest, uint16_t protocolNumber);
   2.138 +  virtual bool SendFrom (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber);
   2.139 +  virtual Ptr<Node> GetNode (void) const;
   2.140 +  virtual void SetNode (Ptr<Node> node);
   2.141 +  virtual bool NeedsArp (void) const;
   2.142 +  virtual void SetReceiveCallback (NetDevice::ReceiveCallback cb);
   2.143 +  virtual void SetPromiscReceiveCallback (NetDevice::PromiscReceiveCallback cb);
   2.144 +  virtual bool SupportsSendFrom () const;
   2.145 +  virtual bool IsBridge (void) const;
   2.146 +
   2.147 +protected:
   2.148 +
   2.149 +  virtual void DoDispose (void);
   2.150 +
   2.151 +private:
   2.152 +
   2.153 +  SendFromCallback m_sendCb;
   2.154 +  TracedCallback<Ptr<const Packet> > m_rxTrace;
   2.155 +  TracedCallback<Ptr<const Packet> > m_txTrace;
   2.156 +  Ptr<Node> m_node;
   2.157 +  ReceiveCallback m_rxCallback;
   2.158 +  PromiscReceiveCallback m_promiscRxCallback;
   2.159 +  std::string m_name;
   2.160 +  uint32_t m_index;
   2.161 +  uint16_t m_mtu;
   2.162 +  bool m_needsArp;
   2.163 +  bool m_supportsSendFrom;
   2.164 +};
   2.165 +
   2.166 +}; // namespace ns3
   2.167 +
   2.168 +#endif
   2.169 +
     3.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     3.2 +++ b/src/devices/tap-net-device/waf	Sun May 24 16:18:20 2009 +0100
     3.3 @@ -0,0 +1,1 @@
     3.4 +exec "`dirname "$0"`"/../../../waf "$@"
     4.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     4.2 +++ b/src/devices/tap-net-device/wscript	Sun May 24 16:18:20 2009 +0100
     4.3 @@ -0,0 +1,14 @@
     4.4 +## -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
     4.5 +
     4.6 +
     4.7 +def build(bld):
     4.8 +    module = bld.create_ns3_module('tap-net-device', ['node'])
     4.9 +    module.source = [
    4.10 +        'tap-net-device.cc',
    4.11 +        ]
    4.12 +    headers = bld.new_task_gen('ns3header')
    4.13 +    headers.module = 'tap-net-device'
    4.14 +    headers.source = [
    4.15 +        'tap-net-device.h',
    4.16 +        ]
    4.17 +
     5.1 --- a/src/wscript	Sun May 24 11:39:41 2009 +0100
     5.2 +++ b/src/wscript	Sun May 24 16:18:20 2009 +0100
     5.3 @@ -23,6 +23,7 @@
     5.4      'devices/emu',
     5.5      'devices/bridge',
     5.6      'devices/tap-bridge',
     5.7 +    'devices/tap-net-device',
     5.8      'applications/onoff',
     5.9      'applications/packet-sink',
    5.10      'applications/udp-echo',