1 /* This NetX test concentrates on overlapping TCP data packets. */
2
3 #include "tx_api.h"
4 #include "nx_api.h"
5
6 extern void test_control_return(UINT status);
7
8 #if !defined(NX_TCP_ACK_EVERY_N_PACKETS) && !defined(NX_DISABLE_IPV4)
9
10 #define DEMO_STACK_SIZE 2048
11
12 #define MSG "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"
13
14 /* Define the ThreadX and NetX object control blocks... */
15
16 static TX_THREAD thread_0;
17 static TX_THREAD thread_1;
18
19 static NX_PACKET_POOL pool_0;
20 static NX_IP ip_0;
21 static NX_IP ip_1;
22 static NX_TCP_SOCKET client_socket;
23 static NX_TCP_SOCKET server_socket;
24
25 /* Define the counters used in the demo application... */
26
27 static ULONG error_counter;
28
29 extern ULONG packet_gather;
30
31 /* Define thread prototypes. */
32
33 static void thread_0_entry(ULONG thread_input);
34 static void thread_1_entry(ULONG thread_input);
35 static void thread_1_connect_received(NX_TCP_SOCKET *server_socket, UINT port);
36 static void thread_1_disconnect_received(NX_TCP_SOCKET *server_socket);
37 extern void test_control_return(UINT status);
38 extern void _nx_ram_network_driver_256(struct NX_IP_DRIVER_STRUCT *driver_req);
39
40 /* Define what the initial system looks like. */
41
42 #ifdef CTEST
test_application_define(void * first_unused_memory)43 VOID test_application_define(void *first_unused_memory)
44 #else
45 void netx_tcp_overlapping_packet_test_10_application_define(void *first_unused_memory)
46 #endif
47 {
48 CHAR *pointer;
49 UINT status;
50
51 /* Setup the working pointer. */
52 pointer = (CHAR *) first_unused_memory;
53
54 error_counter = 0;
55
56 /* Create the main thread. */
57 tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0,
58 pointer, DEMO_STACK_SIZE,
59 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START);
60
61 pointer = pointer + DEMO_STACK_SIZE;
62
63 /* Create the main thread. */
64 tx_thread_create(&thread_1, "thread 1", thread_1_entry, 0,
65 pointer, DEMO_STACK_SIZE,
66 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START);
67
68 pointer = pointer + DEMO_STACK_SIZE;
69
70 /* Initialize the NetX system. */
71 nx_system_initialize();
72
73 /* Create a packet pool. */
74 status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", 512, pointer, 8192);
75 pointer = pointer + 8192;
76
77 if(status)
78 error_counter++;
79
80 /* Create an IP instance. */
81 status = nx_ip_create(&ip_0, "NetX IP Instance 0", IP_ADDRESS(1, 2, 3, 4), 0xFFFFFF00UL, &pool_0, _nx_ram_network_driver_256,
82 pointer, 2048, 1);
83 pointer = pointer + 2048;
84
85 /* Create another IP instance. */
86 status += nx_ip_create(&ip_1, "NetX IP Instance 1", IP_ADDRESS(1, 2, 3, 5), 0xFFFFFF00UL, &pool_0, _nx_ram_network_driver_256,
87 pointer, 2048, 1);
88 pointer = pointer + 2048;
89
90 if(status)
91 error_counter++;
92
93 /* Enable ARP and supply ARP cache memory for IP Instance 0. */
94 status = nx_arp_enable(&ip_0, (void *) pointer, 1024);
95 pointer = pointer + 1024;
96
97 /* Enable ARP and supply ARP cache memory for IP Instance 1. */
98 status += nx_arp_enable(&ip_1, (void *) pointer, 1024);
99 pointer = pointer + 1024;
100
101 /* Check ARP enable status. */
102 if(status)
103 error_counter++;
104
105 /* Enable TCP processing for both IP instances. */
106 status = nx_tcp_enable(&ip_0);
107 status += nx_tcp_enable(&ip_1);
108
109 /* Check TCP enable status. */
110 if(status)
111 error_counter++;
112 }
113
114 /* Define the test threads. */
115
thread_0_entry(ULONG thread_input)116 static void thread_0_entry(ULONG thread_input)
117 {
118
119 UINT status;
120 NX_PACKET *my_packet1;
121 NX_PACKET *my_packet2;
122 NX_PACKET *my_packet3;
123 NX_PACKET *my_packet4;
124 char *msg = MSG;
125 ULONG seq1;
126
127 /* Print out test information banner. */
128 printf("NetX Test: TCP Overlapping Packet Test 10............................");
129
130 /* Check for earlier error. */
131 if(error_counter)
132 {
133 printf("ERROR!\n");
134 test_control_return(1);
135 }
136
137 /* Create a socket. */
138 status = nx_tcp_socket_create(&ip_0, &client_socket, "Client Socket",
139 NX_IP_NORMAL, NX_FRAGMENT_OKAY, NX_IP_TIME_TO_LIVE, 300,
140 NX_NULL, NX_NULL);
141
142 /* Check for error. */
143 if(status)
144 error_counter++;
145
146 /* Bind the socket. */
147 status = nx_tcp_client_socket_bind(&client_socket, 12, NX_WAIT_FOREVER);
148
149 /* Check for error. */
150 if(status)
151 error_counter++;
152
153 /* Attempt to connect the socket. */
154 tx_thread_relinquish();
155
156 status = nx_tcp_client_socket_connect(&client_socket, IP_ADDRESS(1, 2, 3, 5), 12, 5 * NX_IP_PERIODIC_RATE);
157
158 /* Check for error. */
159 if(status)
160 error_counter++;
161
162 /* Create 4 packets */
163 status = nx_packet_allocate(&pool_0, &my_packet1, NX_TCP_PACKET, NX_WAIT_FOREVER);
164 status += nx_packet_allocate(&pool_0, &my_packet2, NX_TCP_PACKET, NX_WAIT_FOREVER);
165 status += nx_packet_allocate(&pool_0, &my_packet3, NX_TCP_PACKET, NX_WAIT_FOREVER);
166 status += nx_packet_allocate(&pool_0, &my_packet4, NX_TCP_PACKET, NX_WAIT_FOREVER);
167
168 if(status)
169 error_counter++;
170
171 /* Fill in the packet with data. */
172 /* Packet 1 contains bytes 0 - 19
173 Packet 2 contains bytes 60 - 79
174 Packet 3 contains bytes 40 - 59
175 packet 4 contains bytes 20 - 45 */
176
177 memcpy(my_packet1 -> nx_packet_prepend_ptr, &msg[0], 20);
178 my_packet1 -> nx_packet_length = 20;
179 my_packet1 -> nx_packet_append_ptr = my_packet1 -> nx_packet_prepend_ptr + 20;
180
181 memcpy(my_packet2 -> nx_packet_prepend_ptr, &msg[60], 20);
182 my_packet2 -> nx_packet_length = 20;
183 my_packet2 -> nx_packet_append_ptr = my_packet2 -> nx_packet_prepend_ptr + 20;
184
185 memcpy(my_packet3 -> nx_packet_prepend_ptr, &msg[40], 20);
186 my_packet3 -> nx_packet_length = 20;
187 my_packet3 -> nx_packet_append_ptr = my_packet3 -> nx_packet_prepend_ptr + 20;
188
189 memcpy(my_packet4 -> nx_packet_prepend_ptr, &msg[20], 26);
190 my_packet4 -> nx_packet_length = 26;
191 my_packet4 -> nx_packet_append_ptr = my_packet4 -> nx_packet_prepend_ptr + 26;
192
193 /* Send the 1st one. */
194 status = nx_tcp_socket_send(&client_socket, my_packet1, NX_IP_PERIODIC_RATE);
195
196 /* Update the seq number and send the 3rd one. */
197 seq1 = client_socket.nx_tcp_socket_tx_sequence;
198 client_socket.nx_tcp_socket_tx_sequence += 20;
199 status += nx_tcp_socket_send(&client_socket, my_packet3, NX_IP_PERIODIC_RATE);
200
201 /* Send the 2nd one. */
202 status += nx_tcp_socket_send(&client_socket, my_packet2, NX_IP_PERIODIC_RATE);
203
204 /* Send the 4th one. */
205 client_socket.nx_tcp_socket_tx_sequence = seq1;
206 status += nx_tcp_socket_send(&client_socket, my_packet4, NX_IP_PERIODIC_RATE);
207
208 if(status)
209 {
210 error_counter++;
211 }
212 }
213
214 static char rcv_buffer[200];
thread_1_entry(ULONG thread_input)215 static void thread_1_entry(ULONG thread_input)
216 {
217
218 UINT status;
219 NX_PACKET *packet_ptr;
220 ULONG actual_status;
221 ULONG recv_length = 0;
222
223 /* Ensure the IP instance has been initialized. */
224 status = nx_ip_status_check(&ip_1, NX_IP_INITIALIZE_DONE, &actual_status, NX_IP_PERIODIC_RATE);
225
226 /* Check status... */
227 if(status != NX_SUCCESS)
228 {
229 error_counter++;
230 test_control_return(1);
231 }
232
233 /* Create a socket. */
234 status = nx_tcp_socket_create(&ip_1, &server_socket, "Server Socket",
235 NX_IP_NORMAL, NX_FRAGMENT_OKAY, NX_IP_TIME_TO_LIVE, 200,
236 NX_NULL, thread_1_disconnect_received);
237
238 /* Check for error. */
239 if(status)
240 error_counter++;
241
242 /* Setup this thread to listen. */
243 status = nx_tcp_server_socket_listen(&ip_1, 12, &server_socket, 5, thread_1_connect_received);
244
245 /* Check for error. */
246 if(status)
247 error_counter++;
248
249 /* Accept a client socket connection. */
250 status = nx_tcp_server_socket_accept(&server_socket, NX_IP_PERIODIC_RATE);
251
252 /* Check for error. */
253 if(status)
254 error_counter++;
255
256 /* Receive a TCP message from the socket. */
257 while (nx_tcp_socket_receive(&server_socket, &packet_ptr, 5 * NX_IP_PERIODIC_RATE) == NX_SUCCESS)
258 {
259
260 if(packet_ptr -> nx_packet_length == 0)
261 error_counter++;
262
263 memcpy(&rcv_buffer[recv_length], packet_ptr -> nx_packet_prepend_ptr, packet_ptr -> nx_packet_length);
264 recv_length += packet_ptr -> nx_packet_length;
265
266 /* Release the packet. */
267 nx_packet_release(packet_ptr);
268 }
269
270 if(recv_length != 80)
271 error_counter++;
272
273 if(memcmp(rcv_buffer, (void*)MSG, recv_length))
274 error_counter++;
275
276 server_socket.nx_tcp_socket_rx_sequence = client_socket.nx_tcp_socket_tx_sequence;
277
278 /* Determine if the test was successful. */
279 if(error_counter)
280 {
281 printf("ERROR!\n");
282 test_control_return(1);
283 }
284 else
285 {
286 printf("SUCCESS!\n");
287 test_control_return(0);
288 }
289 }
290
291
thread_1_connect_received(NX_TCP_SOCKET * socket_ptr,UINT port)292 static void thread_1_connect_received(NX_TCP_SOCKET *socket_ptr, UINT port)
293 {
294
295 /* Check for the proper socket and port. */
296 if((socket_ptr != &server_socket) || (port != 12))
297 error_counter++;
298 }
299
300
thread_1_disconnect_received(NX_TCP_SOCKET * socket)301 static void thread_1_disconnect_received(NX_TCP_SOCKET *socket)
302 {
303
304 /* Check for proper disconnected socket. */
305 if(socket != &server_socket)
306 error_counter++;
307 }
308 #else
309 #ifdef CTEST
test_application_define(void * first_unused_memory)310 VOID test_application_define(void *first_unused_memory)
311 #else
312 void netx_tcp_overlapping_packet_test_10_application_define(void *first_unused_memory)
313 #endif
314 {
315 printf("NetX Test: TCP Overlapping Packet Test 10............................N/A\n");
316 test_control_return(3);
317 }
318 #endif
319
320