replace RefCountBase with SimpleRefCount<> to avoid duplicate refcounting implementations.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /* vim: set ts=2 sw=2 sta expandtab ai si cin: */
4 * Copyright (c) 2009 Drexel University
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation;
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 * Author: Tom Wambold <tom5760@gmail.com>
21 /* These classes implement RFC 5444 - The Generalized Mobile Ad Hoc Network
22 * (MANET) Packet/PbbMessage Format
23 * See: http://tools.ietf.org/html/rfc5444 for details */
25 #include "ns3/ipv4-address.h"
26 #include "ns3/ipv6-address.h"
27 #include "ns3/assert.h"
31 static const uint8_t VERSION = 0;
33 static const uint8_t PHAS_SEQ_NUM = 0x8;
34 static const uint8_t PHAS_TLV = 0x4;
36 /* PbbMessage flags */
37 static const uint8_t MHAS_ORIG = 0x80;
38 static const uint8_t MHAS_HOP_LIMIT = 0x40;
39 static const uint8_t MHAS_HOP_COUNT = 0x20;
40 static const uint8_t MHAS_SEQ_NUM = 0x10;
42 /* Address block flags */
43 static const uint8_t AHAS_HEAD = 0x80;
44 static const uint8_t AHAS_FULL_TAIL = 0x40;
45 static const uint8_t AHAS_ZERO_TAIL = 0x20;
46 static const uint8_t AHAS_SINGLE_PRE_LEN = 0x10;
47 static const uint8_t AHAS_MULTI_PRE_LEN = 0x08;
50 static const uint8_t THAS_TYPE_EXT = 0x80;
51 static const uint8_t THAS_SINGLE_INDEX = 0x40;
52 static const uint8_t THAS_MULTI_INDEX = 0x20;
53 static const uint8_t THAS_VALUE = 0x10;
54 static const uint8_t THAS_EXT_LEN = 0x08;
55 static const uint8_t TIS_MULTIVALUE = 0x04;
59 NS_OBJECT_ENSURE_REGISTERED (PbbPacket);
61 PbbTlvBlock::PbbTlvBlock (void)
66 PbbTlvBlock::~PbbTlvBlock (void)
72 PbbTlvBlock::Begin (void)
74 return m_tlvList.begin ();
77 PbbTlvBlock::ConstIterator
78 PbbTlvBlock::Begin (void) const
80 return m_tlvList.begin ();
84 PbbTlvBlock::End (void)
86 return m_tlvList.end ();
89 PbbTlvBlock::ConstIterator
90 PbbTlvBlock::End (void) const
92 return m_tlvList.end ();
96 PbbTlvBlock::Size (void) const
98 return m_tlvList.size ();
102 PbbTlvBlock::Empty (void) const
104 return m_tlvList.empty ();
108 PbbTlvBlock::Front (void) const
110 return m_tlvList.front ();
114 PbbTlvBlock::Back (void) const
116 return m_tlvList.back ();
120 PbbTlvBlock::PushFront (Ptr<PbbTlv> tlv)
122 m_tlvList.push_front (tlv);
126 PbbTlvBlock::PopFront (void)
128 m_tlvList.pop_front ();
132 PbbTlvBlock::PushBack (Ptr<PbbTlv> tlv)
134 m_tlvList.push_back (tlv);
138 PbbTlvBlock::PopBack (void)
140 m_tlvList.pop_back ();
143 PbbTlvBlock::Iterator
144 PbbTlvBlock::Insert (PbbTlvBlock::Iterator position, const Ptr<PbbTlv> tlv)
146 return m_tlvList.insert (position, tlv);
149 PbbTlvBlock::Iterator
150 PbbTlvBlock::Erase (PbbTlvBlock::Iterator position)
152 return m_tlvList.erase (position);
155 PbbTlvBlock::Iterator
156 PbbTlvBlock::Erase (PbbTlvBlock::Iterator first, PbbTlvBlock::Iterator last)
158 return m_tlvList.erase (first, last);
162 PbbTlvBlock::Clear (void)
164 for (Iterator iter = Begin (); iter != End (); iter++)
172 PbbTlvBlock::GetSerializedSize (void) const
176 for (ConstIterator iter = Begin (); iter != End (); iter++)
178 size += (*iter)->GetSerializedSize ();
184 PbbTlvBlock::Serialize (Buffer::Iterator &start) const
188 start.WriteHtonU16 (0);
192 /* We need to write the size of the TLV block in front, so save its
194 Buffer::Iterator tlvsize = start;
196 for (ConstIterator iter = Begin (); iter != End (); iter++)
198 (*iter)->Serialize (start);
200 /* - 2 to not include the size field */
201 uint16_t size = start.GetDistanceFrom (tlvsize) - 2;
202 tlvsize.WriteHtonU16 (size);
206 PbbTlvBlock::Deserialize (Buffer::Iterator &start)
208 uint16_t size = start.ReadNtohU16 ();
210 Buffer::Iterator tlvstart = start;
213 while (start.GetDistanceFrom (tlvstart) < size)
215 Ptr<PbbTlv> newtlv = Create<PbbTlv> ();
216 newtlv->Deserialize (start);
223 PbbTlvBlock::Print (std::ostream &os) const
229 PbbTlvBlock::Print (std::ostream &os, int level) const
231 std::string prefix = "";
232 for (int i = 0; i < level; i++)
237 os << prefix << "TLV Block {" << std::endl;
238 os << prefix << "\tsize = " << Size () << std::endl;
239 os << prefix << "\tmembers [" << std::endl;
241 for (ConstIterator iter = Begin (); iter != End (); iter++)
243 (*iter)->Print (os, level+2);
246 os << prefix << "\t]" << std::endl;
247 os << prefix << "}" << std::endl;
251 PbbTlvBlock::operator== (const PbbTlvBlock &other) const
253 if (Size () != other.Size ())
258 ConstIterator ti, oi;
259 for (ti = Begin (), oi = other.Begin ();
260 ti != End () && oi != other.End ();
272 PbbTlvBlock::operator!= (const PbbTlvBlock &other) const
274 return !(*this == other);
277 /* End PbbTlvBlock class */
279 PbbAddressTlvBlock::PbbAddressTlvBlock (void)
284 PbbAddressTlvBlock::~PbbAddressTlvBlock (void)
289 PbbAddressTlvBlock::Iterator
290 PbbAddressTlvBlock::Begin (void)
292 return m_tlvList.begin ();
295 PbbAddressTlvBlock::ConstIterator
296 PbbAddressTlvBlock::Begin (void) const
298 return m_tlvList.begin ();
301 PbbAddressTlvBlock::Iterator
302 PbbAddressTlvBlock::End (void)
304 return m_tlvList.end ();
307 PbbAddressTlvBlock::ConstIterator
308 PbbAddressTlvBlock::End (void) const
310 return m_tlvList.end ();
314 PbbAddressTlvBlock::Size (void) const
316 return m_tlvList.size ();
320 PbbAddressTlvBlock::Empty (void) const
322 return m_tlvList.empty ();
326 PbbAddressTlvBlock::Front (void) const
328 return m_tlvList.front ();
332 PbbAddressTlvBlock::Back (void) const
334 return m_tlvList.back ();
338 PbbAddressTlvBlock::PushFront (Ptr<PbbAddressTlv> tlv)
340 m_tlvList.push_front (tlv);
344 PbbAddressTlvBlock::PopFront (void)
346 m_tlvList.pop_front ();
350 PbbAddressTlvBlock::PushBack (Ptr<PbbAddressTlv> tlv)
352 m_tlvList.push_back (tlv);
356 PbbAddressTlvBlock::PopBack (void)
358 m_tlvList.pop_back ();
361 PbbAddressTlvBlock::Iterator
362 PbbAddressTlvBlock::Insert (PbbAddressTlvBlock::Iterator position, const Ptr<PbbAddressTlv> tlv)
364 return m_tlvList.insert (position, tlv);
367 PbbAddressTlvBlock::Iterator
368 PbbAddressTlvBlock::Erase (PbbAddressTlvBlock::Iterator position)
370 return m_tlvList.erase (position);
373 PbbAddressTlvBlock::Iterator
374 PbbAddressTlvBlock::Erase (PbbAddressTlvBlock::Iterator first, PbbAddressTlvBlock::Iterator last)
376 return m_tlvList.erase (first, last);
380 PbbAddressTlvBlock::Clear (void)
382 for (Iterator iter = Begin (); iter != End (); iter++)
390 PbbAddressTlvBlock::GetSerializedSize (void) const
394 for (ConstIterator iter = Begin (); iter != End (); iter++)
396 size += (*iter)->GetSerializedSize ();
402 PbbAddressTlvBlock::Serialize (Buffer::Iterator &start) const
406 start.WriteHtonU16 (0);
410 /* We need to write the size of the TLV block in front, so save its
412 Buffer::Iterator tlvsize = start;
414 for (ConstIterator iter = Begin (); iter != End (); iter++)
416 (*iter)->Serialize (start);
418 /* - 2 to not include the size field */
419 uint16_t size = start.GetDistanceFrom (tlvsize) - 2;
420 tlvsize.WriteHtonU16 (size);
424 PbbAddressTlvBlock::Deserialize (Buffer::Iterator &start)
426 uint16_t size = start.ReadNtohU16 ();
428 Buffer::Iterator tlvstart = start;
431 while (start.GetDistanceFrom (tlvstart) < size)
433 Ptr<PbbAddressTlv> newtlv = Create<PbbAddressTlv> ();
434 newtlv->Deserialize (start);
441 PbbAddressTlvBlock::Print (std::ostream &os) const
447 PbbAddressTlvBlock::Print (std::ostream &os, int level) const
449 std::string prefix = "";
450 for (int i = 0; i < level; i++)
455 os << prefix << "TLV Block {" << std::endl;
456 os << prefix << "\tsize = " << Size () << std::endl;
457 os << prefix << "\tmembers [" << std::endl;
459 for (ConstIterator iter = Begin (); iter != End (); iter++)
461 (*iter)->Print (os, level+2);
464 os << prefix << "\t]" << std::endl;
465 os << prefix << "}" << std::endl;
469 PbbAddressTlvBlock::operator== (const PbbAddressTlvBlock &other) const
471 if (Size () != other.Size ())
476 ConstIterator it, ot;
477 for (it = Begin (), ot = other.Begin ();
478 it != End () && ot != other.End ();
490 PbbAddressTlvBlock::operator!= (const PbbAddressTlvBlock &other) const
492 return !(*this == other);
496 /* End PbbAddressTlvBlock Class */
498 PbbPacket::PbbPacket (void)
504 PbbPacket::~PbbPacket (void)
510 PbbPacket::GetVersion (void) const
516 PbbPacket::SetSequenceNumber (uint16_t number)
523 PbbPacket::GetSequenceNumber (void) const
525 NS_ASSERT (HasSequenceNumber ());
530 PbbPacket::HasSequenceNumber (void) const
535 /* Manipulating Packet TLVs */
537 PbbPacket::TlvIterator
538 PbbPacket::TlvBegin (void)
540 return m_tlvList.Begin ();
543 PbbPacket::ConstTlvIterator
544 PbbPacket::TlvBegin (void) const
546 return m_tlvList.Begin ();
549 PbbPacket::TlvIterator
550 PbbPacket::TlvEnd (void)
552 return m_tlvList.End ();
555 PbbPacket::ConstTlvIterator
556 PbbPacket::TlvEnd (void) const
558 return m_tlvList.End ();
562 PbbPacket::TlvSize (void) const
564 return m_tlvList.Size ();
568 PbbPacket::TlvEmpty (void) const
570 return m_tlvList.Empty ();
574 PbbPacket::TlvFront (void)
576 return m_tlvList.Front ();
580 PbbPacket::TlvFront (void) const
582 return m_tlvList.Front ();
586 PbbPacket::TlvBack (void)
588 return m_tlvList.Back ();
592 PbbPacket::TlvBack (void) const
594 return m_tlvList.Back ();
598 PbbPacket::TlvPushFront (Ptr<PbbTlv> tlv)
600 m_tlvList.PushFront (tlv);
604 PbbPacket::TlvPopFront (void)
606 m_tlvList.PopFront ();
610 PbbPacket::TlvPushBack (Ptr<PbbTlv> tlv)
612 m_tlvList.PushBack (tlv);
616 PbbPacket::TlvPopBack (void)
618 m_tlvList.PopBack ();
621 PbbPacket::TlvIterator
622 PbbPacket::Erase (PbbPacket::TlvIterator position)
624 return m_tlvList.Erase (position);
627 PbbPacket::TlvIterator
628 PbbPacket::Erase (PbbPacket::TlvIterator first, PbbPacket::TlvIterator last)
630 return m_tlvList.Erase (first, last);
634 PbbPacket::TlvClear (void)
639 /* Manipulating Packet Messages */
641 PbbPacket::MessageIterator
642 PbbPacket::MessageBegin (void)
644 return m_messageList.begin ();
647 PbbPacket::ConstMessageIterator
648 PbbPacket::MessageBegin (void) const
650 return m_messageList.begin ();
653 PbbPacket::MessageIterator
654 PbbPacket::MessageEnd (void)
656 return m_messageList.end ();
659 PbbPacket::ConstMessageIterator
660 PbbPacket::MessageEnd (void) const
662 return m_messageList.end ();
666 PbbPacket::MessageSize (void) const
668 return m_messageList.size ();
672 PbbPacket::MessageEmpty (void) const
674 return m_messageList.empty ();
678 PbbPacket::MessageFront (void)
680 return m_messageList.front ();
683 const Ptr<PbbMessage>
684 PbbPacket::MessageFront (void) const
686 return m_messageList.front ();
690 PbbPacket::MessageBack (void)
692 return m_messageList.back ();
695 const Ptr<PbbMessage>
696 PbbPacket::MessageBack (void) const
698 return m_messageList.back ();
702 PbbPacket::MessagePushFront (Ptr<PbbMessage> tlv)
704 m_messageList.push_front (tlv);
708 PbbPacket::MessagePopFront (void)
710 m_messageList.pop_front ();
714 PbbPacket::MessagePushBack (Ptr<PbbMessage> tlv)
716 m_messageList.push_back (tlv);
720 PbbPacket::MessagePopBack (void)
722 m_messageList.pop_back ();
725 PbbPacket::MessageIterator
726 PbbPacket::Erase (PbbPacket::MessageIterator position)
728 return m_messageList.erase (position);
731 PbbPacket::MessageIterator
732 PbbPacket::Erase (PbbPacket::MessageIterator first,
733 PbbPacket::MessageIterator last)
735 return m_messageList.erase (first, last);
739 PbbPacket::MessageClear (void)
741 for (MessageIterator iter = MessageBegin (); iter != MessageEnd (); iter++)
745 m_messageList.clear ();
750 PbbPacket::GetTypeId (void)
752 static TypeId tid = TypeId ("ns3::PbbPacket")
753 .SetParent<Header> ()
754 .AddConstructor<PbbPacket> ()
760 PbbPacket::GetInstanceTypeId (void) const
766 PbbPacket::GetSerializedSize (void) const
768 /* Version number + flags */
771 if (HasSequenceNumber())
778 size += m_tlvList.GetSerializedSize ();
781 for (ConstMessageIterator iter = MessageBegin ();
782 iter != MessageEnd ();
785 size += (*iter)->GetSerializedSize ();
792 PbbPacket::Serialize (Buffer::Iterator start) const
794 /* We remember the start, so we can write the flags after we check for a
795 * sequence number and TLV. */
796 Buffer::Iterator bufref = start;
799 uint8_t flags = VERSION;
800 /* Make room for 4 bit flags */
803 if (HasSequenceNumber ())
805 flags |= PHAS_SEQ_NUM;
806 start.WriteHtonU16 (GetSequenceNumber ());
812 m_tlvList.Serialize (start);
815 bufref.WriteU8(flags);
817 for (ConstMessageIterator iter = MessageBegin ();
818 iter != MessageEnd ();
821 (*iter)->Serialize (start);
826 PbbPacket::Deserialize (Buffer::Iterator start)
828 Buffer::Iterator begin = start;
830 uint8_t flags = start.ReadU8 ();
832 if (flags & PHAS_SEQ_NUM)
834 SetSequenceNumber (start.ReadNtohU16 ());
837 if (flags & PHAS_TLV)
839 m_tlvList.Deserialize (start);
842 while (!start.IsEnd())
844 Ptr<PbbMessage> newmsg = PbbMessage::DeserializeMessage (start);
847 return start.GetDistanceFrom (begin);
849 MessagePushBack (newmsg);
855 return start.GetDistanceFrom (begin);
859 PbbPacket::Print (std::ostream &os) const
861 os << "PbbPacket {" << std::endl;
863 if (HasSequenceNumber ())
865 os << "\tsequence number = " << GetSequenceNumber ();
870 m_tlvList.Print (os, 1);
872 for (ConstMessageIterator iter = MessageBegin ();
873 iter != MessageEnd ();
876 (*iter)->Print (os, 1);
879 os << "}" << std::endl;
883 PbbPacket::operator== (const PbbPacket &other) const
885 if (GetVersion () != other.GetVersion ())
890 if (HasSequenceNumber () != other.HasSequenceNumber ())
895 if (HasSequenceNumber ())
897 if (GetSequenceNumber () != other.GetSequenceNumber ())
901 if (m_tlvList != other.m_tlvList)
906 if (MessageSize () != other.MessageSize ())
911 ConstMessageIterator tmi, omi;
912 for (tmi = MessageBegin (), omi = other.MessageBegin ();
913 tmi != MessageEnd () && omi != other.MessageEnd ();
925 PbbPacket::operator!= (const PbbPacket &other) const
927 return !(*this == other);
930 /* End PbbPacket class */
932 PbbMessage::PbbMessage ()
934 /* Default to IPv4 */
936 m_hasOriginatorAddress = false;
937 m_hasHopLimit = false;
938 m_hasHopCount = false;
939 m_hasSequenceNumber = false;
942 PbbMessage::~PbbMessage ()
944 AddressBlockClear ();
948 PbbMessage::SetType (uint8_t type)
954 PbbMessage::GetType (void) const
960 PbbMessage::GetAddressLength (void) const
966 PbbMessage::SetOriginatorAddress (Address address)
968 m_originatorAddress = address;
969 m_hasOriginatorAddress = true;
973 PbbMessage::GetOriginatorAddress (void) const
975 NS_ASSERT (HasOriginatorAddress ());
976 return m_originatorAddress;
980 PbbMessage::HasOriginatorAddress (void) const
982 return m_hasOriginatorAddress;
986 PbbMessage::SetHopLimit (uint8_t hopLimit)
988 m_hopLimit = hopLimit;
989 m_hasHopLimit = true;
993 PbbMessage::GetHopLimit (void) const
995 NS_ASSERT (HasHopLimit ());
1000 PbbMessage::HasHopLimit (void) const
1002 return m_hasHopLimit;
1006 PbbMessage::SetHopCount (uint8_t hopCount)
1008 m_hopCount = hopCount;
1009 m_hasHopCount = true;
1013 PbbMessage::GetHopCount (void) const
1015 NS_ASSERT (HasHopCount ());
1020 PbbMessage::HasHopCount (void) const
1022 return m_hasHopCount;
1026 PbbMessage::SetSequenceNumber (uint16_t sequenceNumber)
1028 m_sequenceNumber = sequenceNumber;
1029 m_hasSequenceNumber = true;
1033 PbbMessage::GetSequenceNumber (void) const
1035 NS_ASSERT (HasSequenceNumber ());
1036 return m_sequenceNumber;
1040 PbbMessage::HasSequenceNumber (void) const
1042 return m_hasSequenceNumber;
1045 /* Manipulating PbbMessage TLVs */
1047 PbbMessage::TlvIterator
1048 PbbMessage::TlvBegin (void)
1050 return m_tlvList.Begin();
1053 PbbMessage::ConstTlvIterator
1054 PbbMessage::TlvBegin (void) const
1056 return m_tlvList.Begin();
1059 PbbMessage::TlvIterator
1060 PbbMessage::TlvEnd (void)
1062 return m_tlvList.End();
1065 PbbMessage::ConstTlvIterator
1066 PbbMessage::TlvEnd (void) const
1068 return m_tlvList.End();
1072 PbbMessage::TlvSize (void) const
1074 return m_tlvList.Size();
1078 PbbMessage::TlvEmpty (void) const
1080 return m_tlvList.Empty();
1084 PbbMessage::TlvFront (void)
1086 return m_tlvList.Front();
1090 PbbMessage::TlvFront (void) const
1092 return m_tlvList.Front();
1096 PbbMessage::TlvBack (void)
1098 return m_tlvList.Back();
1102 PbbMessage::TlvBack (void) const
1104 return m_tlvList.Back();
1108 PbbMessage::TlvPushFront (Ptr<PbbTlv> tlv)
1110 m_tlvList.PushFront(tlv);
1114 PbbMessage::TlvPopFront (void)
1116 m_tlvList.PopFront();
1120 PbbMessage::TlvPushBack (Ptr<PbbTlv> tlv)
1122 m_tlvList.PushBack(tlv);
1126 PbbMessage::TlvPopBack (void)
1128 m_tlvList.PopBack();
1131 PbbMessage::TlvIterator
1132 PbbMessage::TlvErase (PbbMessage::TlvIterator position)
1134 return m_tlvList.Erase(position);
1137 PbbMessage::TlvIterator
1138 PbbMessage::TlvErase (PbbMessage::TlvIterator first, PbbMessage::TlvIterator last)
1140 return m_tlvList.Erase(first, last);
1144 PbbMessage::TlvClear (void)
1149 /* Manipulating Address Block and Address TLV pairs */
1151 PbbMessage::AddressBlockIterator
1152 PbbMessage::AddressBlockBegin (void)
1154 return m_addressBlockList.begin();
1157 PbbMessage::ConstAddressBlockIterator
1158 PbbMessage::AddressBlockBegin (void) const
1160 return m_addressBlockList.begin();
1163 PbbMessage::AddressBlockIterator
1164 PbbMessage::AddressBlockEnd (void)
1166 return m_addressBlockList.end();
1169 PbbMessage::ConstAddressBlockIterator
1170 PbbMessage::AddressBlockEnd (void) const
1172 return m_addressBlockList.end();
1176 PbbMessage::AddressBlockSize (void) const
1178 return m_addressBlockList.size();
1182 PbbMessage::AddressBlockEmpty (void) const
1184 return m_addressBlockList.empty();
1187 Ptr<PbbAddressBlock>
1188 PbbMessage::AddressBlockFront (void)
1190 return m_addressBlockList.front();
1193 const Ptr<PbbAddressBlock>
1194 PbbMessage::AddressBlockFront (void) const
1196 return m_addressBlockList.front();
1199 Ptr<PbbAddressBlock>
1200 PbbMessage::AddressBlockBack (void)
1202 return m_addressBlockList.back();
1205 const Ptr<PbbAddressBlock>
1206 PbbMessage::AddressBlockBack (void) const
1208 return m_addressBlockList.back();
1212 PbbMessage::AddressBlockPushFront (Ptr<PbbAddressBlock> tlv)
1214 m_addressBlockList.push_front(tlv);
1218 PbbMessage::AddressBlockPopFront (void)
1220 m_addressBlockList.pop_front();
1224 PbbMessage::AddressBlockPushBack (Ptr<PbbAddressBlock> tlv)
1226 m_addressBlockList.push_back(tlv);
1230 PbbMessage::AddressBlockPopBack (void)
1232 m_addressBlockList.pop_back();
1235 PbbMessage::AddressBlockIterator
1236 PbbMessage::AddressBlockErase (PbbMessage::AddressBlockIterator position)
1238 return m_addressBlockList.erase(position);
1241 PbbMessage::AddressBlockIterator
1242 PbbMessage::AddressBlockErase (PbbMessage::AddressBlockIterator first,
1243 PbbMessage::AddressBlockIterator last)
1245 return m_addressBlockList.erase(first, last);
1249 PbbMessage::AddressBlockClear (void)
1251 for (AddressBlockIterator iter = AddressBlockBegin ();
1252 iter != AddressBlockEnd ();
1257 return m_addressBlockList.clear();
1261 PbbMessage::GetSerializedSize (void) const
1263 /* msg-type + (msg-flags + msg-addr-length) + 2msg-size */
1266 if (HasOriginatorAddress())
1268 size += GetAddressLength() + 1;
1281 if (HasSequenceNumber())
1286 size += m_tlvList.GetSerializedSize ();
1288 for (ConstAddressBlockIterator iter = AddressBlockBegin ();
1289 iter != AddressBlockEnd ();
1292 size += (*iter)->GetSerializedSize ();
1299 PbbMessage::Serialize (Buffer::Iterator &start) const
1301 Buffer::Iterator front = start;
1303 start.WriteU8 (GetType());
1305 /* Save a reference to the spot where we will later write the flags */
1306 Buffer::Iterator bufref = start;
1311 flags = GetAddressLength ();
1313 Buffer::Iterator sizeref = start;
1316 if (HasOriginatorAddress ())
1319 SerializeOriginatorAddress (start);
1324 flags |= MHAS_HOP_LIMIT;
1325 start.WriteU8 (GetHopLimit ());
1330 flags |= MHAS_HOP_COUNT;
1331 start.WriteU8 (GetHopCount ());
1334 if (HasSequenceNumber ())
1336 flags |= MHAS_SEQ_NUM;
1337 start.WriteHtonU16 (GetSequenceNumber ());
1340 bufref.WriteU8(flags);
1342 m_tlvList.Serialize (start);
1344 for (ConstAddressBlockIterator iter = AddressBlockBegin ();
1345 iter != AddressBlockEnd ();
1348 (*iter)->Serialize (start);
1351 sizeref.WriteHtonU16 (front.GetDistanceFrom (start));
1355 PbbMessage::DeserializeMessage (Buffer::Iterator &start)
1357 /* We need to read the msg-addr-len field to determine what kind of object to
1360 uint8_t addrlen = start.ReadU8 ();
1361 start.Prev (2); /* Go back to the start */
1363 /* The first four bytes of the flag is the address length. Set the last four
1364 * bytes to 0 to read it. */
1365 addrlen = (addrlen & 0xf);
1367 Ptr<PbbMessage> newmsg;
1373 newmsg = Create<PbbMessageIpv4> ();
1376 newmsg = Create<PbbMessageIpv6> ();
1382 newmsg->Deserialize (start);
1387 PbbMessage::Deserialize (Buffer::Iterator &start)
1389 Buffer::Iterator front = start;
1390 SetType (start.ReadU8 ());
1391 uint8_t flags = start.ReadU8 ();
1393 uint16_t size = start.ReadNtohU16 ();
1395 if (flags & MHAS_ORIG)
1397 SetOriginatorAddress (DeserializeOriginatorAddress (start));
1400 if (flags & MHAS_HOP_LIMIT)
1402 SetHopLimit (start.ReadU8 ());
1405 if (flags & MHAS_HOP_COUNT)
1407 SetHopCount (start.ReadU8 ());
1410 if (flags & MHAS_SEQ_NUM)
1412 SetSequenceNumber (start.ReadNtohU16 ());
1415 m_tlvList.Deserialize (start);
1419 while (start.GetDistanceFrom(front) < size)
1421 Ptr<PbbAddressBlock> newab = AddressBlockDeserialize (start);
1422 AddressBlockPushBack (newab);
1428 PbbMessage::Print (std::ostream &os) const
1434 PbbMessage::Print (std::ostream &os, int level) const
1436 std::string prefix = "";
1437 for (int i = 0; i < level; i++)
1439 prefix.append ("\t");
1442 os << prefix << "PbbMessage {" << std::endl;
1444 os << prefix << "\tmessage type = " << (int)GetType () << std::endl;
1445 os << prefix << "\taddress size = " << GetAddressLength () << std::endl;
1447 if (HasOriginatorAddress ())
1449 os << prefix << "\toriginator address = ";
1450 PrintOriginatorAddress (os);
1456 os << prefix << "\thop limit = " << (int)GetHopLimit () << std::endl;
1461 os << prefix << "\thop count = " << (int)GetHopCount () << std::endl;
1464 if (HasSequenceNumber ())
1466 os << prefix << "\tseqnum = " << GetSequenceNumber () << std::endl;
1469 m_tlvList.Print (os, level+1);
1471 for (ConstAddressBlockIterator iter = AddressBlockBegin ();
1472 iter != AddressBlockEnd ();
1475 (*iter)->Print (os, level+1);
1477 os << prefix << "}" << std::endl;
1481 PbbMessage::operator== (const PbbMessage &other) const
1483 if (GetAddressLength () != other.GetAddressLength ())
1488 if (GetType () != other.GetType ())
1493 if (HasOriginatorAddress () != other.HasOriginatorAddress ())
1498 if (HasOriginatorAddress ())
1500 if (GetOriginatorAddress () != other.GetOriginatorAddress ())
1506 if (HasHopLimit () != other.HasHopLimit ())
1513 if (GetHopLimit () != other.GetHopLimit ())
1519 if (HasHopCount () != other.HasHopCount ())
1526 if (GetHopCount () != other.GetHopCount ())
1532 if (HasSequenceNumber () != other.HasSequenceNumber ())
1537 if (HasSequenceNumber ())
1539 if (GetSequenceNumber () != other.GetSequenceNumber ())
1545 if (m_tlvList != other.m_tlvList)
1550 if (AddressBlockSize () != other.AddressBlockSize ())
1555 ConstAddressBlockIterator tai, oai;
1556 for (tai = AddressBlockBegin (), oai = other.AddressBlockBegin ();
1557 tai != AddressBlockEnd () && oai != other.AddressBlockEnd ();
1569 PbbMessage::operator!= (const PbbMessage &other) const
1571 return !(*this == other);
1574 /* End PbbMessage Class */
1576 PbbMessageIpv4::PbbMessageIpv4 ()
1580 PbbMessageIpv4::~PbbMessageIpv4 ()
1585 PbbMessageIpv4::GetAddressLength (void) const
1591 PbbMessageIpv4::SerializeOriginatorAddress (Buffer::Iterator &start) const
1593 uint8_t buffer[GetAddressLength () + 1];
1594 Ipv4Address::ConvertFrom (GetOriginatorAddress ()).Serialize(buffer);
1595 start.Write (buffer, GetAddressLength () + 1);
1599 PbbMessageIpv4::DeserializeOriginatorAddress (Buffer::Iterator &start) const
1601 uint8_t buffer[GetAddressLength () + 1];
1602 start.Read(buffer, GetAddressLength () + 1);
1603 return Ipv4Address::Deserialize (buffer);
1607 PbbMessageIpv4::PrintOriginatorAddress (std::ostream &os) const
1609 Ipv4Address::ConvertFrom (GetOriginatorAddress ()).Print (os);
1612 Ptr<PbbAddressBlock>
1613 PbbMessageIpv4::AddressBlockDeserialize (Buffer::Iterator &start) const
1615 Ptr<PbbAddressBlock> newab = Create<PbbAddressBlockIpv4> ();
1616 newab->Deserialize (start);
1620 /* End PbbMessageIpv4 Class */
1622 PbbMessageIpv6::PbbMessageIpv6 ()
1626 PbbMessageIpv6::~PbbMessageIpv6 ()
1631 PbbMessageIpv6::GetAddressLength (void) const
1637 PbbMessageIpv6::SerializeOriginatorAddress (Buffer::Iterator &start) const
1639 uint8_t buffer[GetAddressLength () + 1];
1640 Ipv6Address::ConvertFrom (GetOriginatorAddress ()).Serialize(buffer);
1641 start.Write (buffer, GetAddressLength () + 1);
1645 PbbMessageIpv6::DeserializeOriginatorAddress (Buffer::Iterator &start) const
1647 uint8_t buffer[GetAddressLength () + 1];
1648 start.Read(buffer, GetAddressLength () + 1);
1649 return Ipv6Address::Deserialize (buffer);
1653 PbbMessageIpv6::PrintOriginatorAddress (std::ostream &os) const
1655 Ipv6Address::ConvertFrom (GetOriginatorAddress ()).Print (os);
1658 Ptr<PbbAddressBlock>
1659 PbbMessageIpv6::AddressBlockDeserialize (Buffer::Iterator &start) const
1661 Ptr<PbbAddressBlock> newab = Create<PbbAddressBlockIpv6> ();
1662 newab->Deserialize (start);
1666 /* End PbbMessageIpv6 Class */
1668 PbbAddressBlock::PbbAddressBlock ()
1671 PbbAddressBlock::~PbbAddressBlock ()
1674 /* Manipulating the address block */
1676 PbbAddressBlock::AddressIterator
1677 PbbAddressBlock::AddressBegin (void)
1679 return m_addressList.begin();
1682 PbbAddressBlock::ConstAddressIterator
1683 PbbAddressBlock::AddressBegin (void) const
1685 return m_addressList.begin();
1688 PbbAddressBlock::AddressIterator
1689 PbbAddressBlock::AddressEnd (void)
1691 return m_addressList.end();
1694 PbbAddressBlock::ConstAddressIterator
1695 PbbAddressBlock::AddressEnd (void) const
1697 return m_addressList.end();
1701 PbbAddressBlock::AddressSize (void) const
1703 return m_addressList.size();
1707 PbbAddressBlock::AddressEmpty (void) const
1709 return m_addressList.empty();
1713 PbbAddressBlock::AddressFront (void) const
1715 return m_addressList.front();
1719 PbbAddressBlock::AddressBack (void) const
1721 return m_addressList.back();
1725 PbbAddressBlock::AddressPushFront (Address tlv)
1727 m_addressList.push_front(tlv);
1731 PbbAddressBlock::AddressPopFront (void)
1733 m_addressList.pop_front();
1737 PbbAddressBlock::AddressPushBack (Address tlv)
1739 m_addressList.push_back(tlv);
1743 PbbAddressBlock::AddressPopBack (void)
1745 m_addressList.pop_back();
1748 PbbAddressBlock::AddressIterator
1749 PbbAddressBlock::AddressErase (PbbAddressBlock::AddressIterator position)
1751 return m_addressList.erase(position);
1754 PbbAddressBlock::AddressIterator
1755 PbbAddressBlock::AddressErase (PbbAddressBlock::AddressIterator first,
1756 PbbAddressBlock::AddressIterator last)
1758 return m_addressList.erase(first, last);
1762 PbbAddressBlock::AddressClear (void)
1764 return m_addressList.clear();
1767 /* Manipulating the prefix list */
1769 PbbAddressBlock::PrefixIterator
1770 PbbAddressBlock::PrefixBegin (void)
1772 return m_prefixList.begin ();
1775 PbbAddressBlock::ConstPrefixIterator
1776 PbbAddressBlock::PrefixBegin (void) const
1778 return m_prefixList.begin ();
1781 PbbAddressBlock::PrefixIterator
1782 PbbAddressBlock::PrefixEnd (void)
1784 return m_prefixList.end ();
1787 PbbAddressBlock::ConstPrefixIterator
1788 PbbAddressBlock::PrefixEnd (void) const
1790 return m_prefixList.end ();
1794 PbbAddressBlock::PrefixSize (void) const
1796 return m_prefixList.size ();
1800 PbbAddressBlock::PrefixEmpty (void) const
1802 return m_prefixList.empty ();
1806 PbbAddressBlock::PrefixFront (void) const
1808 return m_prefixList.front ();
1812 PbbAddressBlock::PrefixBack (void) const
1814 return m_prefixList.back ();
1818 PbbAddressBlock::PrefixPushFront (uint8_t prefix)
1820 m_prefixList.push_front (prefix);
1824 PbbAddressBlock::PrefixPopFront (void)
1826 m_prefixList.pop_front ();
1830 PbbAddressBlock::PrefixPushBack (uint8_t prefix)
1832 m_prefixList.push_back (prefix);
1836 PbbAddressBlock::PrefixPopBack (void)
1838 m_prefixList.pop_back ();
1841 PbbAddressBlock::PrefixIterator
1842 PbbAddressBlock::PrefixInsert (PbbAddressBlock::PrefixIterator position, const uint8_t value)
1844 return m_prefixList.insert (position, value);
1847 PbbAddressBlock::PrefixIterator
1848 PbbAddressBlock::PrefixErase (PbbAddressBlock::PrefixIterator position)
1850 return m_prefixList.erase (position);
1853 PbbAddressBlock::PrefixIterator
1854 PbbAddressBlock::PrefixErase (PbbAddressBlock::PrefixIterator first, PbbAddressBlock::PrefixIterator last)
1856 return m_prefixList.erase (first, last);
1860 PbbAddressBlock::PrefixClear (void)
1862 m_prefixList.clear ();
1865 /* Manipulating the TLV block */
1867 PbbAddressBlock::TlvIterator
1868 PbbAddressBlock::TlvBegin (void)
1870 return m_addressTlvList.Begin();
1873 PbbAddressBlock::ConstTlvIterator
1874 PbbAddressBlock::TlvBegin (void) const
1876 return m_addressTlvList.Begin();
1879 PbbAddressBlock::TlvIterator
1880 PbbAddressBlock::TlvEnd (void)
1882 return m_addressTlvList.End();
1885 PbbAddressBlock::ConstTlvIterator
1886 PbbAddressBlock::TlvEnd (void) const
1888 return m_addressTlvList.End();
1892 PbbAddressBlock::TlvSize (void) const
1894 return m_addressTlvList.Size();
1898 PbbAddressBlock::TlvEmpty (void) const
1900 return m_addressTlvList.Empty();
1904 PbbAddressBlock::TlvFront (void)
1906 return m_addressTlvList.Front();
1909 const Ptr<PbbAddressTlv>
1910 PbbAddressBlock::TlvFront (void) const
1912 return m_addressTlvList.Front();
1916 PbbAddressBlock::TlvBack (void)
1918 return m_addressTlvList.Back();
1921 const Ptr<PbbAddressTlv>
1922 PbbAddressBlock::TlvBack (void) const
1924 return m_addressTlvList.Back();
1928 PbbAddressBlock::TlvPushFront (Ptr<PbbAddressTlv> tlv)
1930 m_addressTlvList.PushFront(tlv);
1934 PbbAddressBlock::TlvPopFront (void)
1936 m_addressTlvList.PopFront();
1940 PbbAddressBlock::TlvPushBack (Ptr<PbbAddressTlv> tlv)
1942 m_addressTlvList.PushBack(tlv);
1946 PbbAddressBlock::TlvPopBack (void)
1948 m_addressTlvList.PopBack();
1951 PbbAddressBlock::TlvIterator
1952 PbbAddressBlock::TlvErase (PbbAddressBlock::TlvIterator position)
1954 return m_addressTlvList.Erase(position);
1957 PbbAddressBlock::TlvIterator
1958 PbbAddressBlock::TlvErase (PbbAddressBlock::TlvIterator first,
1959 PbbAddressBlock::TlvIterator last)
1961 return m_addressTlvList.Erase(first, last);
1965 PbbAddressBlock::TlvClear (void)
1967 m_addressTlvList.Clear();
1970 PbbAddressBlock::GetSerializedSize (void) const
1972 /* num-addr + flags */
1975 if (AddressSize () == 1)
1977 size += GetAddressLength () + PrefixSize();
1979 else if (AddressSize () > 0)
1981 uint8_t head[GetAddressLength ()];
1982 uint8_t headlen = 0;
1983 uint8_t tail[GetAddressLength ()];
1984 uint8_t taillen = 0;
1986 GetHeadTail (head, headlen, tail, taillen);
1990 size += 1 + headlen;
1996 if (!HasZeroTail (tail, taillen))
2003 size += (GetAddressLength () - headlen - taillen) * AddressSize ();
2005 size += PrefixSize ();
2008 size += m_addressTlvList.GetSerializedSize ();
2014 PbbAddressBlock::Serialize (Buffer::Iterator &start) const
2016 start.WriteU8 (AddressSize ());
2018 if (AddressSize () == 1)
2022 uint8_t buf[GetAddressLength ()];
2023 SerializeAddress (buf, AddressBegin ());
2024 start.Write (buf, GetAddressLength ());
2026 if (PrefixSize () == 1)
2028 start.WriteU8 (PrefixFront ());
2031 else if (AddressSize () > 0)
2033 Buffer::Iterator bufref = start;
2037 uint8_t head[GetAddressLength ()];
2038 uint8_t tail[GetAddressLength ()];
2039 uint8_t headlen = 0;
2040 uint8_t taillen = 0;
2042 GetHeadTail (head, headlen, tail, taillen);
2047 start.WriteU8 (headlen);
2048 start.Write (head, headlen);
2053 start.WriteU8 (taillen);
2055 if (HasZeroTail (tail, taillen))
2057 flags |= AHAS_ZERO_TAIL;
2061 flags |= AHAS_FULL_TAIL;
2062 start.Write (tail, taillen);
2066 if (headlen + taillen < GetAddressLength ())
2068 uint8_t mid[GetAddressLength ()];
2069 for (PbbAddressBlock::ConstAddressIterator iter = AddressBegin ();
2070 iter != AddressEnd ();
2073 SerializeAddress (mid, iter);
2074 start.Write (mid + headlen, GetAddressLength () - headlen - taillen);
2078 flags |= GetPrefixFlags ();
2079 bufref.WriteU8 (flags);
2081 for (ConstPrefixIterator iter = PrefixBegin ();
2082 iter != PrefixEnd ();
2085 start.WriteU8 (*iter);
2089 m_addressTlvList.Serialize (start);
2093 PbbAddressBlock::Deserialize (Buffer::Iterator &start)
2095 uint8_t numaddr = start.ReadU8 ();
2096 uint8_t flags = start.ReadU8 ();
2100 uint8_t headlen = 0;
2101 uint8_t taillen = 0;
2102 uint8_t addrtmp[GetAddressLength ()];
2103 memset(addrtmp, 0, GetAddressLength ());
2105 if (flags & AHAS_HEAD)
2107 headlen = start.ReadU8 ();
2108 start.Read (addrtmp, headlen);
2111 if ((flags & AHAS_FULL_TAIL) ^ (flags & AHAS_ZERO_TAIL))
2113 taillen = start.ReadU8 ();
2115 if (flags & AHAS_FULL_TAIL)
2117 start.Read (addrtmp + GetAddressLength () - taillen, taillen);
2121 for (int i = 0; i < numaddr; i++)
2123 start.Read (addrtmp + headlen, GetAddressLength () - headlen - taillen);
2124 AddressPushBack (DeserializeAddress (addrtmp));
2127 if (flags & AHAS_SINGLE_PRE_LEN)
2129 PrefixPushBack (start.ReadU8 ());
2131 else if (flags & AHAS_MULTI_PRE_LEN)
2133 for (int i = 0; i < numaddr; i++)
2135 PrefixPushBack (start.ReadU8 ());
2140 m_addressTlvList.Deserialize (start);
2144 PbbAddressBlock::Print (std::ostream &os) const
2150 PbbAddressBlock::Print (std::ostream &os, int level) const
2152 std::string prefix = "";
2153 for (int i = 0; i < level; i++)
2155 prefix.append ("\t");
2158 os << prefix << "PbbAddressBlock {" << std::endl;
2159 os << prefix << "\taddresses = " << std::endl;
2160 for (ConstAddressIterator iter = AddressBegin ();
2161 iter != AddressEnd ();
2164 os << prefix << "\t\t";
2165 PrintAddress(os, iter);
2169 os << prefix << "\tprefixes = " << std::endl;
2170 for (ConstPrefixIterator iter = PrefixBegin ();
2171 iter != PrefixEnd ();
2174 os << prefix << "\t\t" << (int)(*iter) << std::endl;
2177 m_addressTlvList.Print (os, level+1);
2181 PbbAddressBlock::operator== (const PbbAddressBlock &other) const
2183 if (AddressSize () != other.AddressSize ())
2188 ConstAddressIterator tai, oai;
2189 for (tai = AddressBegin (), oai = other.AddressBegin ();
2190 tai != AddressEnd () && oai != other.AddressEnd ();
2199 if (PrefixSize () != other.PrefixSize ())
2204 ConstPrefixIterator tpi, opi;
2205 for (tpi = PrefixBegin (), opi = other.PrefixBegin ();
2206 tpi != PrefixEnd () && opi != other.PrefixEnd ();
2215 if (m_addressTlvList != other.m_addressTlvList)
2224 PbbAddressBlock::operator!= (const PbbAddressBlock &other) const
2226 return !(*this == other);
2230 PbbAddressBlock::GetPrefixFlags (void) const
2232 switch (PrefixSize ())
2238 return AHAS_SINGLE_PRE_LEN;
2241 return AHAS_MULTI_PRE_LEN;
2245 /* Quiet compiler */
2250 PbbAddressBlock::GetHeadTail (uint8_t *head, uint8_t &headlen,
2251 uint8_t *tail, uint8_t &taillen) const
2253 headlen = GetAddressLength ();
2256 /* Temporary automatic buffers to store serialized addresses */
2257 uint8_t * buflast = new uint8_t[GetAddressLength ()];
2258 uint8_t * bufcur = new uint8_t[GetAddressLength ()];
2261 SerializeAddress (buflast, AddressBegin ());
2263 /* Skip the first item */
2264 for (PbbAddressBlock::ConstAddressIterator iter = AddressBegin ()++;
2265 iter != AddressEnd ();
2268 SerializeAddress (bufcur, iter);
2271 for (i = 0; i < headlen; i++)
2273 if (buflast[i] != bufcur[i])
2280 /* If headlen == fulllen - 1, then tail is 0 */
2281 if (headlen <= GetAddressLength () - 1)
2283 for (i = GetAddressLength () - 1;
2284 GetAddressLength () - 1 - i <= taillen && i > headlen;
2287 if (buflast[i] != bufcur[i])
2292 taillen = GetAddressLength () - 1 - i;
2294 else if (headlen == 0)
2305 memcpy(head, bufcur, headlen);
2306 memcpy(tail, bufcur + (GetAddressLength () - taillen), taillen);
2313 PbbAddressBlock::HasZeroTail (const uint8_t *tail, uint8_t taillen) const
2316 for (i = 0; i < taillen; i++)
2323 return i == taillen;
2326 /* End PbbAddressBlock Class */
2328 PbbAddressBlockIpv4::PbbAddressBlockIpv4 ()
2332 PbbAddressBlockIpv4::~PbbAddressBlockIpv4 ()
2337 PbbAddressBlockIpv4::GetAddressLength (void) const
2343 PbbAddressBlockIpv4::SerializeAddress (uint8_t *buffer, ConstAddressIterator iter) const
2345 Ipv4Address::ConvertFrom (*iter).Serialize (buffer);
2349 PbbAddressBlockIpv4::DeserializeAddress (uint8_t *buffer) const
2351 return Ipv4Address::Deserialize (buffer);
2355 PbbAddressBlockIpv4::PrintAddress (std::ostream &os, ConstAddressIterator iter) const
2357 Ipv4Address::ConvertFrom (*iter).Print (os);
2360 /* End PbbAddressBlockIpv4 Class */
2362 PbbAddressBlockIpv6::PbbAddressBlockIpv6 ()
2366 PbbAddressBlockIpv6::~PbbAddressBlockIpv6 ()
2371 PbbAddressBlockIpv6::GetAddressLength (void) const
2377 PbbAddressBlockIpv6::SerializeAddress (uint8_t *buffer, ConstAddressIterator iter) const
2379 Ipv6Address::ConvertFrom (*iter).Serialize (buffer);
2383 PbbAddressBlockIpv6::DeserializeAddress (uint8_t *buffer) const
2385 return Ipv6Address::Deserialize (buffer);
2389 PbbAddressBlockIpv6::PrintAddress (std::ostream &os, ConstAddressIterator iter) const
2391 Ipv6Address::ConvertFrom (*iter).Print (os);
2394 /* End PbbAddressBlockIpv6 Class */
2396 PbbTlv::PbbTlv (void)
2398 m_hasTypeExt = false;
2399 m_hasIndexStart = false;
2400 m_hasIndexStop = false;
2401 m_isMultivalue = false;
2405 PbbTlv::~PbbTlv (void)
2407 m_value.RemoveAtEnd (m_value.GetSize ());
2411 PbbTlv::SetType (uint8_t type)
2417 PbbTlv::GetType (void) const
2423 PbbTlv::SetTypeExt (uint8_t typeExt)
2425 m_typeExt = typeExt;
2426 m_hasTypeExt = true;
2430 PbbTlv::GetTypeExt (void) const
2432 NS_ASSERT (HasTypeExt ());
2437 PbbTlv::HasTypeExt (void) const
2439 return m_hasTypeExt;
2443 PbbTlv::SetIndexStart (uint8_t index)
2445 m_indexStart = index;
2446 m_hasIndexStart = true;
2450 PbbTlv::GetIndexStart (void) const
2452 NS_ASSERT (HasIndexStart ());
2453 return m_indexStart;
2457 PbbTlv::HasIndexStart (void) const
2459 return m_hasIndexStart;
2463 PbbTlv::SetIndexStop (uint8_t index)
2465 m_indexStop = index;
2466 m_hasIndexStop = true;
2470 PbbTlv::GetIndexStop (void) const
2472 NS_ASSERT (HasIndexStop ());
2477 PbbTlv::HasIndexStop (void) const
2479 return m_hasIndexStop;
2483 PbbTlv::SetMultivalue (bool isMultivalue)
2485 m_isMultivalue = isMultivalue;
2489 PbbTlv::IsMultivalue (void) const
2491 return m_isMultivalue;
2495 PbbTlv::SetValue (Buffer start)
2502 PbbTlv::SetValue (const uint8_t * buffer, uint32_t size)
2505 m_value.AddAtStart (size);
2506 m_value.Begin ().Write (buffer, size);
2510 PbbTlv::GetValue (void) const
2512 NS_ASSERT (HasValue ());
2517 PbbTlv::HasValue (void) const
2523 PbbTlv::GetSerializedSize (void) const
2533 if (HasIndexStart ())
2538 if (HasIndexStop ())
2545 if (GetValue ().GetSize () > 255)
2553 size += GetValue ().GetSize ();
2560 PbbTlv::Serialize (Buffer::Iterator &start) const
2562 start.WriteU8 (GetType ());
2564 Buffer::Iterator bufref = start;
2570 flags |= THAS_TYPE_EXT;
2571 start.WriteU8 (GetTypeExt ());
2574 if (HasIndexStart ())
2576 start.WriteU8 (GetIndexStart ());
2578 if (HasIndexStop ())
2580 flags |= THAS_MULTI_INDEX;
2581 start.WriteU8 (GetIndexStop ());
2585 flags |= THAS_SINGLE_INDEX;
2591 flags |= THAS_VALUE;
2593 uint32_t size = GetValue ().GetSize ();
2596 flags |= THAS_EXT_LEN;
2597 start.WriteHtonU16 (size);
2601 start.WriteU8 (size);
2604 if (IsMultivalue ())
2606 flags |= TIS_MULTIVALUE;
2609 start.Write(GetValue ().Begin (), GetValue ().End ());
2612 bufref.WriteU8 (flags);
2616 PbbTlv::Deserialize (Buffer::Iterator &start)
2618 SetType (start.ReadU8 ());
2620 uint8_t flags = start.ReadU8 ();
2622 if (flags & THAS_TYPE_EXT)
2624 SetTypeExt (start.ReadU8 ());
2627 if (flags & THAS_MULTI_INDEX)
2629 SetIndexStart (start.ReadU8 ());
2630 SetIndexStop (start.ReadU8 ());
2632 else if (flags & THAS_SINGLE_INDEX)
2634 SetIndexStart (start.ReadU8 ());
2637 if (flags & THAS_VALUE)
2641 if (flags & THAS_EXT_LEN)
2643 len = start.ReadNtohU16 ();
2647 len = start.ReadU8 ();
2650 m_value.AddAtStart (len);
2652 Buffer::Iterator valueStart = start;
2654 m_value.Begin ().Write (valueStart, start);
2660 PbbTlv::Print (std::ostream &os) const
2666 PbbTlv::Print (std::ostream &os, int level) const
2668 std::string prefix = "";
2669 for (int i = 0; i < level; i++)
2671 prefix.append ("\t");
2674 os << prefix << "PbbTlv {" << std::endl;
2675 os << prefix << "\ttype = " << (int)GetType () << std::endl;
2679 os << prefix << "\ttypeext = " << (int)GetTypeExt () << std::endl;
2682 if (HasIndexStart ())
2684 os << prefix << "\tindexStart = " << (int)GetIndexStart () << std::endl;
2687 if (HasIndexStop ())
2689 os << prefix << "\tindexStop = " << (int)GetIndexStop () << std::endl;
2692 os << prefix << "\tisMultivalue = " << IsMultivalue () << std::endl;
2696 os << prefix << "\thas value; size = " << GetValue (). GetSize () << std::endl;
2699 os << prefix << "}" << std::endl;
2703 PbbTlv::operator== (const PbbTlv &other) const
2705 if (GetType () != other.GetType ())
2710 if (HasTypeExt () != other.HasTypeExt ())
2717 if (GetTypeExt () != other.GetTypeExt ())
2723 if (HasValue () != other.HasValue ())
2730 Buffer tv = GetValue ();
2731 Buffer ov = other.GetValue ();
2732 if (tv.GetSize () != ov.GetSize ())
2737 /* The docs say I probably shouldn't use Buffer::PeekData, but I think it
2738 * is justified in this case. */
2739 if (memcmp (tv.PeekData (), ov.PeekData (), tv.GetSize ()) != 0)
2748 PbbTlv::operator!= (const PbbTlv &other) const
2750 return !(*this == other);
2753 /* End PbbTlv Class */
2756 PbbAddressTlv::SetIndexStart (uint8_t index)
2758 PbbTlv::SetIndexStart (index);
2762 PbbAddressTlv::GetIndexStart (void) const
2764 return PbbTlv::GetIndexStart ();
2768 PbbAddressTlv::HasIndexStart (void) const
2770 return PbbTlv::HasIndexStart ();
2774 PbbAddressTlv::SetIndexStop (uint8_t index)
2776 PbbTlv::SetIndexStop (index);
2780 PbbAddressTlv::GetIndexStop (void) const
2782 return PbbTlv::GetIndexStop ();
2786 PbbAddressTlv::HasIndexStop (void) const
2788 return PbbTlv::HasIndexStop ();
2792 PbbAddressTlv::SetMultivalue (bool isMultivalue)
2794 PbbTlv::SetMultivalue (isMultivalue);
2798 PbbAddressTlv::IsMultivalue (void) const
2800 return PbbTlv::IsMultivalue ();
2803 } /* namespace ns3 */