1 /*
2 * FreeRTOS+TCP <DEVELOPMENT BRANCH>
3 * Copyright (C) 2022 Amazon.com, Inc. or its affiliates. All Rights Reserved.
4 *
5 * SPDX-License-Identifier: MIT
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining a copy of
8 * this software and associated documentation files (the "Software"), to deal in
9 * the Software without restriction, including without limitation the rights to
10 * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
11 * the Software, and to permit persons to whom the Software is furnished to do so,
12 * subject to the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be included in all
15 * copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
19 * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
20 * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
21 * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 *
24 * http://aws.amazon.com/freertos
25 * http://www.FreeRTOS.org
26 */
27
28
29 /* Include Unity header */
30 #include "unity.h"
31
32 /* Include standard libraries */
33 #include <stdlib.h>
34 #include <string.h>
35 #include <stdint.h>
36
37 #include "mock_task.h"
38 #include "mock_list.h"
39
40 /* This must come after list.h is included (in this case, indirectly
41 * by mock_list.h). */
42 #include "mock_Sockets_list_macros.h"
43 #include "mock_queue.h"
44 #include "mock_event_groups.h"
45 #include "mock_portable.h"
46
47 #include "mock_FreeRTOS_IP.h"
48 #include "mock_FreeRTOS_IP_Private.h"
49 #include "mock_NetworkBufferManagement.h"
50 #include "mock_FreeRTOS_Stream_Buffer.h"
51 #include "mock_FreeRTOS_TCP_WIN.h"
52 #include "mock_FreeRTOS_IPv4_Sockets.h"
53 #include "mock_FreeRTOS_IPv6_Sockets.h"
54
55 #include "FreeRTOS_Sockets.h"
56
57 #include "FreeRTOS_Sockets_stubs.c"
58 #include "catch_assert.h"
59
60 #include "FreeRTOSIPConfig.h"
61
62 /* =========================== EXTERN VARIABLES =========================== */
63
64 #define TEST_MAX_UDPV4_PAYLOAD_LENGTH ipconfigNETWORK_MTU - ( ipSIZE_OF_IPv4_HEADER + ipSIZE_OF_UDP_HEADER )
65 #define TEST_MAX_UDPV6_PAYLOAD_LENGTH ipconfigNETWORK_MTU - ( ipSIZE_OF_IPv6_HEADER + ipSIZE_OF_UDP_HEADER )
66
67 /* ============================== Test Cases ============================== */
68
69 /**
70 * @brief NULL socket.
71 */
test_FreeRTOS_recvfrom_NullSocket(void)72 void test_FreeRTOS_recvfrom_NullSocket( void )
73 {
74 int32_t lReturn;
75 Socket_t xSocket = NULL;
76 void * pvBuffer;
77 size_t uxBufferLength;
78 BaseType_t xFlags = 0;
79 struct freertos_sockaddr * pxSourceAddress;
80 socklen_t * pxSourceAddressLength;
81
82 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
83
84 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINVAL, lReturn );
85 }
86
87 /**
88 * @brief Receiving from a TCP socket (while a UDP socket should be called).
89 */
test_FreeRTOS_recvfrom_TCPSocket(void)90 void test_FreeRTOS_recvfrom_TCPSocket( void )
91 {
92 int32_t lReturn;
93 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
94 Socket_t xSocket = ( Socket_t ) ucSocket;
95 void * pvBuffer;
96 size_t uxBufferLength;
97 BaseType_t xFlags = 0;
98 struct freertos_sockaddr * pxSourceAddress = NULL;
99 socklen_t * pxSourceAddressLength = NULL;
100
101 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
102
103 xSocket->ucProtocol = FREERTOS_IPPROTO_TCP;
104
105 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
106
107 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
108
109 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINVAL, lReturn );
110 }
111
112 /**
113 * @brief Call to the function is interrupted.
114 */
test_FreeRTOS_recvfrom_NonBlockingInterrupted(void)115 void test_FreeRTOS_recvfrom_NonBlockingInterrupted( void )
116 {
117 int32_t lReturn;
118 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
119 Socket_t xSocket = ( Socket_t ) ucSocket;
120 void * pvBuffer;
121 size_t uxBufferLength;
122 BaseType_t xFlags = 0;
123 struct freertos_sockaddr * pxSourceAddress;
124 socklen_t * pxSourceAddressLength;
125
126 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
127
128 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
129
130 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
131
132 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
133
134 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( EventBits_t ) eSOCKET_INTR, pdTRUE, pdFALSE, 0, eSOCKET_INTR );
135
136 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
137
138 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINTR, lReturn );
139 }
140
141 /**
142 * @brief Non blocking call which will block.
143 */
test_FreeRTOS_recvfrom_NonBlocking(void)144 void test_FreeRTOS_recvfrom_NonBlocking( void )
145 {
146 int32_t lReturn;
147 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
148 Socket_t xSocket = ( Socket_t ) ucSocket;
149 void * pvBuffer;
150 size_t uxBufferLength;
151 BaseType_t xFlags = 0;
152 struct freertos_sockaddr * pxSourceAddress;
153 socklen_t * pxSourceAddressLength;
154
155 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
156
157 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
158
159 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
160
161 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
162
163 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( EventBits_t ) eSOCKET_INTR, pdTRUE, pdFALSE, 0, ~eSOCKET_INTR );
164
165 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
166
167 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EWOULDBLOCK, lReturn );
168 }
169
170 /**
171 * @brief Non-blocking flag set but nothing received by the socket yet.
172 */
test_FreeRTOS_recvfrom_NonBlockingFlagSet(void)173 void test_FreeRTOS_recvfrom_NonBlockingFlagSet( void )
174 {
175 int32_t lReturn;
176 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
177 Socket_t xSocket = ( Socket_t ) ucSocket;
178 void * pvBuffer;
179 size_t uxBufferLength;
180 BaseType_t xFlags = FREERTOS_MSG_DONTWAIT;
181 struct freertos_sockaddr * pxSourceAddress;
182 socklen_t * pxSourceAddressLength;
183
184 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
185
186 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
187 xSocket->xReceiveBlockTime = 0x123;
188
189 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
190
191 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
192
193 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
194
195 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EWOULDBLOCK, lReturn );
196 }
197
198 /**
199 * @brief Blocking read times out.
200 */
test_FreeRTOS_recvfrom_BlockingButTimeout(void)201 void test_FreeRTOS_recvfrom_BlockingButTimeout( void )
202 {
203 int32_t lReturn;
204 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
205 Socket_t xSocket = ( Socket_t ) ucSocket;
206 void * pvBuffer;
207 size_t uxBufferLength;
208 BaseType_t xFlags = 0;
209 struct freertos_sockaddr * pxSourceAddress;
210 socklen_t * pxSourceAddressLength;
211
212 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
213
214 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
215 xSocket->xReceiveBlockTime = 0x123;
216
217 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
218
219 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
220
221 vTaskSetTimeOutState_ExpectAnyArgs();
222
223 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
224
225 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
226
227 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
228
229 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
230
231 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EWOULDBLOCK, lReturn );
232 }
233
234 /**
235 * @brief Blocking read - timeout in second iteration.
236 */
test_FreeRTOS_recvfrom_BlockingButTimeoutSecondTime(void)237 void test_FreeRTOS_recvfrom_BlockingButTimeoutSecondTime( void )
238 {
239 int32_t lReturn;
240 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
241 Socket_t xSocket = ( Socket_t ) ucSocket;
242 void * pvBuffer;
243 size_t uxBufferLength;
244 BaseType_t xFlags = 0;
245 struct freertos_sockaddr * pxSourceAddress;
246 socklen_t * pxSourceAddressLength;
247
248 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
249
250 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
251 xSocket->xReceiveBlockTime = 0x123;
252
253 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
254
255 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
256
257 vTaskSetTimeOutState_ExpectAnyArgs();
258
259 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
260
261 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
262
263 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdFALSE );
264
265 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
266
267 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
268
269 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
270
271 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
272
273 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EWOULDBLOCK, lReturn );
274 }
275
276 /**
277 * @brief Blocking read interrupted.
278 */
test_FreeRTOS_recvfrom_BlockingButInterrupted(void)279 void test_FreeRTOS_recvfrom_BlockingButInterrupted( void )
280 {
281 int32_t lReturn;
282 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
283 Socket_t xSocket = ( Socket_t ) ucSocket;
284 void * pvBuffer;
285 size_t uxBufferLength;
286 BaseType_t xFlags = 0;
287 struct freertos_sockaddr * pxSourceAddress;
288 socklen_t * pxSourceAddressLength;
289
290 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
291
292 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
293 xSocket->xReceiveBlockTime = 0x123;
294
295 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
296 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
297
298 vTaskSetTimeOutState_ExpectAnyArgs();
299
300 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, eSOCKET_INTR );
301
302 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
303
304 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINTR, lReturn );
305 }
306
307 /**
308 * @brief Blocking read interrupted and received.
309 */
test_FreeRTOS_recvfrom_BlockingButInterruptedAndReceived(void)310 void test_FreeRTOS_recvfrom_BlockingButInterruptedAndReceived( void )
311 {
312 int32_t lReturn;
313 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
314 Socket_t xSocket = ( Socket_t ) ucSocket;
315 void * pvBuffer;
316 size_t uxBufferLength;
317 BaseType_t xFlags = 0;
318 struct freertos_sockaddr * pxSourceAddress;
319 socklen_t * pxSourceAddressLength;
320
321 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
322
323 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
324 xSocket->xReceiveBlockTime = 0x123;
325
326 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
327 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
328
329 vTaskSetTimeOutState_ExpectAnyArgs();
330
331 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, eSOCKET_INTR | eSOCKET_RECEIVE );
332
333 xEventGroupSetBits_ExpectAndReturn( xSocket->xEventGroup, ( EventBits_t ) eSOCKET_RECEIVE, pdFALSE );
334
335 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, pxSourceAddress, pxSourceAddressLength );
336
337 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINTR, lReturn );
338 }
339
340 /**
341 * @brief Blocking read socket gets a packet while it is waiting. However, the packet
342 * is only a UDP header.
343 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_JustUDPHeader(void)344 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_JustUDPHeader( void )
345 {
346 int32_t lReturn;
347 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
348 Socket_t xSocket = ( Socket_t ) ucSocket;
349 char pvBuffer[ ipconfigTCP_MSS ];
350 size_t uxBufferLength = ipconfigTCP_MSS;
351 BaseType_t xFlags = 0;
352 struct freertos_sockaddr xSourceAddress;
353 socklen_t xSourceAddressLength;
354 ListItem_t xListItem;
355 NetworkBufferDescriptor_t xNetworkBuffer;
356 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
357
358 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
359 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t );
360 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
361 xNetworkBuffer.usPort = 0xABCD;
362
363 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
364 memset( &xListItem, 0, sizeof( ListItem_t ) );
365 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
366 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
367
368 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
369 xSocket->xReceiveBlockTime = 0x123;
370 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
371
372 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
373
374 xListItem.pvOwner = &xNetworkBuffer;
375 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
376
377 vTaskSetTimeOutState_ExpectAnyArgs();
378
379 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
380
381 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
382
383 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
384
385 uxListRemove_ExpectAndReturn( &( xNetworkBuffer.xBufferListItem ), 0 );
386
387 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
388
389 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xSourceAddress, ipUDP_PAYLOAD_OFFSET_IPv4 );
390
391 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
392
393 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, &xSourceAddressLength );
394
395 TEST_ASSERT_EQUAL( 0, lReturn );
396 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
397 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, pvBuffer, ipconfigTCP_MSS );
398 }
399
400 /**
401 * @brief Blocking read socket gets a packet while it is waiting. However, the packet
402 * is UDP header and 100 bytes.
403 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100(void)404 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100( void )
405 {
406 int32_t lReturn;
407 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
408 Socket_t xSocket = ( Socket_t ) ucSocket;
409 char pvBuffer[ ipconfigTCP_MSS ];
410 size_t uxBufferLength = ipconfigTCP_MSS;
411 BaseType_t xFlags = 0;
412 struct freertos_sockaddr xSourceAddress;
413 socklen_t xSourceAddressLength;
414 ListItem_t xListItem;
415 NetworkBufferDescriptor_t xNetworkBuffer;
416 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
417
418 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
419 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
420 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
421 xNetworkBuffer.usPort = 0xABCD;
422
423 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
424 memset( &xListItem, 0, sizeof( ListItem_t ) );
425 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
426 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
427
428 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
429 xSocket->xReceiveBlockTime = 0x123;
430
431 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
432
433 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
434
435 xListItem.pvOwner = &xNetworkBuffer;
436 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
437
438 vTaskSetTimeOutState_ExpectAnyArgs();
439
440 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
441
442 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
443
444 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
445
446 uxListRemove_ExpectAndReturn( &( xNetworkBuffer.xBufferListItem ), 0 );
447
448 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
449
450 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xSourceAddress, ipUDP_PAYLOAD_OFFSET_IPv4 );
451
452 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
453
454 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, &xSourceAddressLength );
455
456 TEST_ASSERT_EQUAL( 100, lReturn );
457 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
458 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, 100 );
459 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, &pvBuffer[ 100 ], ipconfigTCP_MSS - 100 );
460 }
461
462 /**
463 * @brief Blocking read socket gets a packet while it is waiting. However, the packet
464 * is UDP header and 100 bytes.
465 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall(void)466 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall( void )
467 {
468 int32_t lReturn;
469 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
470 Socket_t xSocket = ( Socket_t ) ucSocket;
471 char pvBuffer[ ipconfigTCP_MSS ];
472 size_t uxBufferLength = 50;
473 BaseType_t xFlags = 0;
474 struct freertos_sockaddr xSourceAddress;
475 socklen_t xSourceAddressLength;
476 ListItem_t xListItem;
477 NetworkBufferDescriptor_t xNetworkBuffer;
478 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
479
480 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
481 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
482 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
483 xNetworkBuffer.usPort = 0xABCD;
484
485 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
486 memset( &xListItem, 0, sizeof( ListItem_t ) );
487 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
488 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
489
490 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
491 xSocket->xReceiveBlockTime = 0x123;
492
493 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
494
495 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
496
497 xListItem.pvOwner = &xNetworkBuffer;
498 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
499
500 vTaskSetTimeOutState_ExpectAnyArgs();
501
502 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
503
504 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
505
506 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
507
508 uxListRemove_ExpectAndReturn( &( xNetworkBuffer.xBufferListItem ), 0 );
509
510 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
511
512 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xSourceAddress, ipUDP_PAYLOAD_OFFSET_IPv4 );
513
514 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
515
516 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, &xSourceAddressLength );
517
518 TEST_ASSERT_EQUAL( 50, lReturn );
519 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
520 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, uxBufferLength );
521 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, &pvBuffer[ uxBufferLength ], ipconfigTCP_MSS - uxBufferLength );
522 }
523
524 /**
525 * @brief Blocking read socket gets a packet while it is waiting. The packet
526 * is UDP header and 100 bytes. But the buffer is small and the receive
527 * call is used to peek in the list.
528 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_Peek(void)529 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_Peek( void )
530 {
531 int32_t lReturn;
532 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
533 Socket_t xSocket = ( Socket_t ) ucSocket;
534 char pvBuffer[ ipconfigTCP_MSS ];
535 size_t uxBufferLength = 50;
536 BaseType_t xFlags = FREERTOS_MSG_PEEK;
537 struct freertos_sockaddr xSourceAddress;
538 socklen_t xSourceAddressLength;
539 ListItem_t xListItem;
540 NetworkBufferDescriptor_t xNetworkBuffer;
541 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
542
543 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
544 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
545 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
546 xNetworkBuffer.usPort = 0xABCD;
547
548 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
549 memset( &xListItem, 0, sizeof( ListItem_t ) );
550 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
551 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
552
553 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
554 xSocket->xReceiveBlockTime = 0x123;
555
556 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
557
558 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
559
560 xListItem.pvOwner = &xNetworkBuffer;
561 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
562
563 vTaskSetTimeOutState_ExpectAnyArgs();
564
565 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
566
567 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
568
569 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
570
571 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
572
573 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xSourceAddress, ipUDP_PAYLOAD_OFFSET_IPv4 );
574
575 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, &xSourceAddressLength );
576
577 TEST_ASSERT_EQUAL( 50, lReturn );
578 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
579 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, uxBufferLength );
580 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, &pvBuffer[ uxBufferLength ], ipconfigTCP_MSS - uxBufferLength );
581 }
582
583 /**
584 * @brief Blocking read socket gets a packet while it is waiting. The packet
585 * is UDP header and 100 bytes. But the buffer is small and the receive
586 * call is used to peek in the list. The source address param passed is NULL.
587 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_Peek_SourceAddrNULL(void)588 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_Peek_SourceAddrNULL( void )
589 {
590 int32_t lReturn;
591 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
592 Socket_t xSocket = ( Socket_t ) ucSocket;
593 char pvBuffer[ ipconfigTCP_MSS ];
594 size_t uxBufferLength = 50;
595 BaseType_t xFlags = FREERTOS_MSG_PEEK;
596 socklen_t xSourceAddressLength;
597 ListItem_t xListItem;
598 NetworkBufferDescriptor_t xNetworkBuffer;
599 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
600
601 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
602 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
603 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
604 xNetworkBuffer.usPort = 0xABCD;
605
606 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
607 memset( &xListItem, 0, sizeof( ListItem_t ) );
608 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
609 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
610
611 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
612 xSocket->xReceiveBlockTime = 0x123;
613
614 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
615
616 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
617
618 xListItem.pvOwner = &xNetworkBuffer;
619 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
620
621 vTaskSetTimeOutState_ExpectAnyArgs();
622
623 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
624
625 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
626
627 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
628
629 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
630
631 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, NULL, ipUDP_PAYLOAD_OFFSET_IPv4 );
632
633 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, NULL, &xSourceAddressLength );
634
635 TEST_ASSERT_EQUAL( 50, lReturn );
636 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
637 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, uxBufferLength );
638 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, &pvBuffer[ uxBufferLength ], ipconfigTCP_MSS - uxBufferLength );
639 }
640
641 /**
642 * @brief Blocking read socket gets a packet while it is waiting. The packet
643 * is UDP header and 100 bytes. But the buffer is small and the receive
644 * call is used to peek in the list with zero copy flag.
645 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_ZeroCopyAndPeek(void)646 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_Packet100SizeSmall_ZeroCopyAndPeek( void )
647 {
648 int32_t lReturn;
649 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
650 Socket_t xSocket = ( Socket_t ) ucSocket;
651 char * pvBuffer;
652 size_t uxBufferLength = 50;
653 BaseType_t xFlags = FREERTOS_ZERO_COPY;
654 socklen_t xSourceAddressLength;
655 ListItem_t xListItem;
656 NetworkBufferDescriptor_t xNetworkBuffer;
657 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
658
659 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
660 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
661 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
662 xNetworkBuffer.usPort = 0xABCD;
663
664 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
665 memset( &xListItem, 0, sizeof( ListItem_t ) );
666 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
667
668 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
669 xSocket->xReceiveBlockTime = 0x123;
670
671 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
672
673 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
674
675 xListItem.pvOwner = &xNetworkBuffer;
676 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
677
678 vTaskSetTimeOutState_ExpectAnyArgs();
679
680 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
681
682 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
683
684 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
685
686 uxListRemove_ExpectAndReturn( &xNetworkBuffer.xBufferListItem, 0U );
687
688 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
689
690 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, NULL, ipUDP_PAYLOAD_OFFSET_IPv4 );
691
692 lReturn = FreeRTOS_recvfrom( xSocket, &pvBuffer, uxBufferLength, xFlags, NULL, &xSourceAddressLength );
693
694 TEST_ASSERT_EQUAL( 100, lReturn );
695 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
696 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, 100 );
697 }
698
699 /**
700 * @brief Blocking read socket gets a packet as soon as the function is called. The packet
701 * is UDP header and 100 bytes. But the buffer is small and the receive
702 * call is used to peek in the list.
703 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBegining_Packet100SizeSmall_ZeroCopyAndPeek(void)704 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBegining_Packet100SizeSmall_ZeroCopyAndPeek( void )
705 {
706 int32_t lReturn;
707 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
708 Socket_t xSocket = ( Socket_t ) ucSocket;
709 char * pvBuffer;
710 size_t uxBufferLength = 50;
711 BaseType_t xFlags = FREERTOS_MSG_PEEK | FREERTOS_ZERO_COPY;
712 socklen_t xSourceAddressLength;
713 ListItem_t xListItem;
714 NetworkBufferDescriptor_t xNetworkBuffer;
715 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
716
717 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
718 xNetworkBuffer.xDataLength = sizeof( UDPPacket_t ) + 100;
719 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
720 xNetworkBuffer.usPort = 0xABCD;
721
722 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
723 memset( &xListItem, 0, sizeof( ListItem_t ) );
724 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
725
726 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
727 xSocket->xReceiveBlockTime = 0x123;
728
729 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
730
731 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
732
733 xListItem.pvOwner = &xNetworkBuffer;
734 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
735
736 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
737
738 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv4_HEADER );
739
740 xRecv_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, NULL, ipUDP_PAYLOAD_OFFSET_IPv4 );
741
742 lReturn = FreeRTOS_recvfrom( xSocket, &pvBuffer, uxBufferLength, xFlags, NULL, &xSourceAddressLength );
743
744 TEST_ASSERT_EQUAL( 100, lReturn );
745 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
746 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, 100 );
747 }
748
749 /**
750 * @brief Blocking read socket gets a packet while it is waiting. However, the packet
751 * is UDPv6 header and 100 bytes.
752 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_IPv6Packet100(void)753 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_IPv6Packet100( void )
754 {
755 int32_t lReturn;
756 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
757 Socket_t xSocket = ( Socket_t ) ucSocket;
758 char pvBuffer[ ipconfigTCP_MSS ];
759 size_t uxBufferLength = ipconfigTCP_MSS;
760 BaseType_t xFlags = 0;
761 struct freertos_sockaddr xSourceAddress;
762 ListItem_t xListItem;
763 NetworkBufferDescriptor_t xNetworkBuffer;
764 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
765
766 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
767 xNetworkBuffer.xDataLength = sizeof( UDPPacket_IPv6_t ) + 100;
768 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
769 xNetworkBuffer.usPort = 0xABCD;
770
771 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
772 memset( &xListItem, 0, sizeof( ListItem_t ) );
773 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
774 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
775
776 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
777 xSocket->xReceiveBlockTime = 0x123;
778
779 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
780
781 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
782
783 xListItem.pvOwner = &xNetworkBuffer;
784 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
785
786 vTaskSetTimeOutState_ExpectAnyArgs();
787
788 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
789
790 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
791
792 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
793
794 uxListRemove_ExpectAndReturn( &( xNetworkBuffer.xBufferListItem ), 0 );
795
796 uxIPHeaderSizePacket_IgnoreAndReturn( ipSIZE_OF_IPv6_HEADER );
797
798 xRecv_Update_IPv6_ExpectAndReturn( &xNetworkBuffer, &xSourceAddress, ipUDP_PAYLOAD_OFFSET_IPv6 );
799
800 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
801
802 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, NULL );
803
804 TEST_ASSERT_EQUAL( 100, lReturn );
805 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pucEthernetBuffer, ipconfigTCP_MSS );
806 TEST_ASSERT_EACH_EQUAL_UINT8( 0x12, pvBuffer, 100 );
807 TEST_ASSERT_EACH_EQUAL_UINT8( 0xAB, &pvBuffer[ 100 ], ipconfigTCP_MSS - 100 );
808 }
809
810 /**
811 * @brief Blocking read socket gets a packet while it is waiting. However, the packet
812 * is UDPv6 header and 100 bytes.
813 */
test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_UnknownIPHeaderSize(void)814 void test_FreeRTOS_recvfrom_BlockingGetsPacketInBetween_UnknownIPHeaderSize( void )
815 {
816 int32_t lReturn;
817 uint8_t ucSocket[ sizeof( FreeRTOS_Socket_t ) ];
818 Socket_t xSocket = ( Socket_t ) ucSocket;
819 char pvBuffer[ ipconfigTCP_MSS ];
820 size_t uxBufferLength = ipconfigTCP_MSS;
821 BaseType_t xFlags = FREERTOS_ZERO_COPY;
822 struct freertos_sockaddr xSourceAddress;
823 ListItem_t xListItem;
824 NetworkBufferDescriptor_t xNetworkBuffer;
825 uint8_t pucEthernetBuffer[ ipconfigTCP_MSS ];
826
827 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
828 xNetworkBuffer.xDataLength = sizeof( UDPPacket_IPv6_t ) + 100;
829 xNetworkBuffer.xIPAddress.ulIP_IPv4 = 0x1234ABCD;
830 xNetworkBuffer.usPort = 0xABCD;
831
832 memset( xSocket, 0, sizeof( FreeRTOS_Socket_t ) );
833 memset( &xListItem, 0, sizeof( ListItem_t ) );
834 memset( pucEthernetBuffer, 0x12, ipconfigTCP_MSS );
835 memset( pvBuffer, 0xAB, ipconfigTCP_MSS );
836
837 xSocket->ucProtocol = FREERTOS_IPPROTO_UDP;
838 xSocket->xReceiveBlockTime = 0x123;
839
840 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket->xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
841
842 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0 );
843
844 xListItem.pvOwner = &xNetworkBuffer;
845 xSocket->u.xUDP.xWaitingPacketsList.xListEnd.pxNext = &xListItem;
846
847 vTaskSetTimeOutState_ExpectAnyArgs();
848
849 xEventGroupWaitBits_ExpectAndReturn( xSocket->xEventGroup, ( ( EventBits_t ) eSOCKET_RECEIVE ) | ( ( EventBits_t ) eSOCKET_INTR ), pdTRUE, pdFALSE, xSocket->xReceiveBlockTime, 0 );
850
851 listCURRENT_LIST_LENGTH_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), 0x12 );
852
853 listGET_OWNER_OF_HEAD_ENTRY_ExpectAndReturn( &( xSocket->u.xUDP.xWaitingPacketsList ), &xNetworkBuffer );
854
855 uxListRemove_ExpectAndReturn( &( xNetworkBuffer.xBufferListItem ), 0 );
856
857 uxIPHeaderSizePacket_IgnoreAndReturn( 0xFF );
858
859 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
860
861 lReturn = FreeRTOS_recvfrom( xSocket, pvBuffer, uxBufferLength, xFlags, &xSourceAddress, NULL );
862
863 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINVAL, lReturn );
864 }
865
866 /**
867 * @brief Assert to catch sending buffer is NULL.
868 */
test_FreeRTOS_sendto_CatchAssert(void)869 void test_FreeRTOS_sendto_CatchAssert( void )
870 {
871 int32_t lResult;
872 Socket_t xSocket;
873 char * pvBuffer = NULL;
874 size_t uxTotalDataLength = 0;
875 BaseType_t xFlags = 0;
876 struct freertos_sockaddr xDestinationAddress;
877 socklen_t xDestinationAddressLength;
878
879 catch_assert( FreeRTOS_sendto( xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength ) );
880 }
881
882 /**
883 * @brief Assert to catch destination address is NULL.
884 */
test_FreeRTOS_sendto_CatchAssertNullDest(void)885 void test_FreeRTOS_sendto_CatchAssertNullDest( void )
886 {
887 int32_t lResult;
888 Socket_t xSocket;
889 char pvBuffer[ ipconfigTCP_MSS ];
890 size_t uxTotalDataLength = 0;
891 BaseType_t xFlags = 0;
892 socklen_t xDestinationAddressLength;
893
894 catch_assert( FreeRTOS_sendto( xSocket, pvBuffer, uxTotalDataLength, xFlags, NULL, xDestinationAddressLength ) );
895 }
896
897 /**
898 * @brief Sending more than maximum allowed data in one go.
899 */
test_FreeRTOS_sendto_MoreDataThanUDPPayload(void)900 void test_FreeRTOS_sendto_MoreDataThanUDPPayload( void )
901 {
902 int32_t lResult;
903 Socket_t xSocket;
904 char pvBuffer[ ipconfigTCP_MSS ];
905 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH + 1;
906 BaseType_t xFlags;
907 struct freertos_sockaddr xDestinationAddress;
908 socklen_t xDestinationAddressLength;
909
910 xDestinationAddress.sin_family = FREERTOS_AF_INET;
911
912 lResult = FreeRTOS_sendto( xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
913
914 TEST_ASSERT_EQUAL( 0, lResult );
915 }
916
917 /**
918 * @brief Trying to send with a TCP socket.
919 */
test_FreeRTOS_sendto_TCPSocket(void)920 void test_FreeRTOS_sendto_TCPSocket( void )
921 {
922 int32_t lResult;
923 FreeRTOS_Socket_t xSocket;
924 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
925 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
926 BaseType_t xFlags;
927 struct freertos_sockaddr xDestinationAddress;
928 socklen_t xDestinationAddressLength;
929
930 xDestinationAddress.sin_family = FREERTOS_AF_INET;
931 xSocket.ucProtocol = FREERTOS_IPPROTO_TCP;
932
933 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
934
935 TEST_ASSERT_EQUAL( 0, lResult );
936 }
937
938 /**
939 * @brief Sending from IP task when a buffer cannot be allocated.
940 */
test_FreeRTOS_sendto_IPTaskCalling_NoNetworkBuffer(void)941 void test_FreeRTOS_sendto_IPTaskCalling_NoNetworkBuffer( void )
942 {
943 int32_t lResult;
944 FreeRTOS_Socket_t xSocket;
945 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
946 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
947 BaseType_t xFlags = 0;
948 struct freertos_sockaddr xDestinationAddress;
949 socklen_t xDestinationAddressLength;
950
951 xDestinationAddress.sin_family = FREERTOS_AF_INET;
952 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
953
954 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
955
956 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
957
958 vTaskSetTimeOutState_ExpectAnyArgs();
959
960 pxGetNetworkBufferWithDescriptor_ExpectAnyArgsAndReturn( NULL );
961
962 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
963
964 TEST_ASSERT_EQUAL( 0, lResult );
965 }
966
967 /**
968 * @brief Sending from IP task without using zero copy.
969 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy(void)970 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy( void )
971 {
972 int32_t lResult;
973 FreeRTOS_Socket_t xSocket;
974 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
975 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
976 BaseType_t xFlags = 0;
977 struct freertos_sockaddr xDestinationAddress;
978 socklen_t xDestinationAddressLength;
979 NetworkBufferDescriptor_t xNetworkBuffer;
980 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
981
982 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
983 memset( &xSocket, 0, sizeof( xSocket ) );
984 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
985
986 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
987
988 xDestinationAddress.sin_family = FREERTOS_AF_INET;
989 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
990 xSocket.u.xUDP.pxHandleSent = NULL;
991
992 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
993
994 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
995
996 vTaskSetTimeOutState_ExpectAnyArgs();
997
998 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
999
1000 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
1001
1002 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1003
1004 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1005
1006 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1007
1008 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1009
1010 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1011 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1012 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1013 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1014 }
1015
1016 /**
1017 * @brief Sending from IP task without using zero copy.
1018 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy1(void)1019 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy1( void )
1020 {
1021 int32_t lResult;
1022 FreeRTOS_Socket_t xSocket;
1023 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1024 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1025 BaseType_t xFlags = 0;
1026 struct freertos_sockaddr xDestinationAddress;
1027 socklen_t xDestinationAddressLength;
1028 NetworkBufferDescriptor_t xNetworkBuffer;
1029 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1030
1031 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1032 memset( &xSocket, 0, sizeof( xSocket ) );
1033 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1034
1035 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1036
1037 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1038 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1039 xSocket.u.xUDP.pxHandleSent = NULL;
1040
1041 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1042
1043 xIsCallingFromIPTask_ExpectAndReturn( pdFALSE );
1044
1045 vTaskSetTimeOutState_ExpectAnyArgs();
1046
1047 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
1048
1049 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
1050
1051 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1052
1053 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1054
1055 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1056
1057 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1058
1059 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1060 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1061 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1062 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1063 }
1064
1065 /**
1066 * @brief Sending from IP task without using zero copy.
1067 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy2(void)1068 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy2( void )
1069 {
1070 int32_t lResult;
1071 FreeRTOS_Socket_t xSocket;
1072 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1073 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1074 BaseType_t xFlags = FREERTOS_MSG_DONTWAIT;
1075 struct freertos_sockaddr xDestinationAddress;
1076 socklen_t xDestinationAddressLength;
1077 NetworkBufferDescriptor_t xNetworkBuffer;
1078 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1079
1080 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1081 memset( &xSocket, 0, sizeof( xSocket ) );
1082 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1083
1084 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1085
1086 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1087 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1088 xSocket.u.xUDP.pxHandleSent = NULL;
1089
1090 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1091
1092 vTaskSetTimeOutState_ExpectAnyArgs();
1093
1094 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
1095
1096 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
1097
1098 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1099
1100 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1101
1102 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1103
1104 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1105
1106 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1107 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1108 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1109 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1110 }
1111
1112 /**
1113 * @brief Sending from IP task without using zero copy. Checks if xIsCallingFromIPTask
1114 * gets called if xFlags's FREERTOS_MSG_DONTWAIT bit is unset.
1115 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy2_xFlagZero(void)1116 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy2_xFlagZero( void )
1117 {
1118 int32_t lResult;
1119 FreeRTOS_Socket_t xSocket;
1120 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1121 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1122 BaseType_t xFlags = 0;
1123 struct freertos_sockaddr xDestinationAddress;
1124 socklen_t xDestinationAddressLength;
1125 NetworkBufferDescriptor_t xNetworkBuffer;
1126 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1127
1128 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1129 memset( &xSocket, 0, sizeof( xSocket ) );
1130 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1131
1132 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1133
1134 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1135 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1136 xSocket.u.xUDP.pxHandleSent = NULL;
1137
1138 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1139
1140 xIsCallingFromIPTask_ExpectAndReturn( pdFALSE );
1141
1142 vTaskSetTimeOutState_ExpectAnyArgs();
1143
1144 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
1145
1146 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdTRUE );
1147
1148 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1149
1150 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1151
1152 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1153
1154 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1155
1156 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1157 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1158 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1159 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1160 }
1161
1162 /**
1163 * @brief Sending from IP task without using zero copy.
1164 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy3(void)1165 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy3( void )
1166 {
1167 int32_t lResult;
1168 FreeRTOS_Socket_t xSocket;
1169 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1170 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1171 BaseType_t xFlags = FREERTOS_MSG_DONTWAIT;
1172 struct freertos_sockaddr xDestinationAddress;
1173 socklen_t xDestinationAddressLength;
1174 NetworkBufferDescriptor_t xNetworkBuffer;
1175 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1176
1177 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1178 memset( &xSocket, 0, sizeof( xSocket ) );
1179 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1180
1181 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1182
1183 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1184 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1185 xSocket.u.xUDP.pxHandleSent = NULL;
1186
1187 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1188
1189 vTaskSetTimeOutState_ExpectAnyArgs();
1190
1191 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
1192
1193 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdFALSE );
1194
1195 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1196
1197 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1198
1199 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1200
1201 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1202
1203 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1204 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1205 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1206 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1207 }
1208
1209 /**
1210 * @brief Sending from IP task with zero copy.
1211 */
test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy(void)1212 void test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy( void )
1213 {
1214 int32_t lResult;
1215 FreeRTOS_Socket_t xSocket;
1216 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1217 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1218 BaseType_t xFlags = FREERTOS_ZERO_COPY;
1219 struct freertos_sockaddr xDestinationAddress;
1220 socklen_t xDestinationAddressLength;
1221 NetworkBufferDescriptor_t xNetworkBuffer;
1222 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1223
1224 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1225 memset( &xSocket, 0, sizeof( xSocket ) );
1226 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1227
1228 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1229
1230 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1231 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1232 xSocket.u.xUDP.pxHandleSent = NULL;
1233
1234 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1235
1236 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
1237
1238 pxUDPPayloadBuffer_to_NetworkBuffer_ExpectAndReturn( pvBuffer, &xNetworkBuffer );
1239
1240 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1241
1242 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1243
1244 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1245
1246 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1247
1248 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1249 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1250 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1251 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1252 }
1253
1254 static uint32_t ulCalled = 0;
xLocalFunctionPointer(Socket_t xSocket,size_t xLength)1255 static void xLocalFunctionPointer( Socket_t xSocket,
1256 size_t xLength )
1257 {
1258 ulCalled++;
1259 }
1260
1261 /**
1262 * @brief Sending from IP task with zero copy. A valid callback function pointer is added.
1263 */
test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy_ValidFunctionPointer(void)1264 void test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy_ValidFunctionPointer( void )
1265 {
1266 int32_t lResult;
1267 FreeRTOS_Socket_t xSocket;
1268 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1269 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1270 BaseType_t xFlags = FREERTOS_ZERO_COPY;
1271 struct freertos_sockaddr xDestinationAddress;
1272 socklen_t xDestinationAddressLength;
1273 NetworkBufferDescriptor_t xNetworkBuffer;
1274 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1275
1276 ulCalled = 0;
1277
1278 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1279 memset( &xSocket, 0, sizeof( xSocket ) );
1280 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1281
1282 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1283
1284 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1285 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1286 xSocket.u.xUDP.pxHandleSent = xLocalFunctionPointer;
1287
1288 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1289
1290 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
1291
1292 pxUDPPayloadBuffer_to_NetworkBuffer_ExpectAndReturn( pvBuffer, &xNetworkBuffer );
1293
1294 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1295
1296 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1297
1298 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1299
1300 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1301
1302 TEST_ASSERT_EQUAL( TEST_MAX_UDPV4_PAYLOAD_LENGTH, lResult );
1303 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1304 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1305 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1306 TEST_ASSERT_EQUAL( 1, ulCalled );
1307 }
1308
1309 /**
1310 * @brief Sending from IP task with zero copy.Sending message to IP task fails.
1311 */
test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy_SendingToIPTaskFails(void)1312 void test_FreeRTOS_sendto_IPTaskCalling_ZeroCopy_SendingToIPTaskFails( void )
1313 {
1314 int32_t lResult;
1315 FreeRTOS_Socket_t xSocket;
1316 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1317 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1318 BaseType_t xFlags = FREERTOS_ZERO_COPY;
1319 struct freertos_sockaddr xDestinationAddress;
1320 socklen_t xDestinationAddressLength;
1321 NetworkBufferDescriptor_t xNetworkBuffer;
1322 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1323
1324 ulCalled = 0;
1325
1326 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1327 memset( &xSocket, 0, sizeof( xSocket ) );
1328 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1329
1330 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1331
1332 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1333 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1334 xSocket.u.xUDP.pxHandleSent = xLocalFunctionPointer;
1335
1336 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1337
1338 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
1339
1340 pxUDPPayloadBuffer_to_NetworkBuffer_ExpectAndReturn( pvBuffer, &xNetworkBuffer );
1341
1342 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1343
1344 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1345
1346 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdFAIL );
1347
1348 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1349
1350 TEST_ASSERT_EQUAL( 0, lResult );
1351 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1352 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1353 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1354 TEST_ASSERT_EQUAL( 0, ulCalled );
1355 }
1356
1357 /**
1358 * @brief Sending from IP task without zero copy. Sending message to IP task fails.
1359 */
test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy_SendingToIPTaskFails(void)1360 void test_FreeRTOS_sendto_IPTaskCalling_NonZeroCopy_SendingToIPTaskFails( void )
1361 {
1362 int32_t lResult;
1363 FreeRTOS_Socket_t xSocket;
1364 char pvBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH ];
1365 size_t uxTotalDataLength = TEST_MAX_UDPV4_PAYLOAD_LENGTH;
1366 BaseType_t xFlags = 0;
1367 struct freertos_sockaddr xDestinationAddress;
1368 socklen_t xDestinationAddressLength;
1369 NetworkBufferDescriptor_t xNetworkBuffer;
1370 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 ];
1371
1372 ulCalled = 0;
1373
1374 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV4_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv4 );
1375 memset( &xSocket, 0, sizeof( xSocket ) );
1376 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1377
1378 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1379
1380 xDestinationAddress.sin_family = FREERTOS_AF_INET;
1381 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1382 xSocket.u.xUDP.pxHandleSent = xLocalFunctionPointer;
1383
1384 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1385
1386 xIsCallingFromIPTask_ExpectAndReturn( pdTRUE );
1387
1388 vTaskSetTimeOutState_ExpectAnyArgs();
1389
1390 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv4, 0, &xNetworkBuffer );
1391
1392 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdFALSE );
1393
1394 xSend_UDP_Update_IPv4_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1395
1396 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1397
1398 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdFAIL );
1399
1400 vReleaseNetworkBufferAndDescriptor_Expect( &xNetworkBuffer );
1401
1402 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1403
1404 TEST_ASSERT_EQUAL( 0, lResult );
1405 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_t ) );
1406 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1407 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1408 TEST_ASSERT_EQUAL( 0, ulCalled );
1409 }
1410
1411 /**
1412 * @brief Sending an IPv6 packet from IP task without using zero copy.
1413 */
test_FreeRTOS_sendto_IPTaskCalling_IPv6NonZeroCopy(void)1414 void test_FreeRTOS_sendto_IPTaskCalling_IPv6NonZeroCopy( void )
1415 {
1416 int32_t lResult;
1417 FreeRTOS_Socket_t xSocket;
1418 char pvBuffer[ TEST_MAX_UDPV6_PAYLOAD_LENGTH ];
1419 size_t uxTotalDataLength = TEST_MAX_UDPV6_PAYLOAD_LENGTH;
1420 BaseType_t xFlags = FREERTOS_MSG_DONTWAIT;
1421 struct freertos_sockaddr xDestinationAddress;
1422 socklen_t xDestinationAddressLength;
1423 NetworkBufferDescriptor_t xNetworkBuffer;
1424 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV6_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv6 ];
1425
1426 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV6_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv6 );
1427 memset( &xSocket, 0, sizeof( xSocket ) );
1428 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1429
1430 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1431
1432 xDestinationAddress.sin_family = FREERTOS_AF_INET6;
1433 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1434 xSocket.u.xUDP.pxHandleSent = NULL;
1435
1436 listLIST_ITEM_CONTAINER_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), ( struct xLIST * ) ( uintptr_t ) 0x11223344 );
1437
1438 vTaskSetTimeOutState_ExpectAnyArgs();
1439
1440 pxGetNetworkBufferWithDescriptor_ExpectAndReturn( uxTotalDataLength + ipUDP_PAYLOAD_OFFSET_IPv6, 0, &xNetworkBuffer );
1441
1442 xTaskCheckForTimeOut_ExpectAnyArgsAndReturn( pdFALSE );
1443
1444 xSend_UDP_Update_IPv6_ExpectAndReturn( &xNetworkBuffer, &xDestinationAddress, NULL );
1445
1446 listGET_LIST_ITEM_VALUE_ExpectAndReturn( &( xSocket.xBoundSocketListItem ), 0xAADF );
1447
1448 xSendEventStructToIPTask_ExpectAnyArgsAndReturn( pdPASS );
1449
1450 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1451
1452 TEST_ASSERT_EQUAL( TEST_MAX_UDPV6_PAYLOAD_LENGTH, lResult );
1453 TEST_ASSERT_EQUAL( xNetworkBuffer.xDataLength, uxTotalDataLength + sizeof( UDPPacket_IPv6_t ) );
1454 TEST_ASSERT_EQUAL( xNetworkBuffer.usPort, xDestinationAddress.sin_port );
1455 TEST_ASSERT_EQUAL( xNetworkBuffer.usBoundPort, 0xAADF );
1456 }
1457
1458 /**
1459 * @brief Sending an packet with unknown family.
1460 */
test_FreeRTOS_sendto_UnknownDestinationFamily(void)1461 void test_FreeRTOS_sendto_UnknownDestinationFamily( void )
1462 {
1463 int32_t lResult;
1464 FreeRTOS_Socket_t xSocket;
1465 char pvBuffer[ TEST_MAX_UDPV6_PAYLOAD_LENGTH ];
1466 size_t uxTotalDataLength = TEST_MAX_UDPV6_PAYLOAD_LENGTH;
1467 BaseType_t xFlags = FREERTOS_MSG_DONTWAIT;
1468 struct freertos_sockaddr xDestinationAddress;
1469 socklen_t xDestinationAddressLength;
1470 NetworkBufferDescriptor_t xNetworkBuffer;
1471 uint8_t pucEthernetBuffer[ TEST_MAX_UDPV6_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv6 ];
1472
1473 memset( pucEthernetBuffer, 0, TEST_MAX_UDPV6_PAYLOAD_LENGTH + ipUDP_PAYLOAD_OFFSET_IPv6 );
1474 memset( &xSocket, 0, sizeof( xSocket ) );
1475 memset( &xNetworkBuffer, 0, sizeof( xNetworkBuffer ) );
1476
1477 xNetworkBuffer.pucEthernetBuffer = pucEthernetBuffer;
1478
1479 xDestinationAddress.sin_family = 0xFF;
1480 xSocket.ucProtocol = FREERTOS_IPPROTO_UDP;
1481 xSocket.u.xUDP.pxHandleSent = NULL;
1482
1483 lResult = FreeRTOS_sendto( &xSocket, pvBuffer, uxTotalDataLength, xFlags, &xDestinationAddress, xDestinationAddressLength );
1484
1485 TEST_ASSERT_EQUAL( -pdFREERTOS_ERRNO_EINVAL, lResult );
1486 }
1487