linux手册翻译——socket(7)

\color{#A00000}{NAME}
socket - Linux 套接字接口

\color{#A00000}{SYNOPSIS}

#include <sys/socket.h>
sockfd = socket(int socket_family, int socket_type, int protocol);

\color{#A00000}{DESCRIPTION}
本手册页描述了 Linux 网络套接字层用户接口。 套接字是用户进程和内核中网络协议栈之间的统一接口。 协议模块分为协议族(protocol families)(如 AF_INET、AF_IPX 和 AF_PACKET)和套接字类型(socket types)(如 SOCK_STREAM 或 SOCK_DGRAM)。 有关families和types的更多信息,请参阅 socket(2)

Socket-layer functions

用户进程使用这些函数来发送或接收数据包以及执行其他套接字操作。 有关更多信息,请参阅它们各自的手册页。

socket(2) 创建套接字,connect(2) 将套接字连接到远程套接字地址,bind(2) 函数将套接字绑定到本地套接字地址,listen(2) 告诉套接字应接受新连接, accept(2) 用于获取具有新传入连接的新套接字。 socketpair(2) 返回两个连接的匿名套接字(仅为少数本地families如 AF_UNIX 实现)

send(2)、sendto(2) 和sendmsg(2) 通过套接字发送数据,而recv(2)、recvfrom(2)、recvmsg(2) 从套接字接收数据。 poll(2) 和 select(2) 等待数据到达或准备好发送数据。 此外,还可以使用 write(2)、writev(2)、sendfile(2)、read(2) 和 readv(2) 等标准 I/O 操作来读取和写入数据。

getsockname(2) 返回本地套接字地址, getpeername(2) 返回远程套接字地址。 getsockopt(2) 和 setsockopt(2) 用于设置或获取套接字层或协议选项。 ioctl(2) 可用于设置或读取一些其他选项。

close(2) 用于关闭套接字。 shutdown(2) 关闭全双工套接字连接的一部分。

套接字不支持使用非零位置查找或调用 pread(2) 或 pwrite(2)。

通过使用 fcntl(2) 在套接字文件描述符上设置 O_NONBLOCK 标志,可以在套接字上执行非阻塞 I/O。 然后所有会阻塞的操作(通常)将返回 EAGAIN(操作应稍后重试); connect(2) 将返回 EINPROGRESS 错误。 然后用户可以通过 poll(2) 或 select(2) 等待各种事件。

I/O Event
Event Poll flag Occurrence
Event Poll flag Occurrence
Read POLLIN New data arrived.
Read POLLIN A connection setup has been completed (for connection-oriented sockets)
Read POLLHUP A disconnection request has been initiated by the other end.
Read POLLHUP A connection is broken (only for connection-oriented protocols). When the socket is written SIGPIPE is also sent.
Write POLLOUT Socket has enough send buffer space for writing new data.
Read/Write POLLIN |POLLOUT An outgoing connect(2) finished.
Read/Write POLLERR An asynchronous error occurred.
Read/Write POLLHUP The other end has shut down one direction.
Exception POLLPRI Urgent data arrived. SIGURG is sent then

如果不使用poll(2) 和 select(2) ,还让内核通过 SIGIO 信号通知应用程序有关事件的信息。 为此,必须通过 fcntl(2) 在套接字文件描述符上设置 O_ASYNC 标志,并且必须通过 sigaction(2) 安装有效的 SIGIO 信号处理程序。 请参阅下面的信号讨论。

Socket address structures

每个套接字域(families)都有自己的套接字地址格式,具有特定于域的地址结构。 这些结构的首字段都是整数类型的“家族”字段(类型为 sa_family_t),即指出自己的套接字域或者说是protocol families。 这允许对所有套接字域可以使用统一的系统调用(例如,connect(2)、bind(2)、accept(2)、getsockname(2)、getpeername(2)),并通过套接字地址来确定特定的域。

为了允许将任何类型的套接字地址传递给套接字 API 中的接口,定义了类型 struct sockaddr。 这种类型的目的纯粹是为了允许将特定于域的套接字地址类型转换为“通用”类型,以避免编译器在调用套接字 API 时发出有关类型不匹配的警告。
struct sockaddr 以及在AF_INET常用的地址结构struct sockaddr_in如下所示,sockaddr_in.sin_zero是占位符:

struct sockaddr
  {
    sa_family_t sa_family;          /* Common data: address family and length.  */
    char sa_data[14];       /* Address data.  */
  };

/* Structure describing an Internet socket address.  */
struct sockaddr_in
  {
    sa_family_t sin_family;
    in_port_t sin_port;         /* Port number.  */
    struct in_addr sin_addr;        /* Internet address.  */

    /* Pad to size of `struct sockaddr'.  */
    unsigned char sin_zero[sizeof (struct sockaddr)
               - __SOCKADDR_COMMON_SIZE
               - sizeof (in_port_t)
               - sizeof (struct in_addr)];
  };

/* Ditto, for IPv6.  */
struct sockaddr_in6
  {
    sa_family_t sin6_family;
    in_port_t sin6_port;    /* Transport layer port # */
    uint32_t sin6_flowinfo; /* IPv6 flow information */
    struct in6_addr sin6_addr;  /* IPv6 address */
    uint32_t sin6_scope_id; /* IPv6 scope-id */
  };

/* Structure describing the address of an AF_LOCAL (aka AF_UNIX) socket.  */
struct sockaddr_un
  {
    sa_family_t sun_family;
    char sun_path[108];     /* Path name.  */
  };

此外,套接字 API 提供了数据类型 struct sockaddr_storage。 这种类型适合容纳所有支持的特定于域的套接字地址结构; 它足够大并且正确对齐。 (特别是它足够大,可以容纳 IPv6 套接字地址。)同struct sockaddr一样,该结构体包括以下字段,可用于标识实际存储在结构体中的套接字地址的类型:sa_family_t ss_family;
sockaddr_storage 结构在必须以通用方式处理套接字地址的程序中很有用(例如,必须同时处理 IPv4 和 IPv6 套接字地址的程序)。

Socket options

下面列出的套接字选项可以使用setsockopt(2) 设置并使用getsockopt(2) 读取。

  • SO_ACCEPTCONN
  • SO_ATTACH_FILTER (Linux 2.2 ), SO_ATTACH_BPF (Linux 3.19)
  • SO_ATTACH_REUSEPORT_CBPF, SO_ATTACH_REUSEPORT_EBPF
  • SO_BINDTODEVICE
  • SO_BROADCAST
  • SO_BSDCOMPAT
  • SO_DEBUG
  • SO_DETACH_FILTER (since Linux 2.2), SO_DETACH_BPF (since Linux 3.19)
  • SO_DOMAIN
  • SO_ERROR
  • SO_DONTROUTE
  • SO_INCOMING_CPU
  • SO_INCOMING_NAPI_ID
  • SO_KEEPALIVE
  • SO_LINGER
  • SO_LOCK_FILTER
  • SO_MARK
  • SO_OOBINLINE
  • SO_PASSCRED
  • SO_PASSSEC
  • SO_PEEK_OFF
  • SO_PEERCRED
  • SO_PEERSEC
  • SO_PRIORITY
  • SO_PROTOCOL
  • SO_RCVBUF
  • SO_RCVBUFFORCE
  • SO_RCVLOWAT and SO_SNDLOWAT
  • SO_REUSEADDR
  • SO_REUSEPORT
    参考SO_REUSEADDR和SO_REUSEPORT作用
  • SO_RXQ_OVFL
  • SO_SELECT_ERR_QUEUE
  • SO_SNDBUF
  • SO_SNDBUFFORCE
  • SO_TIMESTAMP
  • SO_TIMESTAMPNS
  • SO_TYPE
  • SO_BUSY_POLL
Signals

当写入已关闭(由本地或远程端)的面向连接的套接字时,SIGPIPE 被发送到写入进程并返回 EPIPE。 当写调用指定 MSG_NOSIGNAL 标志时,不发送信号。

当使用 FIOSETOWN fcntl(2) 或 SIOCSPGRP ioctl(2) 请求时,会在 I/O 事件发生时发送 SIGIO。 可以在信号处理程序中使用 poll(2) 或 select(2) 来找出事件发生在哪个套接字上。 另一种方法(在 Linux 2.2 中)是使用 F_SETSIG fcntl(2) 设置实时信号; 实时信号的处理程序将使用其 siginfo_t 的 si_fd 字段中的文件描述符调用。 有关更多信息,请参阅 fcntl(2)。

在某些情况下(例如,多个进程访问单个套接字),当进程对信号做出反应时,导致 SIGIO 的条件可能已经消失。 如果发生这种情况,进程应该再次等待,因为 Linux 稍后会重新发送信号。

/proc interfaces

核心套接字网络参数可以通过目录 /proc/sys/net/core/ 中的文件访问。

  • rmem_default 套接字接收缓冲区的默认设置(以字节为单位)。
  • rmem_max 用户可以使用 SO_RCVBUF 套接字选项设置的最大套接字接收缓冲区大小(以字节为单位)。
  • wmem_default 套接字发送缓冲区的默认设置(以字节为单位)。
  • wmem_max 用户可以使用 SO_SNDBUF 套接字选项设置的最大套接字发送缓冲区大小(以字节为单位)
  • message_cost and message_cost configure the token bucket filter used to load limit warning messages caused by external network events.
  • netdev_max_backlog 全局输入队列中的最大数据包数。
  • optmem_max Maximum length of ancillary data and user control data like the iovecs per socket.
Ioctls

These operations can be accessed using ioctl(2):

error = ioctl(ip_socket, ioctl_type, &value_result);

  • SIOCGSTAMP
    Return a struct timeval with the receive timestamp of the last packet passed to the user. This is useful for accurate round trip time measurements. See setitimer(2) for a description of struct timeval. This ioctl should be used only if the socket options SO_TIMESTAMP and SO_TIMESTAMPNS are not set on the socket. Otherwise, it returns the timestamp of the last packet that was received while SO_TIMESTAMP and SO_TIMESTAMPNS were not set, or it fails if no such packet has been received, (i.e., ioctl(2) returns -1 with errno set to ENOENT).
  • SIOCSPGRP
    Set the process or process group that is to receive SIGIO or SIGURG signals when I/O becomes possible or urgent data is available. The argument is a pointer to a pid_t. For further details, see the description of F_SETOWN in fcntl(2).
  • FIOASYNC
    Change the O_ASYNC flag to enable or disable asynchronous I/O mode of the socket. Asynchronous I/O mode means that the SIGIO signal or the signal set with F_SETSIG is raised when a new I/O event occurs.
    Argument is an integer boolean flag. (This operation is synonymous with the use of fcntl(2) to set the O_ASYNC flag.)
  • SIOCGPGRP
    Get the current process or process group that receives SIGIO or SIGURG signals, or 0 when none is set.

Valid fcntl(2) operations:

  • FIOGETOWN
    The same as the SIOCGPGRP ioctl(2).
  • FIOSETOWN
    The same as the SIOCSPGRP ioctl(2).
    \color{#A00000}{VERSIONS}
    SO_BINDTODEVICE 是在 Linux 2.0.30 中引入的。 SO_PASSCRED 是 Linux 2.2 中的新功能。 /proc 接口是在 Linux 2.2 中引入的。 从 Linux 2.3.41 开始支持 SO_RCVTIMEO 和 SO_SNDTIMEO。 早些时候,超时被固定为特定于协议的设置,并且无法读取或写入。

\color{#A00000}{NOTES}
Linux assumes that half of the send/receive buffer is used for internal kernel structures; thus the values in the corresponding /proc files are twice what can be observed on the wire. Linux will allow port reuse only with the SO_REUSEADDR option when this option was set both in the previous program that performed a bind(2) to the port and in the program that wants to reuse the port. This differs from some implementations (e.g., FreeBSD) where only the later program needs to set the SO_REUSEADDR option. Typically this difference is invisible, since, for example, a server program is designed to always set this option.

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 158,560评论 4 361
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,104评论 1 291
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,297评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 43,869评论 0 204
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,275评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,563评论 1 216
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,833评论 2 312
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,543评论 0 197
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,245评论 1 241
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,512评论 2 244
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,011评论 1 258
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,359评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,006评论 3 235
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,062评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,825评论 0 194
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,590评论 2 273
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,501评论 2 268

推荐阅读更多精彩内容