A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
bridge-net-device.cc
Go to the documentation of this file.
1/*
2 * SPDX-License-Identifier: GPL-2.0-only
3 *
4 * Author: Gustavo Carneiro <gjc@inescporto.pt>
5 */
6#include "bridge-net-device.h"
7
8#include "ns3/boolean.h"
9#include "ns3/channel.h"
10#include "ns3/log.h"
11#include "ns3/node.h"
12#include "ns3/packet.h"
13#include "ns3/simulator.h"
14#include "ns3/uinteger.h"
15
16/**
17 * \file
18 * \ingroup bridge
19 * ns3::BridgeNetDevice implementation.
20 */
21
22namespace ns3
23{
24
25NS_LOG_COMPONENT_DEFINE("BridgeNetDevice");
26
27NS_OBJECT_ENSURE_REGISTERED(BridgeNetDevice);
28
29TypeId
31{
32 static TypeId tid =
33 TypeId("ns3::BridgeNetDevice")
35 .SetGroupName("Bridge")
36 .AddConstructor<BridgeNetDevice>()
37 .AddAttribute("Mtu",
38 "The MAC-level Maximum Transmission Unit",
39 UintegerValue(1500),
42 .AddAttribute("EnableLearning",
43 "Enable the learning mode of the Learning Bridge",
44 BooleanValue(true),
47 .AddAttribute("ExpirationTime",
48 "Time it takes for learned MAC state entry to expire.",
49 TimeValue(Seconds(300)),
52 return tid;
53}
54
56 : m_node(nullptr),
57 m_ifIndex(0)
58{
61}
62
67
68void
70{
72 for (auto iter = m_ports.begin(); iter != m_ports.end(); iter++)
73 {
74 *iter = nullptr;
75 }
76 m_ports.clear();
77 m_channel = nullptr;
78 m_node = nullptr;
80}
81
82void
84 Ptr<const Packet> packet,
85 uint16_t protocol,
86 const Address& src,
87 const Address& dst,
88 PacketType packetType)
89{
91 NS_LOG_DEBUG("UID is " << packet->GetUid());
92
95
97 {
98 m_promiscRxCallback(this, packet, protocol, src, dst, packetType);
99 }
100
101 switch (packetType)
102 {
103 case PACKET_HOST:
104 if (dst48 == m_address)
105 {
106 Learn(src48, incomingPort);
107 m_rxCallback(this, packet, protocol, src);
108 }
109 break;
110
111 case PACKET_BROADCAST:
112 case PACKET_MULTICAST:
113 m_rxCallback(this, packet, protocol, src);
114 ForwardBroadcast(incomingPort, packet, protocol, src48, dst48);
115 break;
116
117 case PACKET_OTHERHOST:
118 if (dst48 == m_address)
119 {
120 Learn(src48, incomingPort);
121 m_rxCallback(this, packet, protocol, src);
122 }
123 else
124 {
125 ForwardUnicast(incomingPort, packet, protocol, src48, dst48);
126 }
127 break;
128 }
129}
130
131void
133 Ptr<const Packet> packet,
134 uint16_t protocol,
135 Mac48Address src,
136 Mac48Address dst)
137{
139 NS_LOG_DEBUG("LearningBridgeForward (incomingPort="
140 << incomingPort->GetInstanceTypeId().GetName() << ", packet=" << packet
141 << ", protocol=" << protocol << ", src=" << src << ", dst=" << dst << ")");
142
143 Learn(src, incomingPort);
144 Ptr<NetDevice> outPort = GetLearnedState(dst);
145 if (outPort && outPort != incomingPort)
146 {
147 NS_LOG_LOGIC("Learning bridge state says to use port `"
148 << outPort->GetInstanceTypeId().GetName() << "'");
149 outPort->SendFrom(packet->Copy(), src, dst, protocol);
150 }
151 else
152 {
153 NS_LOG_LOGIC("No learned state: send through all ports");
154 for (auto iter = m_ports.begin(); iter != m_ports.end(); iter++)
155 {
156 Ptr<NetDevice> port = *iter;
157 if (port != incomingPort)
158 {
159 NS_LOG_LOGIC("LearningBridgeForward ("
160 << src << " => " << dst
161 << "): " << incomingPort->GetInstanceTypeId().GetName() << " --> "
162 << port->GetInstanceTypeId().GetName() << " (UID " << packet->GetUid()
163 << ").");
164 port->SendFrom(packet->Copy(), src, dst, protocol);
165 }
166 }
167 }
168}
169
170void
172 Ptr<const Packet> packet,
173 uint16_t protocol,
174 Mac48Address src,
175 Mac48Address dst)
176{
178 NS_LOG_DEBUG("LearningBridgeForward (incomingPort="
179 << incomingPort->GetInstanceTypeId().GetName() << ", packet=" << packet
180 << ", protocol=" << protocol << ", src=" << src << ", dst=" << dst << ")");
181 Learn(src, incomingPort);
182
183 for (auto iter = m_ports.begin(); iter != m_ports.end(); iter++)
184 {
185 Ptr<NetDevice> port = *iter;
186 if (port != incomingPort)
187 {
188 NS_LOG_LOGIC("LearningBridgeForward (" << src << " => " << dst << "): "
189 << incomingPort->GetInstanceTypeId().GetName()
190 << " --> " << port->GetInstanceTypeId().GetName()
191 << " (UID " << packet->GetUid() << ").");
192 port->SendFrom(packet->Copy(), src, dst, protocol);
193 }
194 }
195}
196
197void
208
211{
214 {
215 Time now = Simulator::Now();
216 auto iter = m_learnState.find(source);
217 if (iter != m_learnState.end())
218 {
219 LearnedState& state = iter->second;
220 if (state.expirationTime > now)
221 {
222 return state.associatedPort;
223 }
224 else
225 {
226 m_learnState.erase(iter);
227 }
228 }
229 }
230 return nullptr;
231}
232
235{
237 return m_ports.size();
238}
239
246
247void
249{
251 NS_ASSERT(bridgePort != this);
252 if (!Mac48Address::IsMatchingType(bridgePort->GetAddress()))
253 {
254 NS_FATAL_ERROR("Device does not support eui 48 addresses: cannot be added to bridge.");
255 }
256 if (!bridgePort->SupportsSendFrom())
257 {
258 NS_FATAL_ERROR("Device does not support SendFrom: cannot be added to bridge.");
259 }
260 if (m_address == Mac48Address())
261 {
262 m_address = Mac48Address::ConvertFrom(bridgePort->GetAddress());
263 }
264
265 NS_LOG_DEBUG("RegisterProtocolHandler for " << bridgePort->GetInstanceTypeId().GetName());
267 0,
268 bridgePort,
269 true);
270 m_ports.push_back(bridgePort);
271 m_channel->AddChannel(bridgePort->GetChannel());
272}
273
274void
276{
278 m_ifIndex = index;
279}
280
287
294
295void
301
308
309bool
310BridgeNetDevice::SetMtu(const uint16_t mtu)
311{
313 m_mtu = mtu;
314 return true;
315}
316
317uint16_t
319{
321 return m_mtu;
322}
323
324bool
326{
328 return true;
329}
330
331void
335
336bool
338{
340 return true;
341}
342
349
350bool
352{
354 return true;
355}
356
359{
360 NS_LOG_FUNCTION(this << multicastGroup);
361 Mac48Address multicast = Mac48Address::GetMulticast(multicastGroup);
362 return multicast;
363}
364
365bool
367{
369 return false;
370}
371
372bool
374{
376 return true;
377}
378
379bool
380BridgeNetDevice::Send(Ptr<Packet> packet, const Address& dest, uint16_t protocolNumber)
381{
383 return SendFrom(packet, m_address, dest, protocolNumber);
384}
385
386bool
388 const Address& src,
389 const Address& dest,
390 uint16_t protocolNumber)
391{
394
395 // try to use the learned state if data is unicast
396 if (!dst.IsGroup())
397 {
398 Ptr<NetDevice> outPort = GetLearnedState(dst);
399 if (outPort)
400 {
401 outPort->SendFrom(packet, src, dest, protocolNumber);
402 return true;
403 }
404 }
405
406 // data was not unicast or no state has been learned for that mac
407 // address => flood through all ports.
408 Ptr<Packet> pktCopy;
409 for (auto iter = m_ports.begin(); iter != m_ports.end(); iter++)
410 {
411 pktCopy = packet->Copy();
412 Ptr<NetDevice> port = *iter;
413 port->SendFrom(pktCopy, src, dest, protocolNumber);
414 }
415
416 return true;
417}
418
421{
423 return m_node;
424}
425
426void
432
433bool
435{
437 return true;
438}
439
440void
446
447void
453
454bool
456{
458 return true;
459}
460
463{
464 NS_LOG_FUNCTION(this << addr);
465 return Mac48Address::GetMulticast(addr);
466}
467
468} // namespace ns3
ns3::BridgeNetDevice declaration.
a polymophic address class
Definition address.h:90
a virtual net device that bridges multiple LAN segments
bool IsBroadcast() const override
Ptr< BridgeChannel > m_channel
virtual bridged channel
void ReceiveFromDevice(Ptr< NetDevice > device, Ptr< const Packet > packet, uint16_t protocol, const Address &source, const Address &destination, PacketType packetType)
Receives a packet from one bridged port.
bool IsBridge() const override
Return true if the net device is acting as a bridge.
Ptr< Node > m_node
node owning this NetDevice
std::map< Mac48Address, LearnedState > m_learnState
Container for known address statuses.
Address GetBroadcast() const override
Address GetMulticast(Ipv4Address multicastGroup) const override
Make and return a MAC multicast address using the provided multicast group.
uint32_t m_ifIndex
Interface index.
bool SupportsSendFrom() const override
Mac48Address m_address
MAC address of the NetDevice.
uint16_t GetMtu() const override
bool NeedsArp() const override
NetDevice::ReceiveCallback m_rxCallback
receive callback
bool Send(Ptr< Packet > packet, const Address &dest, uint16_t protocolNumber) override
static TypeId GetTypeId()
Get the type ID.
std::vector< Ptr< NetDevice > > m_ports
bridged ports
Time m_expirationTime
time it takes for learned MAC state to expire
bool IsPointToPoint() const override
Return true if the net device is on a point-to-point link.
bool IsMulticast() const override
void SetReceiveCallback(NetDevice::ReceiveCallback cb) override
void DoDispose() override
Destructor implementation.
uint32_t GetIfIndex() const override
void ForwardUnicast(Ptr< NetDevice > incomingPort, Ptr< const Packet > packet, uint16_t protocol, Mac48Address src, Mac48Address dst)
Forwards a unicast packet.
Ptr< NetDevice > GetLearnedState(Mac48Address source)
Gets the port associated to a source address.
bool m_enableLearning
true if the bridge will learn the node status
void AddBridgePort(Ptr< NetDevice > bridgePort)
Add a 'port' to a bridge device.
void Learn(Mac48Address source, Ptr< NetDevice > port)
Learns the port a MAC address is sending from.
bool SendFrom(Ptr< Packet > packet, const Address &source, const Address &dest, uint16_t protocolNumber) override
void SetNode(Ptr< Node > node) override
bool SetMtu(const uint16_t mtu) override
uint16_t m_mtu
MTU of the bridged NetDevice.
Ptr< Channel > GetChannel() const override
Address GetAddress() const override
Ptr< NetDevice > GetBridgePort(uint32_t n) const
Gets the n-th bridged port.
void SetIfIndex(const uint32_t index) override
void AddLinkChangeCallback(Callback< void > callback) override
Ptr< Node > GetNode() const override
bool IsLinkUp() const override
NetDevice::PromiscReceiveCallback m_promiscRxCallback
promiscuous receive callback
void SetAddress(Address address) override
Set the address of this interface.
uint32_t GetNBridgePorts() const
Gets the number of bridged 'ports', i.e., the NetDevices currently bridged.
void ForwardBroadcast(Ptr< NetDevice > incomingPort, Ptr< const Packet > packet, uint16_t protocol, Mac48Address src, Mac48Address dst)
Forwards a broadcast or a multicast packet.
void SetPromiscReceiveCallback(NetDevice::PromiscReceiveCallback cb) override
Callback template class.
Definition callback.h:422
bool IsNull() const
Check for null implementation.
Definition callback.h:555
Ipv4 addresses are stored in host order in this class.
Describes an IPv6 address.
an EUI-48 address
static Mac48Address GetMulticast(Ipv4Address address)
bool IsGroup() const
static bool IsMatchingType(const Address &address)
static Mac48Address ConvertFrom(const Address &address)
static Mac48Address GetBroadcast()
Network layer to device interface.
Definition net-device.h:87
PacketType
Packet types are used as they are in Linux.
Definition net-device.h:289
@ PACKET_HOST
Packet addressed to us.
Definition net-device.h:290
@ PACKET_OTHERHOST
Packet addressed to someone else.
Definition net-device.h:296
@ PACKET_BROADCAST
Packet addressed to all.
Definition net-device.h:292
@ PACKET_MULTICAST
Packet addressed to multicast group.
Definition net-device.h:294
void RegisterProtocolHandler(ProtocolHandler handler, uint16_t protocolType, Ptr< NetDevice > device, bool promiscuous=false)
Definition node.cc:220
virtual void DoDispose()
Destructor implementation.
Definition object.cc:433
Smart pointer class similar to boost::intrusive_ptr.
static Time Now()
Return the current simulation virtual time.
Definition simulator.cc:197
Simulation virtual time values and global simulation resolution.
Definition nstime.h:94
a unique identifier for an interface.
Definition type-id.h:48
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition type-id.cc:1001
Hold an unsigned integer type.
Definition uinteger.h:34
uint16_t port
Definition dsdv-manet.cc:33
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition assert.h:55
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:191
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition log.h:257
#define NS_LOG_LOGIC(msg)
Use NS_LOG to output a message of level LOG_LOGIC.
Definition log.h:271
#define NS_LOG_FUNCTION_NOARGS()
Output the name of the function.
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
Ptr< T > CreateObject(Args &&... args)
Create an object by type, with varying number of constructor parameters.
Definition object.h:619
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition object-base.h:35
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition nstime.h:1308
Every class exported by the ns3 library is enclosed in the ns3 namespace.
Ptr< const AttributeChecker > MakeBooleanChecker()
Definition boolean.cc:113
Ptr< const AttributeChecker > MakeUintegerChecker()
Definition uinteger.h:85
Ptr< const AttributeAccessor > MakeTimeAccessor(T1 a1)
Definition nstime.h:1396
Callback< R, Args... > MakeCallback(R(T::*memPtr)(Args...), OBJ objPtr)
Build Callbacks for class method members which take varying numbers of arguments and potentially retu...
Definition callback.h:684
Ptr< const AttributeAccessor > MakeUintegerAccessor(T1 a1)
Definition uinteger.h:35
Ptr< const AttributeAccessor > MakeBooleanAccessor(T1 a1)
Definition boolean.h:70
Ptr< const AttributeChecker > MakeTimeChecker()
Helper to make an unbounded Time checker.
Definition nstime.h:1416
Structure holding the status of an address.
Time expirationTime
time it takes for learned MAC state to expire
Ptr< NetDevice > associatedPort
port associated with the address