root/common/trunk/tests/test_net_udp.c @ 514

Revision 514, 12.3 KB (checked in by ucacoxh, 14 years ago)

- ifdef'ed out FreeBSD bug check on Win32 as it uses fork and exec and I

dont have the energy to hack in CreateProcess?() code for a FreeBSD
specific bug check (no longer present in 4.1 btw).

Reported by Michael Stovenour <michael.stovenour@…>

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1/*
2 * FILE:    test_net_udp.c
3 * AUTHORS: Colin Perkins
4 *
5 * Copyright (c) 2000 University College London
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, is permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 *    notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 *    notice, this list of conditions and the following disclaimer in the
15 *    documentation and/or other materials provided with the distribution.
16 * 3. All advertising materials mentioning features or use of this software
17 *    must display the following acknowledgement:
18 *      This product includes software developed by the Computer Science
19 *      Department at University College London
20 * 4. Neither the name of the University nor of the Department may be used
21 *    to endorse or promote products derived from this software without
22 *    specific prior written permission.
23 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND
24 * ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE
27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33 * SUCH DAMAGE.
34 */
35
36#include "config_unix.h"
37#include "config_win32.h"
38#include "debug.h"
39#include "net_udp.h"
40#include "test_net_udp.h"
41
42#define BUFSIZE 1024
43
44static void randomize(char buf[], int buflen)
45{
46        int     i;
47
48        for (i = 0; i < buflen; i++) {
49                buf[i] = (lrand48() && 0xff00) >> 8;
50        }
51}
52
53void test_net_udp(void)
54{
55        struct timeval   timeout;
56        socket_udp      *s1, *s2;
57        char             buf1[BUFSIZE], buf2[BUFSIZE];
58        const char      *hname;
59        int              rc, i;
60       
61#ifndef WIN32
62
63        /* "BSD" bug test that appears in this function uses fork and
64         * exec, that are not present on WIN32.  Since the original
65         * bug has not been seen on Win32 it's probably not worth
66         * converting to use CreateProcess() */
67
68        int status_parent, status_child;
69
70#endif /* WIN32 */
71
72        srand48(time(NULL));
73
74        /**********************************************************************/
75        /* The first test is to loopback a packet to ourselves...             */
76        printf("UDP/IP networking (IPv4 loopback)...... "); fflush(stdout);
77        s1 = udp_init("127.0.0.1", 5000, 5000, 1);
78        if (s1 == NULL) {
79                printf("fail: cannot initialize socket\n");
80                return;
81        }
82        randomize(buf1, BUFSIZE);
83        randomize(buf2, BUFSIZE);
84        if (udp_send(s1, buf1, BUFSIZE) < 0) {
85                perror("fail");
86                goto abort_loopback;
87        }
88        timeout.tv_sec  = 1;
89        timeout.tv_usec = 0;
90        udp_fd_zero();
91        udp_fd_set(s1);
92        rc = udp_select(&timeout);
93        if (rc < 0) {
94                perror("fail");
95                goto abort_loopback;
96        }
97        if (rc == 0) {
98                printf("fail: no data waiting\n");
99                goto abort_loopback;
100        }
101        if (!udp_fd_isset(s1)) {
102                printf("fail: no data on file descriptor\n");
103                goto abort_loopback;
104        }
105        if (udp_recv(s1, buf2, BUFSIZE) < 0) {
106                perror("fail");
107                goto abort_loopback;
108        }
109        if (memcmp(buf1, buf2, BUFSIZE) != 0) {
110                printf("fail: buffer corrupt\n");
111                goto abort_loopback;
112        }
113        printf("pass\n");
114abort_loopback:
115        hname = udp_host_addr(s1); /* we need this for the unicast test... */
116        udp_exit(s1);
117
118        /**********************************************************************/
119        /* Now we send a packet to ourselves via our real network address...  */
120        printf("UDP/IP networking (IPv4 unicast)....... "); fflush(stdout);
121        s1 = udp_init(hname, 5000, 5001, 1);
122        if (s1 == NULL) {
123                printf("fail: cannot initialize socket\n");
124                return;
125        }
126
127        s2 = udp_init(hname, 5001, 5000, 1);
128        if (s2 == NULL) {
129                printf("fail: cannot initialize socket\n");
130                return;
131        }
132
133        randomize(buf1, BUFSIZE);
134        randomize(buf2, BUFSIZE);
135        if (udp_send(s1, buf1, BUFSIZE) < 0) {
136                perror("fail");
137                goto abort_unicast;
138        }
139        timeout.tv_sec  = 1;
140        timeout.tv_usec = 0;
141        udp_fd_zero();
142        udp_fd_set(s1);
143        udp_fd_set(s2);
144        rc = udp_select(&timeout);
145        if (rc < 0) {
146                perror("fail");
147                goto abort_unicast;
148        }
149        if (rc == 0) {
150                printf("fail: no data waiting (no route to %s?)\n", hname);
151                goto abort_unicast;
152        }
153        if (!udp_fd_isset(s2)) {
154                printf("fail: no data on file descriptor\n");
155                goto abort_unicast;
156        }
157        if (udp_recv(s2, buf2, BUFSIZE) < 0) {
158                perror("fail");
159                goto abort_unicast;
160        }
161        if (memcmp(buf1, buf2, BUFSIZE) != 0) {
162                printf("fail: buffer corrupt\n");
163                goto abort_unicast;
164        }
165        printf("pass\n");
166abort_unicast:
167        udp_exit(s1);
168        udp_exit(s2);
169
170        /**********************************************************************/
171        /* Loopback a packet to ourselves via multicast...                    */
172        printf("UDP/IP networking (IPv4 multicast)..... "); fflush(stdout);
173        s1 = udp_init("224.2.0.1", 5000, 5000, 1);
174        if (s1 == NULL) {
175                printf("fail: cannot initialize socket\n");
176                return;
177        }
178        randomize(buf1, BUFSIZE);
179        randomize(buf2, BUFSIZE);
180        if (udp_send(s1, buf1, BUFSIZE) < 0) {
181                perror("fail");
182                goto abort_multicast;
183        }
184        timeout.tv_sec  = 1;
185        timeout.tv_usec = 0;
186        udp_fd_zero();
187        udp_fd_set(s1);
188        rc = udp_select(&timeout);
189        if (rc < 0) {
190                perror("fail");
191                goto abort_multicast;
192        }
193        if (rc == 0) {
194                printf("fail: no data waiting (no multicast loopback route?)\n");
195                goto abort_multicast;
196        }
197        if (!udp_fd_isset(s1)) {
198                printf("fail: no data on file descriptor\n");
199                goto abort_multicast;
200        }
201        if (udp_recv(s1, buf2, BUFSIZE) < 0) {
202                perror("fail");
203                goto abort_multicast;
204        }
205        if (memcmp(buf1, buf2, BUFSIZE) != 0) {
206                printf("fail: buffer corrupt\n");
207                goto abort_multicast;
208        }
209        printf("pass\n");
210abort_multicast:
211        udp_exit(s1);
212
213        /**********************************************************************/
214        /* Loopback a packet to ourselves via multicast, checking lengths...  */
215        printf("UDP/IP networking (IPv4 length check).. "); fflush(stdout);
216        s1 = udp_init("224.2.0.1", 5000, 5000, 1);
217        if (s1 == NULL) {
218                printf("fail: cannot initialize socket\n");
219                return;
220        }
221        for (i = 1; i < BUFSIZE; i++) {
222                randomize(buf1, i);
223                randomize(buf2, i);
224                if (udp_send(s1, buf1, i) < 0) {
225                        perror("fail");
226                        goto abort_length;
227                }
228                timeout.tv_sec  = 1;
229                timeout.tv_usec = 0;
230                udp_fd_zero();
231                udp_fd_set(s1);
232                rc = udp_select(&timeout);
233                if (rc < 0) {
234                        perror("fail");
235                        goto abort_length;
236                }
237                if (rc == 0) {
238                        printf("fail: no data waiting (no multicast loopback route?)\n");
239                        goto abort_length;
240                }
241                if (!udp_fd_isset(s1)) {
242                        printf("fail: no data on file descriptor\n");
243                        goto abort_length;
244                }
245                if (udp_recv(s1, buf2, BUFSIZE) != i) {
246                        perror("fail");
247                        goto abort_length;
248                }
249                if (memcmp(buf1, buf2, i) != 0) {
250                        printf("fail: buffer corrupt\n");
251                        goto abort_length;
252                }
253        }
254        printf("pass\n");
255abort_length:
256        udp_exit(s1);
257
258
259
260#ifdef HAVE_IPv6
261        /**********************************************************************/
262        /* The first test is to loopback a packet to ourselves...             */
263        printf("UDP/IP networking (IPv6 loopback)...... "); fflush(stdout);
264        s1 = udp_init("::1", 5000, 5000, 1);
265        if (s1 == NULL) {
266                printf("fail: cannot initialize socket\n");
267                return;
268        }
269        randomize(buf1, BUFSIZE);
270        randomize(buf2, BUFSIZE);
271        if (udp_send(s1, buf1, BUFSIZE) < 0) {
272                perror("fail");
273                goto abort_loopback_ipv6;
274        }
275        timeout.tv_sec  = 1;
276        timeout.tv_usec = 0;
277        udp_fd_zero();
278        udp_fd_set(s1);
279        rc = udp_select(&timeout);
280        if (rc < 0) {
281                perror("fail");
282                goto abort_loopback_ipv6;
283        }
284        if (rc == 0) {
285                printf("fail: no data waiting\n");
286                goto abort_loopback_ipv6;
287        }
288        if (!udp_fd_isset(s1)) {
289                printf("fail: no data on file descriptor\n");
290                goto abort_loopback_ipv6;
291        }
292        if (udp_recv(s1, buf2, BUFSIZE) < 0) {
293                perror("fail");
294                goto abort_loopback_ipv6;
295        }
296        if (memcmp(buf1, buf2, BUFSIZE) != 0) {
297                printf("fail: buffer corrupt\n");
298                goto abort_loopback_ipv6;
299        }
300        printf("pass\n");
301abort_loopback_ipv6:
302        udp_exit(s1);
303
304        /**********************************************************************/
305        /* Loopback a packet to ourselves via multicast. The address is the   */
306        /* SAP address, but we use a different port.                          */
307        printf("UDP/IP networking (IPv6 multicast)..... "); fflush(stdout);
308        s1 = udp_init("ff01::2:7ffe", 5000, 5000, 1);
309        if (s1 == NULL) {
310                printf("fail: cannot initialize socket\n");
311                return;
312        }
313        randomize(buf1, BUFSIZE);
314        randomize(buf2, BUFSIZE);
315        if (udp_send(s1, buf1, BUFSIZE) < 0) {
316                perror("fail");
317                goto abort_multicast_ipv6;
318        }
319        timeout.tv_sec  = 1;
320        timeout.tv_usec = 0;
321        udp_fd_zero();
322        udp_fd_set(s1);
323        rc = udp_select(&timeout);
324        if (rc < 0) {
325                perror("fail");
326                goto abort_multicast_ipv6;
327        }
328        if (rc == 0) {
329                printf("fail: no data waiting (no multicast loopback route?)\n");
330                goto abort_multicast_ipv6;
331        }
332        if (!udp_fd_isset(s1)) {
333                printf("fail: no data on file descriptor\n");
334                goto abort_multicast_ipv6;
335        }
336        if (udp_recv(s1, buf2, BUFSIZE) < 0) {
337                perror("fail");
338                goto abort_multicast_ipv6;
339        }
340        if (memcmp(buf1, buf2, BUFSIZE) != 0) {
341                printf("fail: buffer corrupt\n");
342                goto abort_multicast_ipv6;
343        }
344        hname = udp_host_addr(s1); /* we need this for the unicast test... */
345        printf("pass\n");
346abort_multicast_ipv6:
347        udp_exit(s1);
348#else
349        printf("UDP/IP networking (IPv6 loopback)...... disabled\n");
350        printf("UDP/IP networking (IPv6 unicast)....... disabled\n");
351        printf("UDP/IP networking (IPv6 multicast)..... disabled\n");
352#endif
353
354        /**********************************************************************/
355
356#ifdef WIN32
357        printf("UDP/IP networking (FreeBSD bug)........ disabled\n");
358#else
359        printf("UDP/IP networking (FreeBSD bug)........ "); fflush(stdout);
360        status_parent = 0;
361        randomize(buf1, 64);
362        s1 = udp_init("224.2.0.1", 5000, 5000, 1);
363        if (s1 == NULL) {
364                printf("fail (parent): cannot initialize socket\n");
365                return;
366        }
367        rc = fork();
368        if (rc == -1) {
369                printf("fail: cannot fork\n");
370                goto abort_bsd;
371        } else if (rc == 0) {
372                /* child */
373                s2 = udp_init("224.2.0.1", 5000, 5000, 1);
374                if (s2 == NULL) {
375                        printf("fail (child): cannot initialize socket\n");
376                        exit(0);
377                }
378                if (udp_send(s2, buf1, 64) < 0) {
379                        perror("fail (child)");
380                        exit(0);
381                }
382                timeout.tv_sec  = 10;
383                timeout.tv_usec = 0;
384                udp_fd_zero();
385                udp_fd_set(s2);
386                rc = udp_select(&timeout);
387                if (rc < 0) {
388                        perror("fail (child)");
389                        exit(0);
390                }
391                if (rc == 0) {
392                        printf("fail (child): no data waiting (no multicast loopback route?)\n");
393                        exit(0);
394                }
395                if (!udp_fd_isset(s2)) {
396                        printf("fail (child): no data on file descriptor\n");
397                        exit(0);
398                }
399                rc = udp_recv(s2, buf2, BUFSIZE);
400                if (rc < 0) {
401                        perror("fail (child)");
402                        exit(0);
403                }
404                if (rc != 64) {
405                        printf("fail (child): read size incorrect (%d != %d)\n", rc, 64);
406                        exit(0);
407                }
408                if (memcmp(buf1, buf2, 64) != 0) {
409                        printf("fail (child): buffer corrupt\n");
410                        exit(0);
411                }
412                udp_exit(s2);
413                exit(1);
414        } else {
415                /* parent */
416                timeout.tv_sec  = 10;
417                timeout.tv_usec = 0;
418                udp_fd_zero();
419                udp_fd_set(s1);
420                rc = udp_select(&timeout);
421                if (rc < 0) {
422                        perror("fail (parent)");
423                        goto abort_bsd;
424                }
425                if (rc == 0) {
426                        printf("fail (parent): no data waiting (no multicast loopback route?)\n");
427                        goto abort_bsd;
428                }
429                if (!udp_fd_isset(s1)) {
430                        printf("fail (parent): no data on file descriptor\n");
431                        goto abort_bsd;
432                }
433                rc = udp_recv(s1, buf2, BUFSIZE);
434                if (rc < 0) {
435                        perror("fail (parent)");
436                        goto abort_bsd;
437                }
438                if (rc != 64) {
439                        printf("fail (parent): read size incorrect (%d != %d)\n", rc, 64);
440                        goto abort_bsd;
441                }
442                if (memcmp(buf1, buf2, 64) != 0) {
443                        printf("fail (parent): buffer corrupt\n");
444                        goto abort_bsd;
445                }
446                status_parent = 1;
447        }
448abort_bsd:
449        wait(&status_child);
450        if (status_parent && status_child) {
451                printf("pass\n");
452        }
453        udp_exit(s1);
454#endif /* WIN32 */
455
456        return;
457}
Note: See TracBrowser for help on using the browser.