您的位置:首页 > 运维架构

Socket Configuration Options

2012-06-21 13:45 127 查看
Socket Configuration Options:

Socket options:

One can "get" (read) the current socket options or "set" them to new values. The default values are obtained from the OS:

LevelOptionTypeDefaultDescription
IPPROTO_IPTCP_NODELAYint0Don't delay send to coalesce packets. If set, disable the Nagle algorithm. When not set, data is buffered until there is a sufficient amount to send out, thereby avoiding the frequent sending of
small packets, which results in poor utilization of the network. Don't use with TCP_CORK. This option is overridden by TCP_CORK
IPPROTO_IPTCP_MAXSEGint536Maximum segment size for outgoing TCP packets. TCP will impose its minimum and maximum bounds over the value provided.
IPPROTO_IPTCP_CORKint0Control sending of partial frames. If set, don't send out partial frames. Not cross platform.
IPPROTO_IPTCP_KEEPIDLEint7200When the SO_KEEPALIVE option is enabled, TCP probes a connection that has been idle for some amount of time. The default value for this idle period is 2 hours. The TCP_KEEPIDLE option can be used
to affect this value for a given socket, and specifies the number of seconds of idle time between keepalive probes.

Not cross platform. This option takes an int value, with a range of 1 to 32767.
IPPROTO_IPTCP_KEEPINTVLint75Specifies the interval between packets that are sent to validate the connection.

Not cross platform.
IPPROTO_IPTCP_KEEPCNTint9When the SO_KEEPALIVE option is enabled, TCP probes a connection that has been idle for some amount of time. If the remote system does not respond to a keepalive probe, TCP retransmits the probe
a certain number of times before a connection is considered to be broken. The TCP_KEEPCNT option can be used to affect this value for a given socket, and specifies the maximum number of keepalive probes to be sent. This option takes an int value, with a range
of 1 to 32767. Not cross platform.
IPPROTO_IPTCP_SYNCNTint5Number of SYN retransmits that TCP should send before aborting the attempt to connect. It cannot exceed 255.
IPPROTO_IPTCP_LINGER2int60Life time of orphaned FIN-WAIT-2 state. Not to be confused with option SO_LINGER

Not cross platform.
SOL_SOCKETSO_REUSEADDRint

(bool)
0Allow local address reuse. If a problem is encountered when attempting to bind to a port which has been closed but not released (may take up to 2 minutes as defined by TIME_WAIT). Apply the SO_REUSEADDR
socket option to release the resource immediately and to get around the TIME_WAIT state.

0 = disables, 1 = enables
SOL_SOCKETSO_REUSEPORTint

(bool)
0This option is AF_INET socket-specific. This option allows multiple processes to share a port. All incoming multicast or broadcast UDP datagrams that are destined for the port are delivered to
all sockets that are bound to the port. All processes that share the port must specify this option.

0 = disables, 1 = enables
SOL_SOCKETSO_ERRORint

(bool)
0When an error occurs on a socket, set error variable so_error and notify process

0 = disables, 1 = enables
SOL_SOCKETSO_BROADCASTint

(bool)
0Permit sending of broadcast datagrams

0 = disables, 1 = enables
SOL_SOCKETSO_SNDBUFint

(value)
16384Send buffer size
SOL_SOCKETSO_RCVBUFint

(value)
87380Receive buffer size
SOL_SOCKETSO_KEEPALIVEint

(bool)
0Periodically test if connection is alive

0 = disables, 1 = enables
SOL_SOCKETSO_SNDTIMEOtimeval

(struct)
0

0
Set timeout period for socket send.

Disable by setting timeval.tv_sec = 0 sec, timeval.tv_usec = 0 usec (default)

Affects write() writev() send() sendto() and sendmsg()
SOL_SOCKETSO_RCVTIMEOtimeval

(struct)
0

0
Set timeout period for socket receive.

Disable by setting timeval.tv_sec = 0 sec, timeval.tv_usec = 0 usec (default)

Affects read() readv() recv() recvfrom() and recvmsg()
SOL_SOCKETSO_LINGERlinger

(struct)
0

0
Specifies how close function will operate for connection protocols (TCP)

l_onoff: 0 = disables, 1 = enables

l_linger: 0 = unsent data discarded, 1 = close() does not return untill all unsent data is transmitted or remote connection is closed

Structure defined in sys/socket.h
SOL_SOCKETSO_RCVLOWATint

(value)
1Specifies number of bytes used as a threshold by select() to consider a socket read ready
SOL_SOCKETSO_SNDLOWATint

