From owner-freebsd-questions@FreeBSD.ORG Mon Aug 1 15:09:52 2011 Return-Path: Delivered-To: freebsd-questions@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id A8C1F1065676 for ; Mon, 1 Aug 2011 15:09:52 +0000 (UTC) (envelope-from kuku@kukulies.org) Received: from kukulies.org (mail.kukulies.org [78.47.239.221]) by mx1.freebsd.org (Postfix) with ESMTP id 4D3F18FC18 for ; Mon, 1 Aug 2011 15:09:51 +0000 (UTC) Received: by kukulies.org (Postfix, from userid 5001) id 147CF1AC003; Mon, 1 Aug 2011 17:09:51 +0200 (CEST) Received: from [172.27.4.215] (unknown [87.79.34.228]) by kukulies.org (Postfix) with ESMTPSA id ED1151AC002 for ; Mon, 1 Aug 2011 17:09:47 +0200 (CEST) Message-ID: <4E36C1B1.4090708@kukulies.org> Date: Mon, 01 Aug 2011 17:09:37 +0200 From: "Christoph P.U. Kukulies" User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:5.0) Gecko/20110624 Thunderbird/5.0 MIME-Version: 1.0 To: freebsd-questions@freebsd.org References: <4E352563.2070808@kukulies.org> In-Reply-To: <4E352563.2070808@kukulies.org> Content-Type: text/plain; charset=ISO-8859-15; format=flowed Content-Transfer-Encoding: 7bit Subject: Re: invalid argument in select() when peer socket is in FD_SET X-BeenThere: freebsd-questions@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: User questions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 01 Aug 2011 15:09:52 -0000 Am 31.07.2011 11:50, schrieb Christoph P.U. Kukulies: > I have written a small to test TCP/IP roundtrip times of the packets > in a proprietary protocol and while > compiling and running this server on different platforms (Windows > 7/cygwin, UbuntuLinux, FreeBSD 8.0 Release), I found > that the server produces an error when the listening socket (on which > the accpet() is performed) is member of the select() > fd_set. > > On the other platforms the program works without error, just under > FreeBSD I'm getting this "invalid argument" error. > > Comments appreciated (despite comments about the error checking logic :) > > Here is the code: > // testsrv.c > // gcc -o testsrv testsrv.c > // > > #include > #include > #include > #include > #include > #include > #include > #include > > #include > > #define USEDBUFSIZ 60 > #define MAX_HOSTNAME 256 > #define MAXFDS 256 > #define CLRBUF memset(buf,0,sizeof(buf)) > #define max(a,b) (((a) > (b)) ? (a) : (b)) > static unsigned char buf[256]; > int array_of_fds[MAXFDS]; > static fd_set clientfds; > #define SOCKET int > void *memset(void *, int, size_t); > int enter (int); > int remov (int); > int invalidip (char *); > void exit (int); > int getv (int, unsigned char *, int); > int getfds (); > > int > main(int argc, char **argv) > { > int nfds; > static fd_set readfds; > SOCKET ListenSocket, newsockfd; > struct sockaddr_in cli_addr; > struct sockaddr_in service; > struct hostent *thisHost; > int bOptVal = 0; > int bOptLen = sizeof(int); > char hostname[256]; > char *host_addr; > struct in_addr addr = {0}; > char *ip; > u_short port; > int iResult = 0; > int i , n, m, clilen, dummy, connect = 0; > struct timeval tv; > //--------------------------------------- > //Create a listening socket > ListenSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); > if (ListenSocket == -1) { > perror("socket creation"); > return 1; > } else > printf("ListenSocket=%d\n", ListenSocket); > //--------------------------------------- > //Bind the socket to the local IP address > // and port 3210 > port = 3210; > if (gethostname(hostname, 256)) > perror("gethostname failed\n"), exit(3); > printf("%s\n", hostname), fflush(stdout); > thisHost = gethostbyname(hostname); > ip = inet_ntoa(*(struct in_addr *)(*thisHost->h_addr_list)); > > > if (argc == 2) { > host_addr = argv[1]; > service.sin_addr.s_addr = inet_addr(host_addr); > thisHost = gethostbyaddr((const char *)&service.sin_addr.s_addr, > sizeof(service.sin_addr.s_addr), > AF_INET); > if (thisHost == 0) > printf("host unknown\n"), exit(3); > if (invalidip(host_addr)) > printf("invalid IP\n"), exit(4); > } else { > service.sin_addr.s_addr = inet_addr(ip); > } > service.sin_port = htons(port); > service.sin_family = AF_INET; > > iResult = bind(ListenSocket, (struct sockaddr *)&service, > sizeof(service)); > if (iResult == -1) { > perror("bind"); > shutdown(ListenSocket, SHUT_RDWR); > return 1; > } > listen(ListenSocket, SOMAXCONN); > printf("SOMAXCONN=%d %d\n", SOMAXCONN, FD_SETSIZE); > /* all sockets are put into an own array_of_fs */ > /* in the while() loop below the FD_SET id used by looping through > the */ > /* array_of_fds to fill the readfds array in the select() */ > > enter(ListenSocket); > > /* > * Wait for connect > */ > tv.tv_sec = 0; > tv.tv_usec = 5000000; /* 5 seconds */ A friendly soul on FreeBSD-hackers told me that my tv_usec value is wrong in the timeval struct above. FreeBSD checks if it is in the range of 0