1 /* This case tests status 501.
2  * If the method is unrecognized or not implemented by the origin server,
3  * should repond 501.
4  *
5  * Change GET to AET to build a unrecognized method packet.
6  * */
7 /* FIXME XWH: Not support.  */
8 #include    "tx_api.h"
9 #include    "nx_api.h"
10 #include    "fx_api.h"
11 #include    "nx_web_http_client.h"
12 #include    "nx_web_http_server.h"
13 
14 extern void test_control_return(UINT);
15 
16 #if !defined(NX_DISABLE_IPV4)
17 
18 #include "test_device_cert.c"
19 #include "test_ca_cert.c"
20 #define ca_cert_der test_ca_cert_der
21 #define ca_cert_der_len test_ca_cert_der_len
22 
23 #define     DEMO_STACK_SIZE         4096
24 
25 /* Set up FileX and file memory resources. */
26 static CHAR             ram_disk_memory[4096];
27 static FX_MEDIA         ram_disk;
28 static UCHAR            media_memory[4096];
29 
30 static UCHAR            server_stack[16000];
31 
32 /* Define device drivers.  */
33 extern void _fx_ram_driver(FX_MEDIA *media_ptr);
34 extern void _nx_ram_network_driver_1024(NX_IP_DRIVER *driver_req_ptr);
35 
36 /* Set up the HTTP client global variables. */
37 
38 #define         CLIENT_PACKET_SIZE  (NX_WEB_HTTP_CLIENT_MIN_PACKET_SIZE * 2)
39 
40 static TX_THREAD           client_thread;
41 static NX_PACKET_POOL      client_pool;
42 static NX_WEB_HTTP_CLIENT  my_client;
43 static NX_IP               client_ip;
44 static UINT                error_counter;
45 
46 /* Set up the HTTP server global variables */
47 
48 #define         SERVER_PACKET_SIZE  (NX_WEB_HTTP_SERVER_MIN_PACKET_SIZE * 2)
49 
50 static NX_WEB_HTTP_SERVER  my_server;
51 static NX_PACKET_POOL      server_pool;
52 static TX_THREAD           server_thread;
53 static NX_IP               server_ip;
54 static NXD_ADDRESS         server_ip_address;
55 static UINT                http_server_start = 0;
56 static UINT                http_client_stop = 0;
57 
58 static void thread_client_entry(ULONG thread_input);
59 static void thread_server_entry(ULONG thread_input);
60 
61 #define HTTP_SERVER_ADDRESS  IP_ADDRESS(192,168,0,105)
62 #define HTTP_CLIENT_ADDRESS  IP_ADDRESS(192,168,0,123)
63 
64 #ifdef NX_WEB_HTTPS_ENABLE
65 static UINT                https_server_start = 0;
66 static UINT                https_client_stop = 0;
67 static UINT loop = 2;
68 extern const NX_SECURE_TLS_CRYPTO nx_crypto_tls_ciphers;
69 static CHAR crypto_metadata_server[20000 * NX_WEB_HTTP_SERVER_SESSION_MAX];
70 static CHAR crypto_metadata_client[20000 * NX_WEB_HTTP_SERVER_SESSION_MAX];
71 static UCHAR tls_packet_buffer[18500];
72 static NX_SECURE_X509_CERT certificate;
73 static NX_SECURE_X509_CERT trusted_certificate;
74 static NX_SECURE_X509_CERT remote_certificate, remote_issuer;
75 static UCHAR remote_cert_buffer[2000];
76 static UCHAR remote_issuer_buffer[2000];
77 #else
78 static UINT loop = 1;
79 #endif /* NX_WEB_HTTPS_ENABLE  */
80 
81 extern UINT _nx_web_http_client_receive(NX_WEB_HTTP_CLIENT *client_ptr, NX_PACKET **packet_ptr, ULONG wait_option);
82 extern UINT _nx_web_http_client_send(NX_WEB_HTTP_CLIENT *client_ptr, NX_PACKET *packet_ptr, ULONG wait_option);
83 
84 /* This is a HTTP get packet captured by wireshark.
85  * curl 192.168.0.123
86  * GET: pkt[54] = 0x47, pkt[55] = 0x45, pkt[56] = 0x54
87  * AET: pkt[54] = 'A' , pkt[55] = 0x45, pkt[56] = 0x54
88  * */
89 static char pkt[] = {
90     0x00, 0x11, 0x22, 0x33, 0x44, 0x57, 0xb8, 0xca, /* .."3DW.. */
91     0x3a, 0x95, 0xdb, 0x0b, 0x08, 0x00, 0x45, 0x00, /* :.....E. */
92     0x00, 0x75, 0x47, 0x4a, 0x40, 0x00, 0x80, 0x06, /* .uGJ@... */
93     0x31, 0x04, 0xc0, 0xa8, 0x00, 0x69, 0xc0, 0xa8, /* 1....i.. */
94     0x00, 0x7b, 0xe8, 0xeb, 0x00, 0x50, 0xe5, 0x59, /* .{...P.Y */
95     0x56, 0x32, 0x41, 0xf1, 0x07, 0xf0, 0x50, 0x18, /* V2A...P. */
96     0xfa, 0xf0, 0x65, 0x69, 0x00, 0x00, 0x47, 0x45, /* ..ei..GE */
97     0x54, 0x20, 0x2f, 0x20, 0x48, 0x54, 0x54, 0x50, /* T / HTTP */
98     0x2f, 0x31, 0x2e, 0x31, 0x0d, 0x0a, 0x55, 0x73, /* /1.1..Us */
99     0x65, 0x72, 0x2d, 0x41, 0x67, 0x65, 0x6e, 0x74, /* er-Agent */
100     0x3a, 0x20, 0x63, 0x75, 0x72, 0x6c, 0x2f, 0x37, /* : curl/7 */
101     0x2e, 0x33, 0x32, 0x2e, 0x30, 0x0d, 0x0a, 0x48, /* .32.0..H */
102     0x6f, 0x73, 0x74, 0x3a, 0x20, 0x31, 0x39, 0x32, /* ost: 192 */
103     0x2e, 0x31, 0x36, 0x38, 0x2e, 0x30, 0x2e, 0x31, /* .168.0.1 */
104     0x32, 0x33, 0x0d, 0x0a, 0x41, 0x63, 0x63, 0x65, /* 23..Acce */
105     0x70, 0x74, 0x3a, 0x20, 0x2a, 0x2f, 0x2a, 0x0d, /* pt:      */
106     0x0a, 0x0d, 0x0a                                /* ... */
107 };
108 
109 #ifdef CTEST
test_application_define(void * first_unused_memory)110 VOID test_application_define(void *first_unused_memory)
111 #else
112 void    netx_web_status_501_test_application_define(void *first_unused_memory)
113 #endif
114 {
115 CHAR    *pointer;
116 UINT    status;
117 
118 
119     error_counter = 0;
120 
121     /* Setup the working pointer.  */
122     pointer =  (CHAR *) first_unused_memory;
123 
124     /* Create a helper thread for the server. */
125     tx_thread_create(&server_thread, "HTTP Server thread", thread_server_entry, 0,
126                      pointer, DEMO_STACK_SIZE,
127                      NX_WEB_HTTP_SERVER_PRIORITY, NX_WEB_HTTP_SERVER_PRIORITY, TX_NO_TIME_SLICE, TX_AUTO_START);
128 
129     pointer =  pointer + DEMO_STACK_SIZE;
130 
131     /* Initialize the NetX system.  */
132     nx_system_initialize();
133 
134     /* Create the server packet pool.  */
135     status =  nx_packet_pool_create(&server_pool, "HTTP Server Packet Pool", SERVER_PACKET_SIZE,
136                                     pointer, SERVER_PACKET_SIZE*8);
137     pointer = pointer + SERVER_PACKET_SIZE * 8;
138     if (status)
139         error_counter++;
140 
141     /* Create an IP instance.  */
142     status = nx_ip_create(&server_ip, "HTTP Server IP", HTTP_SERVER_ADDRESS,
143                           0xFFFFFF00UL, &server_pool, _nx_ram_network_driver_1024,
144                           pointer, 4096, 1);
145     pointer =  pointer + 4096;
146     if (status)
147         error_counter++;
148 
149     /* Enable ARP and supply ARP cache memory for the server IP instance.  */
150     status = nx_arp_enable(&server_ip, (void *) pointer, 1024);
151     pointer = pointer + 1024;
152     if (status)
153         error_counter++;
154 
155      /* Enable TCP traffic.  */
156     status = nx_tcp_enable(&server_ip);
157     if (status)
158         error_counter++;
159 
160     /* Create the HTTP Client thread. */
161     status = tx_thread_create(&client_thread, "HTTP Client", thread_client_entry, 0,
162                               pointer, DEMO_STACK_SIZE,
163                               NX_WEB_HTTP_SERVER_PRIORITY + 2, NX_WEB_HTTP_SERVER_PRIORITY + 2, TX_NO_TIME_SLICE, TX_AUTO_START);
164     pointer =  pointer + DEMO_STACK_SIZE;
165     if (status)
166         error_counter++;
167 
168     /* Create the Client packet pool.  */
169     status =  nx_packet_pool_create(&client_pool, "HTTP Client Packet Pool", CLIENT_PACKET_SIZE,
170                                     pointer, CLIENT_PACKET_SIZE*8);
171     pointer = pointer + CLIENT_PACKET_SIZE * 8;
172     if (status)
173         error_counter++;
174 
175     /* Create an IP instance.  */
176     status = nx_ip_create(&client_ip, "HTTP Client IP", HTTP_CLIENT_ADDRESS,
177                           0xFFFFFF00UL, &client_pool, _nx_ram_network_driver_1024,
178                           pointer, 2048, 1);
179     pointer =  pointer + 2048;
180     if (status)
181         error_counter++;
182 
183     status  = nx_arp_enable(&client_ip, (void *) pointer, 1024);
184     pointer =  pointer + 2048;
185     if (status)
186         error_counter++;
187 
188      /* Enable TCP traffic.  */
189     status = nx_tcp_enable(&client_ip);
190     if (status)
191         error_counter++;
192 }
193 
194 #ifdef NX_WEB_HTTPS_ENABLE
195 /* Define the TLS setup callback function.  */
tls_setup_callback(NX_WEB_HTTP_CLIENT * client_ptr,NX_SECURE_TLS_SESSION * tls_session)196 static UINT tls_setup_callback(NX_WEB_HTTP_CLIENT *client_ptr, NX_SECURE_TLS_SESSION *tls_session)
197 {
198 UINT status;
199 
200 
201     /* Initialize and create TLS session.  */
202     status = nx_secure_tls_session_create(tls_session, &nx_crypto_tls_ciphers, crypto_metadata_client, sizeof(crypto_metadata_client));
203 
204     /* Check status.  */
205     if (status)
206     {
207         return(status);
208     }
209 
210     /* Allocate space for packet reassembly.  */
211     status = nx_secure_tls_session_packet_buffer_set(&(client_ptr -> nx_web_http_client_tls_session), tls_packet_buffer, sizeof(tls_packet_buffer));
212 
213     /* Check status.  */
214     if (status)
215     {
216         return(status);
217     }
218 
219     /* Add a CA Certificate to our trusted store for verifying incoming server certificates.  */
220     nx_secure_x509_certificate_initialize(&trusted_certificate, ca_cert_der, ca_cert_der_len, NX_NULL, 0, NULL, 0, NX_SECURE_X509_KEY_TYPE_NONE);
221     nx_secure_tls_trusted_certificate_add(&(client_ptr -> nx_web_http_client_tls_session), &trusted_certificate);
222 
223     /* Need to allocate space for the certificate coming in from the remote host.  */
224     nx_secure_tls_remote_certificate_allocate(&(client_ptr -> nx_web_http_client_tls_session), &remote_certificate, remote_cert_buffer, sizeof(remote_cert_buffer));
225     nx_secure_tls_remote_certificate_allocate(&(client_ptr -> nx_web_http_client_tls_session), &remote_issuer, remote_issuer_buffer, sizeof(remote_issuer_buffer));
226 
227     return(NX_SUCCESS);
228 }
229 #endif /* NX_WEB_HTTPS_ENABLE  */
230 
thread_client_entry(ULONG thread_input)231 void thread_client_entry(ULONG thread_input)
232 {
233 UINT            i;
234 UINT            status;
235 NX_PACKET       *recv_packet;
236 NX_PACKET       *my_packet;
237 CHAR            *buffer_ptr;
238 
239 
240     /* Give IP task and driver a chance to initialize the system. */
241     tx_thread_sleep(NX_IP_PERIODIC_RATE);
242 
243     /* Set server IP address.  */
244     server_ip_address.nxd_ip_address.v4 = HTTP_SERVER_ADDRESS;
245     server_ip_address.nxd_ip_version = NX_IP_VERSION_V4;
246 
247     /* First loop test HTTP, second loop test HTTPS.  */
248     for (i = 0; i < loop ; i++)
249     {
250         if (i == 0)
251         {
252 
253             /* Wait HTTP server started.  */
254             while(!http_server_start)
255             {
256                 tx_thread_sleep(NX_IP_PERIODIC_RATE);
257             }
258         }
259 #ifdef NX_WEB_HTTPS_ENABLE
260         else
261         {
262 
263             /* Wait HTTPS server started.  */
264             while(!https_server_start)
265             {
266                 tx_thread_sleep(NX_IP_PERIODIC_RATE);
267             }
268         }
269 #endif /* NX_WEB_HTTPS_ENABLE  */
270 
271         /* Create an HTTP client instance.  */
272         status = nx_web_http_client_create(&my_client, "HTTP Client", &client_ip, &client_pool, 1536);
273 
274         /* Check status.  */
275         if (status)
276             error_counter++;
277 
278 
279         /* Connect to server.  */
280         if (i == 0)
281         {
282             status = nx_web_http_client_connect(&my_client, &server_ip_address, NX_WEB_HTTP_SERVER_PORT, NX_WAIT_FOREVER);
283 
284             /* Check status.  */
285             if (status)
286                 error_counter++;
287         }
288 #ifdef NX_WEB_HTTPS_ENABLE
289         else
290         {
291             status = nx_web_http_client_secure_connect(&my_client, &server_ip_address, NX_WEB_HTTPS_SERVER_PORT,
292                                                        tls_setup_callback, NX_WAIT_FOREVER);
293 
294             /* Check status.  */
295             if (status)
296                 error_counter++;
297         }
298 #endif /* NX_WEB_HTTPS_ENABLE  */
299 
300         /* Allocate a packet.  */
301         status = nx_web_http_client_request_packet_allocate(&my_client, &my_packet, 1 * NX_IP_PERIODIC_RATE);
302         if(status)
303             error_counter++;
304 
305         /* Change 'G' to 'A' .*/
306         pkt[54] = 'A';
307 
308         /* Write Get packet into the packet payload.  */
309         status = nx_packet_data_append(my_packet, &pkt[54] , (sizeof(pkt) - 54), &client_pool, 1 * NX_IP_PERIODIC_RATE);
310         if(status)
311             error_counter++;
312 
313         /* Send the packet out.  */
314         status = _nx_web_http_client_send(&my_client, my_packet, 1 * NX_IP_PERIODIC_RATE);
315         if(status)
316         {
317             nx_packet_release(my_packet);
318             error_counter++;
319         }
320 
321         /* Receive the response from http server.  */
322         status = _nx_web_http_client_receive(&my_client, &recv_packet, 1 * NX_IP_PERIODIC_RATE);
323         if(status)
324             error_counter++;
325         else
326         {
327             buffer_ptr = (CHAR *)recv_packet ->nx_packet_prepend_ptr;
328 
329             /* Check the status, If success , it should be 501. */
330             if((buffer_ptr[9] != '5') || (buffer_ptr[10] != '0') || (buffer_ptr[11] != '1'))
331                 error_counter++;
332 
333             nx_packet_release(recv_packet);
334         }
335 
336         status = nx_web_http_client_delete(&my_client);
337         if (status)
338             error_counter++;
339 
340         /* Set the flag.  */
341         if (i == 0)
342         {
343             http_client_stop = 1;
344         }
345 #ifdef NX_WEB_HTTPS_ENABLE
346         else
347         {
348             https_client_stop = 1;
349         }
350 #endif /* NX_WEB_HTTPS_ENABLE  */
351     }
352 
353     if(error_counter)
354     {
355         printf("ERROR!\n");
356         test_control_return(1);
357     }
358     else
359     {
360         printf("SUCCESS!\n");
361         test_control_return(0);
362     }
363 }
364 
365 
366 /* Define the helper HTTP server thread.  */
thread_server_entry(ULONG thread_input)367 void    thread_server_entry(ULONG thread_input)
368 {
369 UINT            i;
370 UINT            status;
371 FX_FILE         my_file;
372 UINT            server_port = NX_WEB_HTTP_SERVER_PORT;
373 
374 
375     /* Print out test information banner.  */
376     printf("NetX Test:   Web Status 501 Test.......................................");
377 
378     /* Check for earlier error. */
379     if(error_counter)
380     {
381         printf("ERROR!\n");
382         test_control_return(1);
383     }
384 
385     fx_media_format(&ram_disk,
386                     _fx_ram_driver,               // Driver entry
387                     ram_disk_memory,              // RAM disk memory pointer
388                     media_memory,                 // Media buffer pointer
389                     sizeof(media_memory),         // Media buffer size
390                     "MY_RAM_DISK",                // Volume Name
391                     1,                            // Number of FATs
392                     32,                           // Directory Entries
393                     0,                            // Hidden sectors
394                     256,                          // Total sectors
395                     512,                          // Sector size
396                     8,                            // Sectors per cluster
397                     1,                            // Heads
398                     1);                           // Sectors per track
399 
400     /* Open the RAM disk.  */
401     status = fx_media_open(&ram_disk, "RAM DISK", _fx_ram_driver, ram_disk_memory, media_memory, sizeof(media_memory)) ;
402     status += fx_file_create(&ram_disk, "index.htm");
403     status += fx_file_open(&ram_disk, &my_file, "index.htm", FX_OPEN_FOR_WRITE);
404     status += fx_file_write(&my_file, "https server", 12);
405     status += fx_file_close(&my_file);
406     if(status)
407         error_counter++;
408 
409     /* Give NetX a chance to initialize the system. */
410     tx_thread_sleep(NX_IP_PERIODIC_RATE);
411 
412     /* First loop test HTTP, second loop test HTTPS.  */
413     for (i = 0; i < loop; i++)
414     {
415 
416         if (i == 1)
417         {
418             server_port = NX_WEB_HTTPS_SERVER_PORT;
419         }
420 
421         /* Create the HTTP Server. */
422         status = nx_web_http_server_create(&my_server, "My HTTP Server", &server_ip, server_port, &ram_disk,
423                                            &server_stack, sizeof(server_stack), &server_pool,
424                                            NX_NULL, NX_NULL);
425         if (status)
426             error_counter++;
427 
428 #ifdef NX_WEB_HTTPS_ENABLE
429         /* Set TLS for HTTPS.  */
430         if (i == 1)
431         {
432             /* Initialize device certificate (used for all sessions in HTTPS server). */
433             memset(&certificate, 0, sizeof(certificate));
434             nx_secure_x509_certificate_initialize(&certificate, test_device_cert_der, test_device_cert_der_len, NX_NULL, 0, test_device_cert_key_der, test_device_cert_key_der_len, NX_SECURE_X509_KEY_TYPE_RSA_PKCS1_DER);
435 
436             /* Setup TLS session data for the TCP server. */
437             status = nx_web_http_server_secure_configure(&my_server, &nx_crypto_tls_ciphers,
438                                                          crypto_metadata_server, sizeof(crypto_metadata_server), tls_packet_buffer, sizeof(tls_packet_buffer),
439                                                          &certificate, NX_NULL, 0, NX_NULL, 0, NX_NULL, 0);
440             if (status)
441                 error_counter++;
442         }
443 #endif /* NX_WEB_HTTPS_ENABLE  */
444 
445         /* OK to start the HTTP Server.   */
446         status = nx_web_http_server_start(&my_server);
447         if (status)
448             error_counter++;
449 
450         /* Set the flag.  */
451         if (i == 0)
452         {
453             http_server_start = 1;
454 
455             /* Wait HTTP test finished.  */
456             while(!http_client_stop)
457             {
458                 tx_thread_sleep(NX_IP_PERIODIC_RATE);
459             }
460         }
461 #ifdef NX_WEB_HTTPS_ENABLE
462         else
463         {
464             https_server_start = 1;
465 
466             /* Wait HTTPS test finished.  */
467             while(!https_client_stop)
468             {
469                 tx_thread_sleep(NX_IP_PERIODIC_RATE);
470             }
471         }
472 #endif /* NX_WEB_HTTPS_ENABLE  */
473 
474         status = nx_web_http_server_delete(&my_server);
475         if (status)
476             error_counter++;
477     }
478 }
479 
480 #else
481 
482 #ifdef CTEST
test_application_define(void * first_unused_memory)483 VOID test_application_define(void *first_unused_memory)
484 #else
485 void    netx_web_status_501_test_application_define(void *first_unused_memory)
486 #endif
487 {
488 
489     /* Print out test information banner.  */
490     printf("NetX Test:   Web Status 501 Test.......................................N/A\n");
491 
492     test_control_return(3);
493 }
494 #endif
495