(value)
1Specifies number of bytes used as a threshold by select() to consider a socket write ready
SOL_SOCKETSO_TYPEint

(value)
undefinedSpecifies socket type (e.g., tcp (SOCK_STREAM), udp (SOCK_DGRAM), etc.)

For use with getsockopt() only.
IPPROTO_IP macro defines are found in /usr/include/netinet/tcp.h

SOL_SOCKET macro defines require /usr/include/sys/socket.h
For a full list of options see the TCP man page

For a full list of IP options see the IP(7) man page

Function Prototypes:
int getsockopt(int s, int level, int optname, void *optval, socklen_t *optlen);

int setsockopt(int s, int level, int optname, const void *optval, socklen_t optlen);

getsockopt/setsockopt arguments:

int sockfd: Socket file descriptor. Returned by call to "socket".
int level: See table above
int optname: See table above
void *optval: Pointer to value or data structure
optlen: Length of "optval"
Returns 0: Sucess, -1: Failure and errno may be set.

Code to read socket options:
File: printSocketOptions.c
01
#include
<sys/socket.h>
02
#include
<netinet/in.h>
03
#include
<netinet/tcp.h>
04
#include
<errno.h>
05
#include
<stdio.h>
06
07
int
main()
08
{
09
int
socketHandle;
10
11
//
create socket
12
13
if
((socketHandle
= socket(AF_INET, SOCK_STREAM, IPPROTO_IP)) < 0)
14
{
15
close(socketHandle);
16
perror
(
"socket"
);
17
}
18
19
 
int
iSocketOption
= 0;
20
 
int
iSocketOptionLen
=
sizeof
(
int
);;
21
22
 
struct
linger
SocketOptionLinger;
23
 
int
iSocketOptionLingerLen
=
sizeof
(
struct
linger);;
24
25
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_NODELAY, (
char
*)&iSocketOption,
&iSocketOptionLen);
26
 
printf
(
"Socket
TCP_NODELAY = %d\n"
,
iSocketOption);
27
28
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_MAXSEG, (
char
*)&iSocketOption,
&iSocketOptionLen);
29
 
printf
(
"Socket
TCP_MAXSEG = %d\n"
,
iSocketOption);
30
31
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_CORK, (
char
*)&iSocketOption,
&iSocketOptionLen);
32
 
printf
(
"Socket
TCP_CORK = %d\n"
,
iSocketOption);
33
34
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_KEEPIDLE, (
char
*)&iSocketOption,
&iSocketOptionLen);
35
 
printf
(
"Socket
TCP_KEEPIDLE = %d\n"
,
iSocketOption);
36
37
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_KEEPINTVL, (
char
*)&iSocketOption,
&iSocketOptionLen);
38
 
printf
(
"Socket
TCP_KEEPINTVL = %d\n"
,
iSocketOption);
39
40
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_KEEPCNT, (
char
*)&iSocketOption,
&iSocketOptionLen);
41
 
printf
(
"Socket
TCP_KEEPCNT = %d\n"
,
iSocketOption);
42
43
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_SYNCNT, (
char
*)&iSocketOption,
&iSocketOptionLen);
44
 
printf
(
"Socket
TCP_SYNCNT = %d\n"
,
iSocketOption);
45
46
 
getsockopt(socketHandle,
IPPROTO_TCP, TCP_LINGER2, (
char
*)&iSocketOption,
&iSocketOptionLen);
47
 
printf
(
"Socket
TCP_LINGER2 = %d\n"
,
iSocketOption);
48
49
 
getsockopt(socketHandle,
SOL_SOCKET, SO_REUSEADDR, (
char
*)&iSocketOption,
&iSocketOptionLen);
50
 
printf
(
"Socket
SO_REUSEADDR = %d\n"
,
iSocketOption);
51
52
 
getsockopt(socketHandle,
SOL_SOCKET, SO_ERROR, (
char
*)&iSocketOption,
&iSocketOptionLen);
53
 
printf
(
"Socket
SO_ERROR = %d\n"
,
iSocketOption);
54
55
 
getsockopt(socketHandle,
SOL_SOCKET, SO_BROADCAST, (
char
*)&iSocketOption,
&iSocketOptionLen);
56
 
printf
(
"Socket
SO_BROADCAST = %d\n"
,
iSocketOption);
57
58
 
getsockopt(socketHandle,
SOL_SOCKET, SO_KEEPALIVE, (
char
*)&iSocketOption,
&iSocketOptionLen);
59
 
