1 /* This case tests the basic connection of PPPoE server and client.  */
2 
3 #include   "nx_pppoe_client.h"
4 #include   "nx_pppoe_server.h"
5 #include   "tx_api.h"
6 #include   "nx_api.h"
7 #include   "nx_ppp.h"
8 
9 extern void test_control_return(UINT);
10 
11 #if !defined(NX_DISABLE_IPV4) && defined(NX_PPP_PPPOE_ENABLE) && defined(NX_PPPOE_SERVER_INITIALIZE_DRIVER_ENABLE) && defined(NX_PPPOE_CLIENT_INITIALIZE_DRIVER_ENABLE) && (NX_PHYSICAL_HEADER >= 24) && !defined(NX_PPPOE_SERVER_SESSION_CONTROL_ENABLE)
12 
13 /* Defined NX_PPP_PPPOE_ENABLE if use PPP, since PPP module has been modified to match PPPoE moduler under this definition.  */
14 
15 /* If the driver is not initialized in other module, define NX_PPPOE_SERVER_INITIALIZE_DRIVER_ENABLE to initialize the driver in PPPoE module .
16    In this demo, the driver has been initialized in IP module.  */
17 
18 /* NX_PPPOE_SERVER_SESSION_CONTROL_ENABLE:
19    If defined, enables the feature that controls the PPPoE session.
20    PPPoE server does not automatically response to the request until application call specific API.  */
21 
22 /* Define the block size.  */
23 #define     NX_PACKET_POOL_SIZE     ((1536 + sizeof(NX_PACKET)) * 12)
24 #define     DEMO_STACK_SIZE         2048
25 #define     PPPOE_THREAD_SIZE       2048
26 
27 /* Define the ThreadX and NetX object control blocks...  */
28 static TX_THREAD               thread_server;
29 static TX_THREAD               thread_client;
30 
31 /* Define the packet pool and IP instance for normal IP instnace.  */
32 static NX_PACKET_POOL          pool_server;
33 static NX_IP                   ip_server;
34 static NX_PACKET_POOL          pool_client;
35 static NX_IP                   ip_client;
36 static CHAR                    pool_buffer_server[NX_PACKET_POOL_SIZE];
37 static CHAR                    pool_buffer_client[NX_PACKET_POOL_SIZE];
38 
39 /* Define the PPP Server instance.  */
40 static NX_PPP                  ppp_server;
41 static NX_PPP                  ppp_client;
42 
43 /* Define the PPPoE Server instance.  */
44 static NX_PPPOE_SERVER         pppoe_server;
45 static NX_PPPOE_CLIENT         pppoe_client;
46 
47 /* Define the counters.  */
48 static CHAR                    *pointer;
49 static ULONG                   error_counter;
50 
51 /* Define thread prototypes.  */
52 static void    thread_server_entry(ULONG thread_input);
53 static void    thread_client_entry(ULONG thread_input);
54 
55 /***** Substitute your PPP driver entry function here *********/
56 extern void    _nx_ppp_driver(NX_IP_DRIVER *driver_req_ptr);
57 
58 /***** Substitute your Ethernet driver entry function here *********/
59 extern void    _nx_ram_network_driver(NX_IP_DRIVER *driver_req_ptr);
60 
61 /* Define the callback functions.  */
62 static void    pppoe_server_packet_receive(UINT interfaceHandle, ULONG length, UCHAR *data, UINT packet_id);
63 
64 /* Define the porting layer function for PPP.
65    Functions to be provided by PPP for calling by the PPPoE Stack.  */
66 static void    ppp_server_packet_send(NX_PACKET *packet_ptr);
67 
68 /* Define the porting layer function for PPP.
69    Functions to be provided by PPP for calling by the PPPoE Stack.  */
70 static void    ppp_client_packet_send(NX_PACKET *packet_ptr);
71 static void    pppoe_client_packet_receive(NX_PACKET *packet_ptr);
72 
73 #define SERVER_ADDRESS IP_ADDRESS(192, 168, 10, 43)
74 #define CLIENT_ADDRESS IP_ADDRESS(192, 168, 10, 44)
75 
76 #define SERVICE_NAME_1 "test_service_1"
77 #define SERVICE_NAME_2 "test_service_2"
78 
generate_login(CHAR * name,CHAR * password)79 static UINT generate_login(CHAR *name, CHAR *password)
80 {
81 
82     /* Make a name and password, called "myname" and "mypassword".  */
83     name[0] = 'm';
84     name[1] = 'y';
85     name[2] = 'n';
86     name[3] = 'a';
87     name[4] = 'm';
88     name[5] = 'e';
89     name[6] = (CHAR) 0;
90 
91     password[0] = 'm';
92     password[1] = 'y';
93     password[2] = 'p';
94     password[3] = 'a';
95     password[4] = 's';
96     password[5] = 's';
97     password[6] = 'w';
98     password[7] = 'o';
99     password[8] = 'r';
100     password[9] = 'd';
101     password[10] = (CHAR) 0;
102 
103     return(NX_SUCCESS);
104 }
105 
verify_login(CHAR * name,CHAR * password)106 static UINT verify_login(CHAR *name, CHAR *password)
107 {
108 
109 if ((name[0] == 'm') &&
110     (name[1] == 'y') &&
111     (name[2] == 'n') &&
112     (name[3] == 'a') &&
113     (name[4] == 'm') &&
114     (name[5] == 'e') &&
115     (name[6] == (CHAR) 0) &&
116     (password[0] == 'm') &&
117     (password[1] == 'y') &&
118     (password[2] == 'p') &&
119     (password[3] == 'a') &&
120     (password[4] == 's') &&
121     (password[5] == 's') &&
122     (password[6] == 'w') &&
123     (password[7] == 'o') &&
124     (password[8] == 'r') &&
125     (password[9] == 'd') &&
126     (password[10] == (CHAR) 0))
127         return(NX_SUCCESS);
128    else
129         return(NX_PPP_ERROR);
130 }
131 
132 /* Define what the initial system looks like.  */
133 
134 #ifdef CTEST
test_application_define(void * first_unused_memory)135 VOID test_application_define(void *first_unused_memory)
136 #else
137 void    netx_pppoe_basic_test_application_define(void *first_unused_memory)
138 #endif
139 {
140 
141 UINT    status;
142 
143     /* Setup the working pointer.  */
144     pointer =  (CHAR *) first_unused_memory;
145 
146     /* Initialize the NetX system.  */
147     nx_system_initialize();
148 
149     /* Create a packet pool for normal IP instance.  */
150     status = nx_packet_pool_create(&pool_server, "Server Packet Pool",
151                                    (1536 + sizeof(NX_PACKET)),
152                                    pool_buffer_server, NX_PACKET_POOL_SIZE);
153 
154     /* Check for error.  */
155     if (status)
156         error_counter++;
157 
158     /* Create an normal IP instance.  */
159     status = nx_ip_create(&ip_server, "Server IP Instance", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFF00UL, &pool_server, nx_ppp_driver,
160                           pointer, 2048, 1);
161     pointer = pointer + 2048;
162 
163     /* Check for error.  */
164     if (status)
165         error_counter++;
166 
167     /* Create the PPP instance.  */
168     status = nx_ppp_create(&ppp_server, "PPP Server Instance", &ip_server, pointer, 2048, 1, &pool_server, NX_NULL, NX_NULL);
169     pointer = pointer + 2048;
170 
171     /* Check for PPP create error.   */
172     if (status)
173         error_counter++;
174 
175     /* Set the PPP packet send function.  */
176     status = nx_ppp_packet_send_set(&ppp_server, ppp_server_packet_send);
177 
178     /* Check for PPP packet send function set error.   */
179     if (status)
180         error_counter++;
181 
182     /* Define IP address. This PPP instance is effectively the server since it has both IP addresses. */
183     status = nx_ppp_ip_address_assign(&ppp_server, SERVER_ADDRESS, CLIENT_ADDRESS);
184 
185     /* Check for PPP IP address assign error.   */
186     if (status)
187         error_counter++;
188 
189     /* Setup PAP, this PPP instance is effectively the server since it will verify the name and password.  */
190     status = nx_ppp_pap_enable(&ppp_server, NX_NULL, verify_login);
191 
192     /* Check for PPP PAP enable error.  */
193     if (status)
194         error_counter++;
195 
196     /* Enable ARP and supply ARP cache memory for Normal IP Instance.  */
197     status = nx_arp_enable(&ip_server, (void *) pointer, 1024);
198     pointer = pointer + 1024;
199 
200     /* Check for ARP enable errors.  */
201     if (status)
202         error_counter++;
203 
204     /* Enable ICMP */
205     status = nx_icmp_enable(&ip_server);
206     if(status)
207         error_counter++;
208 
209     /* Create the main thread.  */
210     tx_thread_create(&thread_server, "thread server", thread_server_entry, 0,
211                      pointer, DEMO_STACK_SIZE,
212                      5, 5, TX_NO_TIME_SLICE, TX_AUTO_START);
213     pointer =  pointer + DEMO_STACK_SIZE;
214 
215     /* Create a packet pool for normal IP instance.  */
216     status = nx_packet_pool_create(&pool_client, "Client Packet Pool",
217                                    (1536 + sizeof(NX_PACKET)),
218                                    pool_buffer_client, NX_PACKET_POOL_SIZE);
219 
220     /* Check for error.  */
221     if (status)
222         error_counter++;
223 
224     /* Create an normal IP instance.  */
225     status = nx_ip_create(&ip_client, "Client IP Instance", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFF00UL, &pool_client, nx_ppp_driver,
226                           pointer, 2048, 1);
227     pointer = pointer + 2048;
228 
229     /* Check for error.  */
230     if (status)
231         error_counter++;
232 
233     /* Create the PPP instance.  */
234     status = nx_ppp_create(&ppp_client, "PPP Client Instance", &ip_client, pointer, 2048, 1, &pool_client, NX_NULL, NX_NULL);
235     pointer = pointer + 2048;
236 
237     /* Check for PPP create error.   */
238     if (status)
239         error_counter++;
240 
241     /* Set the PPP packet send function.  */
242     status = nx_ppp_packet_send_set(&ppp_client, ppp_client_packet_send);
243 
244     /* Check for PPP packet send function set error.   */
245     if (status)
246         error_counter++;
247 
248     /* Define IP address. This PPP instance is effectively the client since it doesn't have any IP addresses. */
249     status = nx_ppp_ip_address_assign(&ppp_client, IP_ADDRESS(0, 0, 0, 0), IP_ADDRESS(0, 0, 0, 0));
250 
251     /* Check for PPP IP address assign error.   */
252     if (status)
253         error_counter++;
254 
255     /* Setup PAP, this PPP instance is effectively the since it generates the name and password for the peer..  */
256     status = nx_ppp_pap_enable(&ppp_client, generate_login, NX_NULL);
257 
258     /* Check for PPP PAP enable error.  */
259     if (status)
260         error_counter++;
261 
262     /* Enable ARP and supply ARP cache memory for Normal IP Instance.  */
263     status = nx_arp_enable(&ip_client, (void *) pointer, 1024);
264     pointer = pointer + 1024;
265 
266     /* Check for ARP enable errors.  */
267     if (status)
268         error_counter++;
269 
270     /* Enable ICMP */
271     status = nx_icmp_enable(&ip_client);
272     if(status)
273         error_counter++;
274 
275     /* Create the main thread.  */
276     tx_thread_create(&thread_client, "thread client", thread_client_entry, 0,
277                      pointer, DEMO_STACK_SIZE,
278                      6, 6, TX_NO_TIME_SLICE, TX_DONT_START);
279     pointer =  pointer + DEMO_STACK_SIZE;
280 
281 }
282 
thread_client_entry(ULONG thread_input)283 static void    thread_client_entry(ULONG thread_input)
284 {
285 UINT    status;
286 ULONG   ip_status;
287 NX_PACKET *recv_pkt;
288 ULONG   ip_address;
289 ULONG   network_mask;
290 
291     /* Create the PPPoE instance.  */
292     status = nx_pppoe_client_create(&pppoe_client, (UCHAR *)"PPPoE Client", &ip_client, 0, &pool_client, pointer, PPPOE_THREAD_SIZE, 4, _nx_ram_network_driver, pppoe_client_packet_receive);
293     pointer = pointer + PPPOE_THREAD_SIZE;
294     if (status)
295     {
296         error_counter++;
297     }
298 
299     /* Set service name.  */
300     nx_pppoe_client_service_name_set(&pppoe_client, SERVICE_NAME_1);
301 
302     /* Establish PPPoE Client sessione.  */
303     status = nx_pppoe_client_session_connect(&pppoe_client, NX_WAIT_FOREVER);
304     if (status)
305     {
306         error_counter++;
307     }
308 
309     /* Wait for the link to come up.  */
310     status = nx_ip_interface_status_check(&ip_client, 0, NX_IP_ADDRESS_RESOLVED, &ip_status, NX_WAIT_FOREVER);
311     if (status)
312     {
313         error_counter++;
314     }
315 
316     /* Check client IP address.  */
317     status = nx_ip_address_get(&ip_client, &ip_address, &network_mask);
318     if (status || ip_address != CLIENT_ADDRESS)
319     {
320         error_counter++;
321     }
322 
323     /* Ping test.  */
324     status = nx_icmp_ping(&ip_client, SERVER_ADDRESS, "abcd", 4, &recv_pkt, NX_WAIT_FOREVER);
325     if (status)
326     {
327         error_counter++;
328     }
329     else
330     {
331         nx_packet_release(recv_pkt);
332     }
333 
334     if(error_counter)
335     {
336         printf("ERROR!\n");
337         test_control_return(1);
338     }
339     else
340     {
341         printf("SUCCESS!\n");
342         test_control_return(0);
343     }
344 }
345 
346 /* PPPoE Client receive function.  */
pppoe_client_packet_receive(NX_PACKET * packet_ptr)347 static void    pppoe_client_packet_receive(NX_PACKET *packet_ptr)
348 {
349 
350     /* Call PPP Client to receive the PPP data fame.  */
351     nx_ppp_packet_receive(&ppp_client, packet_ptr);
352 }
353 
354 /* PPP Client send function.  */
ppp_client_packet_send(NX_PACKET * packet_ptr)355 static void    ppp_client_packet_send(NX_PACKET *packet_ptr)
356 {
357 
358     /* Directly Call PPPoE send function to send out the data through PPPoE module.  */
359     nx_pppoe_client_session_packet_send(&pppoe_client, packet_ptr);
360 }
361 
362 /* Define the server threads.  */
363 
thread_server_entry(ULONG thread_input)364 static void    thread_server_entry(ULONG thread_input)
365 {
366 UINT    status;
367 ULONG   ip_status;
368 ULONG   ip_address;
369 ULONG   network_mask;
370 UCHAR   *service_names[2];
371 UINT    service_names_count = 2;
372 
373     /* Print out test information banner.  */
374     printf("NetX Test:   PPPoE Basic Test..........................................");
375 
376     /* Create the PPPoE instance.  */
377     status =  nx_pppoe_server_create(&pppoe_server, (UCHAR *)"PPPoE Server",  &ip_server, 0, _nx_ram_network_driver,  &pool_server, pointer, PPPOE_THREAD_SIZE, 4);
378     pointer = pointer + PPPOE_THREAD_SIZE;
379     if (status)
380     {
381         error_counter++;
382     }
383 
384     /* Set the callback notify function.  */
385     status = nx_pppoe_server_callback_notify_set(&pppoe_server, NX_NULL, NX_NULL, NX_NULL, NX_NULL, pppoe_server_packet_receive, NX_NULL);
386     if (status)
387     {
388         error_counter++;
389     }
390 
391     /* Set service name.  */
392     service_names[0] = SERVICE_NAME_1;
393     service_names[1] = SERVICE_NAME_2;
394     nx_pppoe_server_service_name_set(&pppoe_server, service_names, service_names_count);
395 
396     /* Enable PPPoE Server.  */
397     status = nx_pppoe_server_enable(&pppoe_server);
398     if (status)
399     {
400         error_counter++;
401     }
402 
403     tx_thread_resume(&thread_client);
404 
405     /* Wait for the link to come up.  */
406     status = nx_ip_interface_status_check(&ip_server, 0, NX_IP_ADDRESS_RESOLVED, &ip_status, NX_WAIT_FOREVER);
407     if (status)
408     {
409         error_counter++;
410     }
411 
412     /* Check server IP address.  */
413     status = nx_ip_address_get(&ip_server, &ip_address, &network_mask);
414     if (status || ip_address != SERVER_ADDRESS)
415     {
416         error_counter++;
417     }
418 }
419 
pppoe_server_packet_receive(UINT interfaceHandle,ULONG length,UCHAR * data,UINT packet_id)420 static void    pppoe_server_packet_receive(UINT interfaceHandle, ULONG length, UCHAR *data, UINT packet_id)
421 {
422 
423 NX_PACKET   *packet_ptr;
424 
425     /* Get the notify that receive the PPPoE Session data.  */
426 
427     /* Call PPP Server to receive the PPP data fame.  */
428     packet_ptr = (NX_PACKET *)(packet_id);
429     nx_ppp_packet_receive(&ppp_server, packet_ptr);
430 }
431 
432 /* PPP Server send function.  */
ppp_server_packet_send(NX_PACKET * packet_ptr)433 static void    ppp_server_packet_send(NX_PACKET *packet_ptr)
434 {
435 
436 /* For test, the session should be the first session, so set interfaceHandle as 0.  */
437 UINT    interfaceHandle = 0;
438 
439     /* Directly Call PPPoE send function to send out the data through PPPoE module.  */
440     nx_pppoe_server_session_packet_send(&pppoe_server, interfaceHandle, packet_ptr);
441 }
442 
443 #else
444 
445 #ifdef CTEST
test_application_define(void * first_unused_memory)446 VOID test_application_define(void *first_unused_memory)
447 #else
448 void    netx_pppoe_basic_test_application_define(void *first_unused_memory)
449 #endif
450 {
451 
452     /* Print out test information banner.  */
453     printf("NetX Test:   PPPoE Basic Test..........................................N/A\n");
454 
455     test_control_return(3);
456 }
457 #endif