A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
ipv6-extension-header-test-suite.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * This program is free software; you can redistribute it and/or modify
4  * it under the terms of the GNU General Public License version 2 as
5  * published by the Free Software Foundation;
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software
14  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
15  *
16  * Author: Fabian Mauchle <fabian.mauchle@hsr.ch>
17  */
18 
19 #include "ns3/test.h"
20 #include "ns3/ipv6-extension-header.h"
21 #include "ns3/ipv6-option-header.h"
22 
23 using namespace ns3;
24 
25 // ===========================================================================
26 // An empty option field must be filled with pad1 or padN header so theshape
27 // extension header's size is a multiple of 8.
28 //
29 // 0 31
30 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
31 // | Extension Destination Header | |
32 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ PadN Header +
33 // | |
34 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
35 // ===========================================================================
37 {
38 public:
39  TestEmptyOptionField () : TestCase ("TestEmptyOptionField") {}
40 
41  virtual void DoRun ()
42  {
44  NS_TEST_EXPECT_MSG_EQ (header.GetSerializedSize () % 8, 0, "length of extension header is not a multiple of 8");
45 
46  Buffer buf;
47  buf.AddAtStart (header.GetSerializedSize ());
48  header.Serialize (buf.Begin ());
49 
50  const uint8_t* data = buf.PeekData ();
51  NS_TEST_EXPECT_MSG_EQ (*(data+2), 1, "padding is missing"); //expecting a padN header
52  }
53 };
54 
55 // ===========================================================================
56 // An option without alignment requirement must not be padded
57 //
58 // 0 31
59 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
60 // | Extension Destination Header | OptionWithoutAlignmentHeader..|
61 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
62 // |..OptionWithoutAlignmentHeader | PadN Header |
63 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
64 // ===========================================================================
66 {
67 public:
68  static const uint8_t TYPE = 42;
69  virtual uint32_t GetSerializedSize () const
70  {
71  return 4;
72  }
73 
74  virtual void Serialize (Buffer::Iterator start) const
75  {
76  start.WriteU8 (TYPE);
77  start.WriteU8 (GetSerializedSize ()-2);
78  start.WriteU16 (0);
79  }
80 };
81 
82 
84 {
85 public:
86  TestOptionWithoutAlignment () : TestCase ("TestOptionWithoutAlignment") {}
87 
88  virtual void DoRun ()
89  {
91  OptionWithoutAlignmentHeader optionHeader;
92  header.AddOption (optionHeader);
93 
94 
95  NS_TEST_EXPECT_MSG_EQ (header.GetSerializedSize () % 8, 0, "length of extension header is not a multiple of 8");
96 
97  Buffer buf;
98  buf.AddAtStart (header.GetSerializedSize ());
99  header.Serialize (buf.Begin ());
100 
101  const uint8_t* data = buf.PeekData ();
102  NS_TEST_EXPECT_MSG_EQ (*(data+2), OptionWithoutAlignmentHeader::TYPE, "option without alignment is not first in header field");
103  }
104 };
105 
106 // ===========================================================================
107 // An option with alignment requirement must be padded accordingly (padding to
108 // a total size multiple of 8 is allowed)
109 //
110 // 0 31
111 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
112 // | Extension Destination Header | PadN Header |
113 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
114 // | OptionWithAlignmentHeader |
115 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
116 // | PadN Header | |
117 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +
118 // | Ipv6OptionJumbogramHeader |
119 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
120 // ===========================================================================
122 {
123 public:
124  static const uint8_t TYPE = 73;
125  virtual uint32_t GetSerializedSize () const
126  {
127  return 4;
128  }
129 
130  virtual void Serialize (Buffer::Iterator start) const
131  {
132  start.WriteU8 (TYPE);
133  start.WriteU8 (GetSerializedSize ()-2);
134  start.WriteU16 (0);
135  }
136 
137  virtual Alignment GetAlignment () const
138  {
139  return (Alignment){ 4,0};
140  }
141 };
142 
143 
145 {
146 public:
147  TestOptionWithAlignment () : TestCase ("TestOptionWithAlignment") {}
148 
149  virtual void DoRun ()
150  {
152  OptionWithAlignmentHeader optionHeader;
153  header.AddOption (optionHeader);
154  Ipv6OptionJumbogramHeader jumboHeader; //has an alignment of 4n+2
155  header.AddOption (jumboHeader);
156 
157  NS_TEST_EXPECT_MSG_EQ (header.GetSerializedSize () % 8, 0, "length of extension header is not a multiple of 8");
158 
159  Buffer buf;
160  buf.AddAtStart (header.GetSerializedSize ());
161  header.Serialize (buf.Begin ());
162 
163  const uint8_t* data = buf.PeekData ();
164  NS_TEST_EXPECT_MSG_EQ (*(data+2), 1, "padding is missing"); //expecting a padN header
165  NS_TEST_EXPECT_MSG_EQ (*(data+4), OptionWithAlignmentHeader::TYPE, "option with alignment is not padded correctly");
166  NS_TEST_EXPECT_MSG_EQ (*(data+8), 1, "padding is missing"); //expecting a padN header
167  NS_TEST_EXPECT_MSG_EQ (*(data+10), jumboHeader.GetType (), "option with alignment is not padded correctly");
168  }
169 };
170 
171 // ===========================================================================
172 // An option with an alignment that exactly matches the gap must not be padded
173 // (padding to a total size multiple of 8 is allowed)
174 //
175 // 0 31
176 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
177 // | Extension Destination Header | |
178 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +
179 // | Ipv6OptionJumbogramHeader |
180 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
181 // | OptionWithAlignmentHeader |
182 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
183 // | PadN Header |
184 // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
185 // ===========================================================================
186 
188 {
189 public:
190  TestFulfilledAlignment () : TestCase ("TestCorrectAlignment") {}
191 
192  virtual void DoRun ()
193  {
195  Ipv6OptionJumbogramHeader jumboHeader; //has an alignment of 4n+2
196  header.AddOption (jumboHeader);
197  OptionWithAlignmentHeader optionHeader;
198  header.AddOption (optionHeader);
199 
200  NS_TEST_EXPECT_MSG_EQ (header.GetSerializedSize () % 8, 0, "length of extension header is not a multiple of 8");
201 
202  Buffer buf;
203  buf.AddAtStart (header.GetSerializedSize ());
204  header.Serialize (buf.Begin ());
205 
206  const uint8_t* data = buf.PeekData ();
207  NS_TEST_EXPECT_MSG_EQ (*(data+2), jumboHeader.GetType (), "option with fulfilled alignment is padded anyway");
208  NS_TEST_EXPECT_MSG_EQ (*(data+8), OptionWithAlignmentHeader::TYPE, "option with fulfilled alignment is padded anyway");
209  }
210 };
211 
213 {
214 public:
216  : TestSuite ("ipv6-extension-header", UNIT)
217  {
218  AddTestCase (new TestEmptyOptionField, TestCase::QUICK);
219  AddTestCase (new TestOptionWithoutAlignment, TestCase::QUICK);
220  AddTestCase (new TestOptionWithAlignment, TestCase::QUICK);
221  AddTestCase (new TestFulfilledAlignment, TestCase::QUICK);
222 
223  }
224 };
225