printf
(
"Socket
SO_KEEPALIVE = %d\n"
,
iSocketOption);
60
61
 
getsockopt(socketHandle,
SOL_SOCKET, SO_SNDBUF, (
char
*)&iSocketOption,
&iSocketOptionLen);
62
 
printf
(
"Socket
SO_SNDBUF = %d\n"
,
iSocketOption);
63
64
 
getsockopt(socketHandle,
SOL_SOCKET, SO_RCVBUF, (
char
*)&iSocketOption,
&iSocketOptionLen);
65
 
printf
(
"Socket
SO_RCVBUF = %d\n"
,
iSocketOption);
66
67
 
getsockopt(socketHandle,
SOL_SOCKET, SO_LINGER, (
char
*)&SocketOptionLinger,
&iSocketOptionLingerLen);
68
 
printf
(
"Socket
SO_LINGER = %d  time = %d\n"
,
SocketOptionLinger.l_onoff, SocketOptionLinger.l_linger);
69
70
 
getsockopt(socketHandle,
SOL_SOCKET, SO_RCVLOWAT, (
char
*)&iSocketOption,
&iSocketOptionLen);
71
 
printf
(
"Socket
SO_RCVLOWAT = %d\n"
,
iSocketOption);
72
}
Compile: gcc -o printSocketOptions printSocketOptions.c
getsockopt man page: get a particular socket option for the specified socket.

Set socket options:

Socket "keep-alive":
1
int
iOption
= 1;
//
Turn on keep-alive, 0 = disables, 1 = enables
2
3
if
(setsockopt(socketHandle,
SOL_SOCKET, SO_KEEPALIVE, (
const
char
*)
&iOption,
sizeof
(
int
))
== SOCKET_ERROR)
4
{
5
 
cerr
<<
"Set
keepalive: Keepalive option failed"
<<
endl;
6
}

Set socket client options:

Socket re-use:
1
int
iOption
= 0;
//
Reuse address option to set, 0 = disables, 1 = enables
2
3
if
(setsockopt(socketHandle,
SOL_SOCKET, SO_REUSEADDR, (
const
char
*)
&iOption,
sizeof
(
int
))
== SOCKET_ERROR)
4
{
5
 
cerr
<<
"Set
reuse address: Client set reuse address option failed"
<<
endl;
6
}
When a socket connection is closed with a call to close(), shutdown() or exit(), both the client and server will send a FIN (final) packet and will then send an acknowledgment (ACK) that they received the packet. The side which initiates the
closure will be in a TIME_WAIT state until the process has been completed. This time out period is generally 2-4 minutes in duration. It is hoped that all packets are received in a timely manner and the entire time out duration is not required. When
an application is abnormally terminated, the TIME_WAIT period is entered for the full duration.
Setting the SO_REUSEADDR option explicitly allows a process to bind a port in the TIME_WAIT state. This is to avoid the error "bind: Address Already in Use". One caviat is that the process can not be to the same address and port
as the previous connection. If it is, the SO_REUSEADDR option will not help and the duration of the TIME_WAIT will be in effect.

For more info see How to avoid the "Address Already in Use" error.

Solution: Enable socket linger:
1
linger
Option;
2
Option.l_onoff
= 1;
3
Option.l_linger
= 0;
4
5
if
(setsockopt(socketHandle,
SOL_SOCKET, SO_LINGER, (
const
char
*)
&Option,
sizeof
(linger))
== -1)
6
{
7
 
cerr
<<
"Set
SO_LINGER option failed"
<<
endl;
8
}
This allows the socket to die quickly and allow the address to be reused again. Warning: This linger configuration specified may/will result in data loss upon socket termination, thus it would not have the robustness required for a banking transaction but would
be ok for a recreational app.

Broadcast:
view
source

print?

1
int
iOption
= 0;
//
Broadcast option to set, 0 = disables, 1 = enables
2
3
if
(setsockopt(socketHandle,
SOL_SOCKET, SO_BROADCAST, (
const
char
*)
&iOption,
sizeof
(
int
))
== SOCKET_ERROR)
4
{
5
 
cerr
<<
"Set
reuse address: Client set reuse address option failed"
<<
endl;
6
}
Struct: remoteSocketInfo.sin_addr.s_addr = htonl(INADDR_BROADCAST);

setsockopt man
page: set a particular socket option for the specified socket.

more info, pls see:http://www.yolinux.com/TUTORIALS/Sockets.html#OPTIONS
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