@@ -12,6 +12,7 @@ extern "C" {
12
12
#include < Library/DebugLib.h>
13
13
#include " ../Ip6Impl.h"
14
14
#include " ../Ip6Option.h"
15
+ #include " Ip6OptionGoogleTest.h"
15
16
}
16
17
17
18
// ///////////////////////////////////////////////////////////////////////
@@ -127,3 +128,280 @@ TEST_F (Ip6OptionValidationTest, InvalidPrefixInfoOptionLengthShouldReturnFalse)
127
128
128
129
EXPECT_FALSE (Ip6IsNDOptionValid (option, optionLen));
129
130
}
131
+
132
+ // //////////////////////////////////////////////////////////////////////
133
+ // Ip6IsOptionValid Tests
134
+ // //////////////////////////////////////////////////////////////////////
135
+
136
+ // Define a fixture for your tests if needed
137
+ class Ip6IsOptionValidTest : public ::testing::Test {
138
+ protected:
139
+ // Add any setup code if needed
140
+ virtual void
141
+ SetUp (
142
+ )
143
+ {
144
+ // Initialize any resources or variables
145
+ }
146
+
147
+ // Add any cleanup code if needed
148
+ virtual void
149
+ TearDown (
150
+ )
151
+ {
152
+ // Clean up any resources or variables
153
+ }
154
+ };
155
+
156
+ // Test Description
157
+ // Verify that a NULL option is Invalid
158
+ TEST_F (Ip6IsOptionValidTest, NullOptionShouldReturnTrue) {
159
+ NET_BUF Packet = { 0 };
160
+ // we need to define enough of the packet to make the function work
161
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
162
+ IP6_SERVICE *IpSb = NULL ;
163
+
164
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
165
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
166
+ EFI_IP6_HEADER Ip6Header = { 0 };
167
+
168
+ Ip6Header.SourceAddress = SourceAddress;
169
+ Ip6Header.DestinationAddress = DestinationAddress;
170
+ Packet.Ip .Ip6 = &Ip6Header;
171
+
172
+ EXPECT_FALSE (Ip6IsOptionValid (IpSb, &Packet, NULL , 0 , 0 ));
173
+ }
174
+
175
+ // Test Description
176
+ // Verify that an unknown option with a length of 0 and type of <unknown> does not cause an infinite loop
177
+ TEST_F (Ip6IsOptionValidTest, VerifyNoInfiniteLoopOnUnknownOptionLength0) {
178
+ NET_BUF Packet = { 0 };
179
+ // we need to define enough of the packet to make the function work
180
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
181
+ UINT32 DeadCode = 0xDeadC0de ;
182
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
183
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
184
+
185
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
186
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
187
+ EFI_IP6_HEADER Ip6Header = { 0 };
188
+
189
+ Ip6Header.SourceAddress = SourceAddress;
190
+ Ip6Header.DestinationAddress = DestinationAddress;
191
+ Packet.Ip .Ip6 = &Ip6Header;
192
+
193
+ IP6_OPTION_HEADER optionHeader;
194
+
195
+ optionHeader.Type = 23 ; // Unknown Option
196
+ optionHeader.Length = 0 ; // This will cause an infinite loop if the function is not working correctly
197
+
198
+ // This should be a valid option even though the length is 0
199
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
200
+ }
201
+
202
+ // Test Description
203
+ // Verify that an unknown option with a length of 1 and type of <unknown> does not cause an infinite loop
204
+ TEST_F (Ip6IsOptionValidTest, VerifyNoInfiniteLoopOnUnknownOptionLength1) {
205
+ NET_BUF Packet = { 0 };
206
+ // we need to define enough of the packet to make the function work
207
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
208
+ UINT32 DeadCode = 0xDeadC0de ;
209
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
210
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
211
+
212
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
213
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
214
+ EFI_IP6_HEADER Ip6Header = { 0 };
215
+
216
+ Ip6Header.SourceAddress = SourceAddress;
217
+ Ip6Header.DestinationAddress = DestinationAddress;
218
+ Packet.Ip .Ip6 = &Ip6Header;
219
+
220
+ IP6_OPTION_HEADER optionHeader;
221
+
222
+ optionHeader.Type = 23 ; // Unknown Option
223
+ optionHeader.Length = 1 ; // This will cause an infinite loop if the function is not working correctly
224
+
225
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
226
+ }
227
+
228
+ // Test Description
229
+ // Verify that an unknown option with a length of 2 and type of <unknown> does not cause an infinite loop
230
+ TEST_F (Ip6IsOptionValidTest, VerifyIpSkipUnknownOption) {
231
+ NET_BUF Packet = { 0 };
232
+ // we need to define enough of the packet to make the function work
233
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
234
+ UINT32 DeadCode = 0xDeadC0de ;
235
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
236
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
237
+
238
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
239
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
240
+ EFI_IP6_HEADER Ip6Header = { 0 };
241
+
242
+ Ip6Header.SourceAddress = SourceAddress;
243
+ Ip6Header.DestinationAddress = DestinationAddress;
244
+ Packet.Ip .Ip6 = &Ip6Header;
245
+
246
+ IP6_OPTION_HEADER optionHeader;
247
+
248
+ optionHeader.Type = 23 ; // Unknown Option
249
+ optionHeader.Length = 2 ; // Valid length for an unknown option
250
+
251
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
252
+ }
253
+
254
+ // Test Description
255
+ // Verify that Ip6OptionPad1 is valid with a length of 0
256
+ TEST_F (Ip6IsOptionValidTest, VerifyIp6OptionPad1) {
257
+ NET_BUF Packet = { 0 };
258
+ // we need to define enough of the packet to make the function work
259
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
260
+ UINT32 DeadCode = 0xDeadC0de ;
261
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
262
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
263
+
264
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
265
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
266
+ EFI_IP6_HEADER Ip6Header = { 0 };
267
+
268
+ Ip6Header.SourceAddress = SourceAddress;
269
+ Ip6Header.DestinationAddress = DestinationAddress;
270
+ Packet.Ip .Ip6 = &Ip6Header;
271
+
272
+ IP6_OPTION_HEADER optionHeader;
273
+
274
+ optionHeader.Type = Ip6OptionPad1;
275
+ optionHeader.Length = 0 ;
276
+
277
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
278
+ }
279
+
280
+ // Test Description
281
+ // Verify that Ip6OptionPadN doesn't overflow with various lengths
282
+ TEST_F (Ip6IsOptionValidTest, VerifyIp6OptionPadN) {
283
+ NET_BUF Packet = { 0 };
284
+ // we need to define enough of the packet to make the function work
285
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
286
+ UINT32 DeadCode = 0xDeadC0de ;
287
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
288
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
289
+
290
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
291
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
292
+ EFI_IP6_HEADER Ip6Header = { 0 };
293
+
294
+ Ip6Header.SourceAddress = SourceAddress;
295
+ Ip6Header.DestinationAddress = DestinationAddress;
296
+ Packet.Ip .Ip6 = &Ip6Header;
297
+
298
+ IP6_OPTION_HEADER optionHeader;
299
+
300
+ optionHeader.Type = Ip6OptionPadN;
301
+ optionHeader.Length = 0xFF ;
302
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
303
+
304
+ optionHeader.Length = 0xFE ;
305
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
306
+
307
+ optionHeader.Length = 0xFD ;
308
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
309
+
310
+ optionHeader.Length = 0xFC ;
311
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
312
+ }
313
+
314
+ // Test Description
315
+ // Verify an unknown option doesn't cause an infinite loop with various lengths
316
+ TEST_F (Ip6IsOptionValidTest, VerifyNoInfiniteLoopOnUnknownOptionLengthAttemptOverflow) {
317
+ NET_BUF Packet = { 0 };
318
+ // we need to define enough of the packet to make the function work
319
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
320
+ UINT32 DeadCode = 0xDeadC0de ;
321
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
322
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
323
+
324
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
325
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
326
+ EFI_IP6_HEADER Ip6Header = { 0 };
327
+
328
+ Ip6Header.SourceAddress = SourceAddress;
329
+ Ip6Header.DestinationAddress = DestinationAddress;
330
+ Packet.Ip .Ip6 = &Ip6Header;
331
+
332
+ IP6_OPTION_HEADER optionHeader;
333
+
334
+ optionHeader.Type = 23 ; // Unknown Option
335
+ optionHeader.Length = 0xFF ;
336
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
337
+
338
+ optionHeader.Length = 0xFE ;
339
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
340
+
341
+ optionHeader.Length = 0xFD ;
342
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
343
+
344
+ optionHeader.Length = 0xFC ;
345
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, (UINT8 *)&optionHeader, sizeof (optionHeader), 0 ));
346
+ }
347
+
348
+ // Test Description
349
+ // Verify that the function supports multiple options
350
+ TEST_F (Ip6IsOptionValidTest, MultiOptionSupport) {
351
+ UINT16 HdrLen;
352
+ NET_BUF Packet = { 0 };
353
+ // we need to define enough of the packet to make the function work
354
+ // The function being tested will pass IpSb to Ip6SendIcmpError which is defined above
355
+ UINT32 DeadCode = 0xDeadC0de ;
356
+ // Don't actually use this pointer, just pass it to the function, nothing will be done with it
357
+ IP6_SERVICE *IpSb = (IP6_SERVICE *)&DeadCode;
358
+
359
+ EFI_IPv6_ADDRESS SourceAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
360
+ EFI_IPv6_ADDRESS DestinationAddress = { 0x20 , 0x01 , 0x0d , 0xb8 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0x00 , 0xff , 0x00 , 0x00 , 0x42 , 0x83 , 0x29 };
361
+ EFI_IP6_HEADER Ip6Header = { 0 };
362
+
363
+ Ip6Header.SourceAddress = SourceAddress;
364
+ Ip6Header.DestinationAddress = DestinationAddress;
365
+ Packet.Ip .Ip6 = &Ip6Header;
366
+
367
+ UINT8 ExtHdr[1024 ] = { 0 };
368
+ UINT8 *Cursor = ExtHdr;
369
+ IP6_OPTION_HEADER *Option = (IP6_OPTION_HEADER *)ExtHdr;
370
+
371
+ // Let's start chaining options
372
+
373
+ Option->Type = 23 ; // Unknown Option
374
+ Option->Length = 0xFC ;
375
+
376
+ Cursor += sizeof (IP6_OPTION_HEADER) + 0xFC ;
377
+
378
+ Option = (IP6_OPTION_HEADER *)Cursor;
379
+ Option->Type = Ip6OptionPad1;
380
+
381
+ Cursor += sizeof (1 );
382
+
383
+ // Type and length aren't processed, instead it just moves the pointer forward by 4 bytes
384
+ Option = (IP6_OPTION_HEADER *)Cursor;
385
+ Option->Type = Ip6OptionRouterAlert;
386
+ Option->Length = 4 ;
387
+
388
+ Cursor += sizeof (IP6_OPTION_HEADER) + 4 ;
389
+
390
+ Option = (IP6_OPTION_HEADER *)Cursor;
391
+ Option->Type = Ip6OptionPadN;
392
+ Option->Length = 0xFC ;
393
+
394
+ Cursor += sizeof (IP6_OPTION_HEADER) + 0xFC ;
395
+
396
+ Option = (IP6_OPTION_HEADER *)Cursor;
397
+ Option->Type = Ip6OptionRouterAlert;
398
+ Option->Length = 4 ;
399
+
400
+ Cursor += sizeof (IP6_OPTION_HEADER) + 4 ;
401
+
402
+ // Total 524
403
+
404
+ HdrLen = (UINT16)(Cursor - ExtHdr);
405
+
406
+ EXPECT_TRUE (Ip6IsOptionValid (IpSb, &Packet, ExtHdr, HdrLen, 0 ));
407
+ }
0 commit comments