From: Drizzt on 3 May 2010 10:05 Hi all. After a few tries, my co-workers are still fighting with the problems with setsockopt, SO_RCVBUF and SO_SNDBUF, and the migration from a server with Solaris 9 to a new server with Solaris 10. Long story made short: Process A open a listening socket and set both buffers to 700.000 setsockopt gives no err, and subsequent calls to getsockopt gives 700.000 for both buffers. Then, process B opens a client connection to the above listening socket. Again, bot buffer set to 700.000, both setsockopt calls return no error, subsequent getsockopt report 700.000 The funny part: Netstat gives, for the above situation, a connection from A to B with both buffer set to ABOUT 700.000 and a connection from B to A with buffer size of ABOUT 700.000 for A's RCVBUF and about 43.967 for the SNDBUF of B. The command they use is: netstat -f inet | grep -i 9000 The result is: localhost.50579 localhost.9000 43967 0 711660 0 ESTABLISHED localhost.9000 localhost.50579 711648 0 703480 0 ESTABLISHED And, even if we decide to not trust Netstat, what happens is that A can write to B without problems, but after a few write to the socket from B application, B hangs on the write function call. What make everything really, really weird...are two even more funny things: - If we kill the B process, netstat immediately show SNDBUF of the connection from B to A changing to 700.000 - The problem do not happens on the old server on a specific port (8010), but fail on the others they tried. On the new server, it fails even on the 8010 port. It's a really strange behaviour, and not being a Unix C programmer sound even more strange to me :-D Following, is the code for the A process (the one the open the listening end): // Create socket sock = socket (AF_INET, SOCK_STREAM, 0); opt = 1; ret = setsockopt(sock, SOL_SOCKET, SO_REUSEADDR,&opt,sizeof(opt)); memset(&address, 0x0, sizeof(address)); address.sin_family = AF_INET; address.sin_addr.s_addr = htonl(INADDR_ANY); address.sin_port = htons(9000); ret = bind(sock, (const struct sockaddr*)&address, sizeof(address)); // Set receive buffer bufsize = 700000; ret = setsockopt(sock, SOL_SOCKET, SO_RCVBUF, &bufsize, sizeof(bufsize)); // Set send buffer bufsize = 700000; ret = setsockopt(sock, SOL_SOCKET, SO_SNDBUF, &bufsize, sizeof(bufsize)); // Enable keep alive opt = 1; ret = setsockopt(sock, SOL_SOCKET, SO_KEEPALIVE, &opt, sizeof(opt)); // Delete enqued out of bound messages ret = setsockopt(sock, SOL_SOCKET, SO_OOBINLINE, 0, 0); // Listen for connection ret = listen(sock, 10); -------------------------------------------------- And, this is the code for the client side: /* ** Init socket */ if ((nFdSocket = socket (AF_INET, SOCK_STREAM, 0)) < 0) return 0; nOpt = 1; /* ** Set i/o buffer's size */ nDimSockBuf = 700000; err = setsockopt(nFdSocket, SOL_SOCKET, SO_RCVBUF, &nDimSockBuf, sizeof(nDimSockBuf)); if(err < 0 ) { printf("QSOCKET> Invalid RCVBUF\n"); return 0; } nDimSockBuf = 700000; err = setsockopt(nFdSocket, SOL_SOCKET, SO_SNDBUF, &nDimSockBuf, sizeof(nDimSockBuf)); if(err < 0 ) { printf("QSOCKET> Invalid SNDBUF\n"); return 0; } err = setsockopt(nFdSocket, SOL_SOCKET, SO_REUSEADDR, &nOpt, sizeof(nOpt)); if(err < 0 ) { printf ("QSOCKET> Invalid REUSEADDR\n"); return 0; } nOpt = 1; if (setsockopt(nFdSocket,IPPROTO_TCP,TCP_NODELAY,&nOpt,sizeof(nOpt)) <0) return 0; memset (&name, 0, sizeof (name)); name.sin_family = AF_INET; name.sin_port = htons(9000); memcpy(&name.sin_addr, host.h_addr_list[0], host.h_length); if (connect(nFdSocket,(const struct sockaddr*)&name,sizeof(struct sockaddr_in)) < 0) { close(nFdSocket); nFdSocket = 0; return 0; } -------------------------------------------------- Please...what the hell may it be??? Sun says that everything is ok. The sysadm says that both the servers (the new one and the old one) are configured exactly the same. My co- worker are going mad, and we risk to lose the customer. Currently they have implemented a simple internal buffer, and it seems to work, but we feel not much ok with a server that behave that way... Thanks all, eventually :-)
|
Pages: 1 Prev: External DVD-writer Next: Importing zpool from another system |