David Collier-Brown wrote:> I've been in discussion with a colleague who had to reduce (!)
> SO_SNDBUF to get decent performance
The program needed some #ifdef's for Linux (thanks, tridge!)
so here's a re-write and a Linux result from 2.2.12:
Default SO_BROADCAST, broadcast allowed = 0
Default SO_REUSEADDR, address recycling = 0
Default SO_KEEPALIVE, send keepalive packets = 0
Default SO_OOBINLINE, oob data folded inline = 0
Default SO_SNDBUF, send buffer size = 65535
Default SO_RCVLOWAT, receive low-water mark = 1
Default SO_SNDLOWAT, send low-water mark = 1
Default SO_RCVTIMEO, receive timeout = 0
Default SO_SNDTIMEO, send timeout = 0
Default SO_RCVBUF, receive buffer size = 65535
Default SO_ERROR, error status = 0
Default SO_TYPE, socket type = 1
Default TCP_MAXSEG, maximum segment size (mss) = 0
Default TCP_NODELAY, send even tiny packets = 0
--dave
-------------- next part --------------
/*
* getsocketopts -- get the defaults
*
* This (on a Solaris 7 system) should say:
* % su root -c ./getsockopts
* Default SO_ACCEPTCON: accepting connections = 0
* Default SO_BROADCAST, broadcast allowed = 0
* Default SO_REUSEADDR, address recycling = 0
* Default SO_KEEPALIVE, send keepalive packets = 0
* Default SO_OOBINLINE, oob data folded inline = 0
* Default SO_SNDBUF, send buffer size = 8192
* getsocketopts: could not test SO_RCVLOWAT, receive low-water mark
* getsocketopts: could not test SO_SNDLOWAT, send low-water mark
* getsocketopts: could not test SO_RCVTIMEO, receive timeout
* getsocketopts: could not test SO_SNDTIMEO, send timeout
* Default SO_RCVBUF, receive buffer size = 32768
* Default SO_ERROR, error status = 0
* Default SO_TYPE, socket type = 2
* Default TCP_MAXSEG, maximum segment size (mss) = 536
* Default TCP_NODELAY, send even tiny packets = 0
*/
#include <stdio.h>
#include <stdlib.h> /* For defn' of exit(). */
#include <sys/types.h> /* for getuid() */
#include <unistd.h>
#include <sys/socket.h> /* For socket() */
#include <netinet/in.h> /* For protocol numbers. */
#include <netinet/tcp.h> /* For options. */
typedef struct option_t {
int name;
char *printable;
} OPTION;
void query(int, int, OPTION *);
OPTION so_option[] = {
#ifdef SO_ACCEPTCONN
{ SO_ACCEPTCONN, "SO_ACCEPTCON: accepting connections" },
#endif
#ifdef SO_BROADCAST
{ SO_BROADCAST, "SO_BROADCAST, broadcast allowed" },
#endif
#ifdef SO_REUSEADDR
{ SO_REUSEADDR, "SO_REUSEADDR, address recycling" },
#endif
#ifdef SO_KEEPALIVE
{ SO_KEEPALIVE, "SO_KEEPALIVE, send keepalive packets" },
#endif
/* { SO_LINGER, "SO_LINGER, lingers on close"}, */
#ifdef SO_OOBINLINE
{ SO_OOBINLINE, "SO_OOBINLINE, oob data folded inline"},
#endif
#ifdef SO_SNDBUF
{ SO_SNDBUF, "SO_SNDBUF, send buffer size" },
#endif
#ifdef SO_RCVLOWAT
{ SO_RCVLOWAT, "SO_RCVLOWAT, receive low-water mark"},
#endif
#ifdef SO_SNDLOWAT
{ SO_SNDLOWAT, "SO_SNDLOWAT, send low-water mark"},
#endif
#ifdef SO_RCVTIMEO
{ SO_RCVTIMEO, "SO_RCVTIMEO, receive timeout"},
#endif
#ifdef SO_SNDTIMEO
{ SO_SNDTIMEO, "SO_SNDTIMEO, send timeout"},
#endif
#ifdef SO_RCVBUF
{ SO_RCVBUF, "SO_RCVBUF, receive buffer size"},
#endif
#ifdef SO_ERROR
{ SO_ERROR, "SO_ERROR, error status"},
#endif
#ifdef SO_TYPE
{ SO_TYPE, "SO_TYPE, socket type"},
#endif
{ 0, NULL }
};
OPTION tcp_option[] = {
#ifdef TCP_MAXSEG
{ TCP_MAXSEG, "TCP_MAXSEG, maximum segment size (mss)"},
#endif
#ifdef TCP_NODELAY
{ TCP_NODELAY, "TCP_NODELAY, send even tiny packets"},
#endif
{ 0, NULL}
};
main() {
int s;
if ((getuid()) != 0) {
(void) fprintf(stderr,"getsocketopts: you must be root first.\n");
(void) exit(1);
}
if ((s = socket(AF_INET,SOCK_STREAM,IPPROTO_TCP)) == -1) {
perror("failed in socket call,");
(void) exit(1);
}
query(s, SOL_SOCKET, so_option);
query(s, IPPROTO_TCP, tcp_option);
(void) close(s);
(void) exit(0);
/*NOTREACHED*/
}
/*
* query -- see about one option
*/
void
query(int s, int type, OPTION *p) {
int value, vlen = 4;
for (; p->printable != NULL; p++) {
if (getsockopt(s, type, p->name, (void *)&value, &vlen) == -1) {
(void) fprintf(stderr,"getsocketopts: could not test %s\n",
p->printable);
}
else {
(void) printf("Default %s = %d\n",p->printable,value);
}
}
}