1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2014 Universita' di Firenze, Italy
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: Tommaso Pecorella <tommaso.pecorella@unifi.it>
19  */
20 
21 #include "ripng-header.h"
22 #include "ns3/log.h"
23 
24 namespace ns3 {
25 
26 /*
27  * RipNgRte
28  */
29 NS_OBJECT_ENSURE_REGISTERED (RipNgRte);
30 
RipNgRte()31 RipNgRte::RipNgRte ()
32   : m_prefix ("::"), m_tag (0), m_prefixLen (0), m_metric (16)
33 {
34 }
35 
GetTypeId(void)36 TypeId RipNgRte::GetTypeId (void)
37 {
38   static TypeId tid = TypeId ("ns3::RipNgRte")
39     .SetParent<Header> ()
40     .SetGroupName ("Internet")
41     .AddConstructor<RipNgRte> ();
42   return tid;
43 }
44 
GetInstanceTypeId(void) const45 TypeId RipNgRte::GetInstanceTypeId (void) const
46 {
47   return GetTypeId ();
48 }
49 
Print(std::ostream & os) const50 void RipNgRte::Print (std::ostream & os) const
51 {
52   os << "prefix " << m_prefix << "/" << int(m_prefixLen) << " Metric " << int(m_metric) << " Tag " << int(m_tag);
53 }
54 
GetSerializedSize() const55 uint32_t RipNgRte::GetSerializedSize () const
56 {
57   return 20;
58 }
59 
Serialize(Buffer::Iterator i) const60 void RipNgRte::Serialize (Buffer::Iterator i) const
61 {
62   uint8_t tmp[16];
63 
64   m_prefix.Serialize (tmp);
65   i.Write (tmp, 16);
66 
67   i.WriteHtonU16 (m_tag);
68   i.WriteU8 (m_prefixLen);
69   i.WriteU8 (m_metric);
70 }
71 
Deserialize(Buffer::Iterator i)72 uint32_t RipNgRte::Deserialize (Buffer::Iterator i)
73 {
74   uint8_t tmp[16];
75 
76   i.Read (tmp, 16);
77   m_prefix.Set (tmp);
78   m_tag = i.ReadNtohU16 ();
79   m_prefixLen = i.ReadU8 ();
80   m_metric = i.ReadU8 ();
81 
82   return GetSerializedSize ();
83 }
84 
SetPrefix(Ipv6Address prefix)85 void RipNgRte::SetPrefix (Ipv6Address prefix)
86 {
87   m_prefix = prefix;
88 }
89 
GetPrefix() const90 Ipv6Address RipNgRte::GetPrefix () const
91 {
92   return m_prefix;
93 }
94 
SetPrefixLen(uint8_t prefixLen)95 void RipNgRte::SetPrefixLen (uint8_t prefixLen)
96 {
97   m_prefixLen = prefixLen;
98 }
99 
GetPrefixLen() const100 uint8_t RipNgRte::GetPrefixLen () const
101 {
102   return m_prefixLen;
103 }
104 
SetRouteTag(uint16_t routeTag)105 void RipNgRte::SetRouteTag (uint16_t routeTag)
106 {
107   m_tag = routeTag;
108 }
109 
GetRouteTag() const110 uint16_t RipNgRte::GetRouteTag () const
111 {
112   return m_tag;
113 }
114 
SetRouteMetric(uint8_t routeMetric)115 void RipNgRte::SetRouteMetric (uint8_t routeMetric)
116 {
117   m_metric = routeMetric;
118 }
119 
GetRouteMetric() const120 uint8_t RipNgRte::GetRouteMetric () const
121 {
122   return m_metric;
123 }
124 
125 
operator <<(std::ostream & os,const RipNgRte & h)126 std::ostream & operator << (std::ostream & os, const RipNgRte & h)
127 {
128   h.Print (os);
129   return os;
130 }
131 
132 /*
133  * RipNgHeader
134  */
135 NS_LOG_COMPONENT_DEFINE ("RipNgHeader");
136 NS_OBJECT_ENSURE_REGISTERED (RipNgHeader);
137 
RipNgHeader()138 RipNgHeader::RipNgHeader ()
139   : m_command (0)
140 {
141 }
142 
GetTypeId(void)143 TypeId RipNgHeader::GetTypeId (void)
144 {
145   static TypeId tid = TypeId ("ns3::RipNgHeader")
146     .SetParent<Header> ()
147     .SetGroupName ("Internet")
148     .AddConstructor<RipNgHeader> ();
149   return tid;
150 }
151 
GetInstanceTypeId(void) const152 TypeId RipNgHeader::GetInstanceTypeId (void) const
153 {
154   return GetTypeId ();
155 }
156 
Print(std::ostream & os) const157 void RipNgHeader::Print (std::ostream & os) const
158 {
159   os << "command " << int(m_command);
160   for (std::list<RipNgRte>::const_iterator iter = m_rteList.begin ();
161       iter != m_rteList.end (); iter ++)
162     {
163       os << " | ";
164       iter->Print (os);
165     }
166 }
167 
GetSerializedSize() const168 uint32_t RipNgHeader::GetSerializedSize () const
169 {
170   RipNgRte rte;
171   return 4 + m_rteList.size () * rte.GetSerializedSize ();
172 }
173 
Serialize(Buffer::Iterator start) const174 void RipNgHeader::Serialize (Buffer::Iterator start) const
175 {
176   Buffer::Iterator i = start;
177 
178   i.WriteU8 (uint8_t (m_command));
179   i.WriteU8 (1);
180   i.WriteU16 (0);
181 
182   for (std::list<RipNgRte>::const_iterator iter = m_rteList.begin ();
183       iter != m_rteList.end (); iter ++)
184     {
185       iter->Serialize (i);
186       i.Next(iter->GetSerializedSize ());
187     }
188 }
189 
Deserialize(Buffer::Iterator start)190 uint32_t RipNgHeader::Deserialize (Buffer::Iterator start)
191 {
192   Buffer::Iterator i = start;
193 
194   uint8_t temp;
195   temp = i.ReadU8 ();
196   if ((temp == REQUEST) || (temp == RESPONSE))
197     {
198       m_command = temp;
199     }
200   else
201     {
202       return 0;
203     }
204 
205   if (i.ReadU8 () != 1)
206     {
207       NS_LOG_LOGIC ("RIP received a message with mismatch version, ignoring.");
208       return 0;
209     }
210 
211   if (i.ReadU16 () != 0)
212     {
213       NS_LOG_LOGIC ("RIP received a message with invalid filled flags, ignoring.");
214       return 0;
215     }
216 
217   uint8_t rteNumber = i.GetRemainingSize ()/20;
218   for (uint8_t n=0; n<rteNumber; n++)
219     {
220       RipNgRte rte;
221       i.Next (rte.Deserialize (i));
222       m_rteList.push_back (rte);
223     }
224 
225   return GetSerializedSize ();
226 }
227 
SetCommand(RipNgHeader::Command_e command)228 void RipNgHeader::SetCommand (RipNgHeader::Command_e command)
229 {
230   m_command = command;
231 }
232 
GetCommand() const233 RipNgHeader::Command_e RipNgHeader::GetCommand () const
234 {
235   return RipNgHeader::Command_e (m_command);
236 }
237 
AddRte(RipNgRte rte)238 void RipNgHeader::AddRte (RipNgRte rte)
239 {
240   m_rteList.push_back (rte);
241 }
242 
ClearRtes()243 void RipNgHeader::ClearRtes ()
244 {
245   m_rteList.clear ();
246 }
247 
GetRteNumber(void) const248 uint16_t RipNgHeader::GetRteNumber (void) const
249 {
250   return m_rteList.size ();
251 }
252 
GetRteList(void) const253 std::list<RipNgRte> RipNgHeader::GetRteList (void) const
254 {
255   return m_rteList;
256 }
257 
258 
operator <<(std::ostream & os,const RipNgHeader & h)259 std::ostream & operator << (std::ostream & os, const RipNgHeader & h)
260 {
261   h.Print (os);
262   return os;
263 }
264 
265 
266 }
267 
268