1
2 #include "tx_api.h"
3 #include "fx_api.h"
4 #include "nx_api.h"
5 #include "nxd_ftp_client.h"
6 #include "nxd_ftp_server.h"
7
8 extern void test_control_return(UINT);
9
10 #if !defined(NX_DISABLE_IPV4)
11
12 #define DEMO_STACK_SIZE 4096
13
14 /* Define the ThreadX, NetX, and FileX object control blocks... */
15 static TX_THREAD server_thread;
16 static TX_THREAD client_thread;
17 static NX_PACKET_POOL server_pool;
18 static NX_IP server_ip;
19 static NX_PACKET_POOL client_pool;
20 static NX_IP client_ip;
21 static FX_MEDIA ram_disk;
22
23
24 /* Define the NetX FTP object control blocks. */
25 static NX_FTP_CLIENT ftp_client;
26 static NX_FTP_SERVER ftp_server;
27
28 /* Define the counters used in the demo application... */
29 static ULONG error_counter = 0;
30 static UINT test_done = NX_FALSE;
31
32 /* Define the memory area for the FileX RAM disk. */
33 static UCHAR ram_disk_memory[32000];
34 static UCHAR ram_disk_sector_cache[512];
35
36
37 #define FTP_SERVER_ADDRESS IP_ADDRESS(1,2,3,4)
38 #define FTP_CLIENT_ADDRESS IP_ADDRESS(1,2,3,5)
39
40 extern UINT _fx_media_format(FX_MEDIA *media_ptr, VOID (*driver)(FX_MEDIA *media), VOID *driver_info_ptr, UCHAR *memory_ptr, UINT memory_size,
41 CHAR *volume_name, UINT number_of_fats, UINT directory_entries, UINT hidden_sectors,
42 ULONG total_sectors, UINT bytes_per_sector, UINT sectors_per_cluster,
43 UINT heads, UINT sectors_per_track);
44
45 /* Define the FileX and NetX driver entry functions. */
46 extern void _fx_ram_driver(FX_MEDIA *media_ptr);
47 extern void _nx_ram_network_driver_512(NX_IP_DRIVER *driver_req_ptr);
48
49 static void client_thread_entry(ULONG thread_input);
50 static void thread_server_entry(ULONG thread_input);
51
52
53 /* Define server login/logout functions. These are stubs for functions that would
54 validate a client login request. */
55 static UINT server_login(struct NX_FTP_SERVER_STRUCT *ftp_server_ptr, ULONG client_ip_address, UINT client_port, CHAR *name, CHAR *password, CHAR *extra_info);
56 static UINT server_logout(struct NX_FTP_SERVER_STRUCT *ftp_server_ptr, ULONG client_ip_address, UINT client_port, CHAR *name, CHAR *password, CHAR *extra_info);
57
58 #ifdef CTEST
test_application_define(void * first_unused_memory)59 VOID test_application_define(void *first_unused_memory)
60 #else
61 void netx_ftp_client_packet_leak_test_application_define(void *first_unused_memory)
62 #endif
63 {
64
65 UINT status;
66 UCHAR *pointer;
67
68
69 /* Setup the working pointer. */
70 pointer = (UCHAR *) first_unused_memory;
71
72 /* Create a helper thread for the server. */
73 tx_thread_create(&server_thread, "FTP Server thread", thread_server_entry, 0,
74 pointer, DEMO_STACK_SIZE,
75 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START);
76
77 pointer = pointer + DEMO_STACK_SIZE;
78
79 /* Initialize NetX. */
80 nx_system_initialize();
81
82 /* Create the packet pool for the FTP Server. */
83 status = nx_packet_pool_create(&server_pool, "NetX Server Packet Pool", 512, pointer, 8192);
84 pointer = pointer + 8192;
85 if (status)
86 error_counter++;
87
88 /* Create the IP instance for the FTP Server. */
89 status = nx_ip_create(&server_ip, "NetX Server IP Instance", FTP_SERVER_ADDRESS, 0xFFFFFF00UL,
90 &server_pool, _nx_ram_network_driver_512, pointer, 2048, 1);
91 pointer = pointer + 2048;
92 if (status)
93 error_counter++;
94
95 /* Enable ARP and supply ARP cache memory for server IP instance. */
96 status = nx_arp_enable(&server_ip, (void *) pointer, 1024);
97 pointer = pointer + 1024;
98 if (status)
99 error_counter++;
100
101 /* Enable TCP. */
102 status = nx_tcp_enable(&server_ip);
103 if (status)
104 error_counter++;
105
106 /* Create the FTP server. */
107 status = nx_ftp_server_create(&ftp_server, "FTP Server Instance", &server_ip, &ram_disk, pointer, DEMO_STACK_SIZE, &server_pool,
108 server_login, server_logout);
109 pointer = pointer + DEMO_STACK_SIZE;
110 if (status)
111 error_counter++;
112
113 /* Now set up the FTP Client. */
114
115 /* Create the main FTP client thread. */
116 status = tx_thread_create(&client_thread, "FTP Client thread ", client_thread_entry, 0,
117 pointer, DEMO_STACK_SIZE,
118 6, 6, TX_NO_TIME_SLICE, TX_AUTO_START);
119 pointer = pointer + DEMO_STACK_SIZE ;
120 if (status)
121 error_counter++;
122
123 /* Create a packet pool for the FTP client. */
124 status = nx_packet_pool_create(&client_pool, "NetX Client Packet Pool", 256, pointer, 8192);
125 pointer = pointer + 8192;
126 if (status)
127 error_counter++;
128
129 /* Create an IP instance for the FTP client. */
130 status = nx_ip_create(&client_ip, "NetX Client IP Instance", FTP_CLIENT_ADDRESS, 0xFFFFFF00UL,
131 &client_pool, _nx_ram_network_driver_512, pointer, 2048, 1);
132 pointer = pointer + 2048;
133 if (status)
134 error_counter++;
135
136 /* Enable ARP and supply ARP cache memory for the FTP Client IP. */
137 status = nx_arp_enable(&client_ip, (void *) pointer, 1024);
138 pointer = pointer + 1024;
139 if (status)
140 error_counter++;
141
142 /* Enable TCP for client IP instance. */
143 status = nx_tcp_enable(&client_ip);
144 if (status)
145 error_counter++;
146
147 }
148
149 /* Define the FTP client thread. */
150
client_thread_entry(ULONG thread_input)151 void client_thread_entry(ULONG thread_input)
152 {
153
154 NX_PACKET *my_packet;
155 UINT status;
156
157 /* Format the RAM disk - the memory for the RAM disk was defined above. */
158 status = _fx_media_format(&ram_disk,
159 _fx_ram_driver, /* Driver entry */
160 ram_disk_memory, /* RAM disk memory pointer */
161 ram_disk_sector_cache, /* Media buffer pointer */
162 sizeof(ram_disk_sector_cache), /* Media buffer size */
163 "MY_RAM_DISK", /* Volume Name */
164 1, /* Number of FATs */
165 32, /* Directory Entries */
166 0, /* Hidden sectors */
167 256, /* Total sectors */
168 128, /* Sector size */
169 1, /* Sectors per cluster */
170 1, /* Heads */
171 1); /* Sectors per track */
172
173 /* Check status. */
174 if (status)
175 error_counter++;
176
177 /* Open the RAM disk. */
178 status = fx_media_open(&ram_disk, "RAM DISK", _fx_ram_driver, ram_disk_memory, ram_disk_sector_cache, sizeof(ram_disk_sector_cache));
179 if (status)
180 error_counter++;
181
182 /* Create an FTP client. */
183 status = nx_ftp_client_create(&ftp_client, "FTP Client", &client_ip, 2000, &client_pool);
184 if (status)
185 error_counter++;
186
187 /* Now connect with the NetX FTP (IPv4) server. */
188 status = nx_ftp_client_connect(&ftp_client, FTP_SERVER_ADDRESS, "name", "password", NX_IP_PERIODIC_RATE);
189 if (status)
190 error_counter++;
191
192 /* Check packet leak. */
193 if (client_pool.nx_packet_pool_available != client_pool.nx_packet_pool_total)
194 error_counter++;
195
196 /* Open a FTP file for writing. */
197 status = nx_ftp_client_file_open(&ftp_client, "test.txt", NX_FTP_OPEN_FOR_WRITE, NX_IP_PERIODIC_RATE);
198 if (status)
199 error_counter++;
200
201 /* Check packet leak. */
202 if (client_pool.nx_packet_pool_available != client_pool.nx_packet_pool_total)
203 error_counter++;
204
205 /* Allocate a FTP packet. */
206 status = nx_packet_allocate(&client_pool, &my_packet, NX_TCP_PACKET, NX_IP_PERIODIC_RATE);
207 if (status)
208 error_counter++;
209
210 /* Write ABCs into the packet payload! */
211 memcpy(my_packet -> nx_packet_prepend_ptr, "ABCDEFGHIJKLMNOPQRSTUVWXYZ ", 28);
212
213 /* Adjust the write pointer. */
214 my_packet -> nx_packet_length = 28;
215 my_packet -> nx_packet_append_ptr = my_packet -> nx_packet_prepend_ptr + 28;
216
217 /* Write the packet to the file test.txt. */
218 status = nx_ftp_client_file_write(&ftp_client, my_packet, NX_IP_PERIODIC_RATE);
219 if (status)
220 error_counter++;
221
222 /* Close the file. */
223 status = nx_ftp_client_file_close(&ftp_client, NX_IP_PERIODIC_RATE);
224 if (status)
225 error_counter++;
226
227 /* Check packet leak. */
228 if (client_pool.nx_packet_pool_available != client_pool.nx_packet_pool_total)
229 error_counter++;
230
231 /* Get directory listing (NLST). */
232 status = nx_ftp_client_directory_listing_get(&ftp_client, "", &my_packet, 200);
233 if (status != NX_SUCCESS)
234 {
235 error_counter++;
236 }
237 else
238 {
239 nx_packet_release(my_packet);
240 }
241
242 do
243 {
244 /* Receive the next data packet. */
245 status = nx_ftp_client_directory_listing_continue(&ftp_client, &my_packet, 200);
246 if (status == NX_SUCCESS)
247 {
248 nx_packet_release(my_packet);
249 }
250
251 /* Check if this is the end of the download. */
252 if (status == NX_FTP_END_OF_LISTING)
253 break;
254
255 } while (status == NX_SUCCESS);
256
257 /* Check packet leak. */
258 if (client_pool.nx_packet_pool_available != client_pool.nx_packet_pool_total)
259 error_counter++;
260
261 /* Disconnect from the server. */
262 status = nx_ftp_client_disconnect(&ftp_client, NX_IP_PERIODIC_RATE);
263 if (status)
264 error_counter++;
265
266 /* Check packet leak. */
267 if (client_pool.nx_packet_pool_available != client_pool.nx_packet_pool_total)
268 error_counter++;
269
270 /* Delete the FTP client. */
271 status = nx_ftp_client_delete(&ftp_client);
272 if (status)
273 error_counter++;
274
275 /* Set the flag. */
276 test_done = NX_TRUE;
277 }
278
279
280 /* Define the helper FTP server thread. */
thread_server_entry(ULONG thread_input)281 void thread_server_entry(ULONG thread_input)
282 {
283
284 UINT status;
285
286 /* Print out test information banner. */
287 printf("NetX Test: FTP Client Packet Leak Test...............................");
288
289 /* Check for earlier error. */
290 if(error_counter)
291 {
292 printf("ERROR!\n");
293 test_control_return(1);
294 }
295
296 /* OK to start the ftp Server. */
297 status = nx_ftp_server_start(&ftp_server);
298 if (status)
299 error_counter++;
300
301 /* OK to restart the ftp Server. */
302 status = nx_ftp_server_stop(&ftp_server);
303 status += nx_ftp_server_start(&ftp_server);
304 if (status)
305 error_counter++;
306
307 /* Wait for test. */
308 while(test_done == NX_FALSE)
309 tx_thread_sleep(NX_IP_PERIODIC_RATE);
310
311 status = nx_ftp_server_delete(&ftp_server);
312 if(status)
313 error_counter++;
314
315 if(error_counter)
316 {
317 printf("ERROR!\n");
318 test_control_return(1);
319 }
320 else
321 {
322 printf("SUCCESS!\n");
323 test_control_return(0);
324 }
325 }
326
327
server_login(struct NX_FTP_SERVER_STRUCT * ftp_server_ptr,ULONG client_ip_address,UINT client_port,CHAR * name,CHAR * password,CHAR * extra_info)328 static UINT server_login(struct NX_FTP_SERVER_STRUCT *ftp_server_ptr, ULONG client_ip_address, UINT client_port, CHAR *name, CHAR *password, CHAR *extra_info)
329 {
330 /* Always return success. */
331 return(NX_SUCCESS);
332 }
333
server_logout(struct NX_FTP_SERVER_STRUCT * ftp_server_ptr,ULONG client_ip_address,UINT client_port,CHAR * name,CHAR * password,CHAR * extra_info)334 static UINT server_logout(struct NX_FTP_SERVER_STRUCT *ftp_server_ptr, ULONG client_ip_address, UINT client_port, CHAR *name, CHAR *password, CHAR *extra_info)
335 {
336 /* Always return success. */
337 return(NX_SUCCESS);
338 }
339 #else
340
341 #ifdef CTEST
test_application_define(void * first_unused_memory)342 VOID test_application_define(void *first_unused_memory)
343 #else
344 void netx_ftp_client_packet_leak_test_application_define(void *first_unused_memory)
345 #endif
346 {
347
348 /* Print out test information banner. */
349 printf("NetX Test: FTP Client Packet Leak Test...............................N/A\n");
350
351 test_control_return(3);
352 }
353 #endif