From owner-freebsd-hackers Fri Dec 29 03:49:54 1995 Return-Path: owner-hackers Received: (from root@localhost) by freefall.freebsd.org (8.7.3/8.7.3) id DAA15930 for hackers-outgoing; Fri, 29 Dec 1995 03:49:54 -0800 (PST) Received: from iaehv.IAEhv.nl (root@iaehv.IAEhv.nl [192.87.208.2]) by freefall.freebsd.org (8.7.3/8.7.3) with SMTP id DAA15922 for ; Fri, 29 Dec 1995 03:49:49 -0800 (PST) Received: by iaehv.IAEhv.nl (8.6.12/1.63) id MAA13378; Fri, 29 Dec 1995 12:49:46 +0100 From: guido@IAEhv.nl (Guido van Rooij) Message-Id: <199512291149.MAA13378@iaehv.IAEhv.nl> X-Disclaimer: iaehv.nl is a public access UNIX system and cannot be held responsible for the opinions of its individual users. Subject: bug in UDP stack with our aliasing scheme :-( To: freebsd-hackers@freebsd.org Date: Fri, 29 Dec 1995 12:49:46 +0100 (MET) X-Mailer: ELM [version 2.4 PL25] Content-Type: text Sender: owner-hackers@freebsd.org Precedence: bulk I discovered a problem with our ip aliasing implementation: Suppose you have an interface, ed0, with ip 192.1.1.1 netmask 0xffffff00. Further there is an alias 192.1.1.2, with netmask 0xffffffff. Run the program attached below with argument 192.1.1.1. Send an UDP packet to 192.1.1.1. The program will only receive the data on fd1. When the program is run with argument 192.1.1.2 it receives input both on fd1 and fd2. When the alias is set to an ip on another subnet, say 192.1.2.1 with netmask 0xffffffff, this bug can be seen again. But when the netmask is changed to 0xffffff00, the UDP data will be deliverd correctly to only fd1. This definately is a bug. -Guido #include #include #include #include #include int main(int argc, char **argv) { fd_set mask; int on = 1; struct sockaddr_in sin; int s1,s2; long temp; bzero((char *)&sin, sizeof(sin)); sin.sin_family = AF_INET; temp = inet_addr(argv[1]);; if(temp==-1) { fprintf(stderr, "temp==-1\n"); } sin.sin_addr.s_addr = inet_addr(argv[1]);; sin.sin_port = htons(7787); if ((s1 = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { perror("socket"); exit(1); } if (setsockopt(s1, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof(on)) != 0) { perror("setsockopt"); } if (bind(s1, (struct sockaddr *)&sin, sizeof(sin))) { perror("bind"); } if ((s2 = socket(AF_INET, SOCK_DGRAM, 0)) < 0) { perror("socket"); exit(1); } if (setsockopt(s2, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof(on)) != 0) { perror("setsockopt"); } sin.sin_addr.s_addr = INADDR_ANY; if (bind(s2, (struct sockaddr *)&sin, sizeof(sin))) { perror("bind"); exit(1); } FD_ZERO(&mask); FD_SET(s1, &mask); FD_SET(s2, &mask); select(FD_SETSIZE, &mask, (fd_set *)NULL, (fd_set *)NULL, NULL); if(FD_ISSET(s1, &mask)) printf("s1 had input\n"); if(FD_ISSET(s2, &mask) ) printf("s2 had input\n"); }