你需要了解的一些系统调用:
socket()
bind()
connect()
listen()
accept()
send()
recv()
sendto()
recvfrom()
close()
shutdown()
setsockopt()
getsockopt()
getpeername()
getsockname()
gethostbyname()
gethostbyaddr()
getprotobyname()
fcntl()
我们将在以下详细介绍这些系统调用。
1.  socket()函数
#include <sys/types.h>
#include <sys/socket.h>
int socket(int domain , int type , int protocol);
首先,domain 需要被设置为 “AF_INET”,就像上面的struct sockaddr_in。然后,type参数告诉内核这个socket 是什么类型,“SOCK_STREAM”或是“SOCK_DGRAM”。最后,只需要把protocol 设置为0 。
socket()函数只是简单的返回一个你以后可以使用的套接字描述符。如果发生错误,socket()函数返回 –1 。全局变量errno 将被设置为错误代码。(可以参考perror() 的manpages)
2.  bind(int sockfd,const struct sockaddr *myaddr,socklen_t addrlen)
bind()的系统调用声明如下:
#include <sys/types.h>
#include <sys/socket.h>
int bind (int sockfd , struct sockaddr *my_addr , int addrlen) ;
参数说明:
l sockfd 是由socket()函数返回的套接字描述符。
l my_addr 是一个指向struct sockaddr 的指针,包含有关你的地址的信息:名称、端口和IP 地址。
l addrlen 可以设置为sizeof(struct sockaddr)。
当bind()函数调用错误的时候,它也是返回–1 作为错误发生的标志。errn 的值为错误代码。
当你调用bind()的时候,不要把端口数设置的过小!小于1024 的所有端口都是保留下来作为系统使用端口的,没有root 权利无法使用。你可以使用1024 以上的任何端口,一直到65535
对socket进行定位
 
相关函数
socket,accept,connect,listen
表头文件
#include<sys/types.h>
#include<sys/socket.h>
定义函数
int bind(int sockfd,struct sockaddr * my_addr,int addrlen);
函数说明
bind()用来设置给参数sockfd的socket一个名称。此名称由参数my_addr指向一sockaddr结构,对于不同的socket domain定义了一个通用的数据结构
struct sockaddr
{
unsigned short int sa_family;
char sa_data[14];
};
sa_family 为调用socket()时的domain参数,即AF_xxxx值。
sa_data 最多使用14个字符长度。
此sockaddr结构会因使用不同的socket domain而有不同结构定义,例如使用AF_INET domain,其socketaddr结构定义便为
struct socketaddr_in
{
unsigned short int sin_family;
uint16_t sin_port;
struct in_addr sin_addr;
unsigned char sin_zero[8];
};
struct in_addr
{
uint32_t s_addr;
};
sin_family 即为sa_family
sin_port 为使用的port编号
sin_addr.s_addr 为IP 地址
sin_zero 未使用。
参数
addrlen为sockaddr的结构长度。
返回值
成功则返回0,失败返回-1,错误原因存于errno中。
错误代码
EBADF 参数sockfd 非合法socket处理代码。
EACCESS 权限不足
ENOTSOCK 参数sockfd为一文件描述词,非socket。
该函数用来指定一个端口号,一个IP地址,两者都指定,或者两者都不指定.可以不使用该函数调用。使用socket()得到套接口后可以直接调用函数conect()或者listen(),这时内核会自动给套接口分配一个地址和端口号(众所周知的端口号),这是常用的方法。只有在进程需要使用特定的网络地址和端口时才会进行绑定,即使用bind()函数。调用bind()的常见错误是EADDRINUSE,即指定的地址正在使用,主要是指定的端口号被使用了,IP地址可以被多个进程使用,但端口在同一时刻只能被一个进程使用。
套接口中port=0表示由内核指定端口号,设定sin_addr为INADDR_ANY(表示任意的意思),就有内核指定端口号。
设置端口为0的语句:
struct socketaddr_in seeveraddr;
serveraddr.port = 0;
设置IP的语句:
serveraddr.sin_addr = htonl(INADDR_ANY);
htonl()说明:
 
   
表头文件
#include<netinet/in.h>
定义函数
unsigned long int htonl(unsigned long int hostlong);
函数说明
htonl()用来将参数指定的32位hostlong 转换成网络字符顺序。
返回值

返回对应的网络字符顺序。

3.  connect() 函数
#include <sys/types.h>
#include <sys/socket.h>
int connect (int sockfd, struct sockaddr *serv_addr, int addrlen);
connect()的三个参数意义如下:
l sockfd :套接字文件描述符,由socket()函数返回的。
l serv_addr 是一个存储远程计算机的IP 地址和端口信息的结构。
l addrlen 应该是sizeof(struct sockaddr)。
4.  listen()函数
#include <sys/socket.h>
int listen(int sockfd, int backlog);
listen()函数的参数意义如下:
l sockfd 是一个套接字描述符,由socket()系统调用获得。
l backlog 是未经过处理的连接请求队列可以容纳的最大数目。
backlog 具体一些是什么意思呢?每一个连入请求都要进入一个连入请求队列,等待listen 的程序调用accept()(accept()函数下面有介绍)函数来接受这个连接。当系统还没有调用accept()函数的时候,如果有很多连接,那么本地能够等待的最大数目就是backlog 的数值。你可以将其设成5 到10 之间的数值(推荐)。像上面的所有函数一样, listen()如果返回 –1 ,那么说明在listen()的执行过程中发生了错误。全局变量errno 中存储了错误代码。
5.  accept()函数
当调用它的时候, 大致过程是下面这样的
l 有人从很远很远的地方尝试调用connect()来连接你的机器上的某个端口(当然是你已经在listen()的)。
l 他的连接将被listen 加入等待队列等待accept()函数的调用(加入等待队列的最多数目由调用listen()函数的第二个参数backlog 来决定)。
l 你调用accept()函数,告诉他你准备连接。
l accept()函数将回返回一个新的套接字描述符,这个描述符就代表了这个连接!
#include <sys/socket.h>
int accept(int sockfd, void *addr, int *addrlen);
accept()函数的参数意义如下:
l sockfd 是正在listen() 的一个套接字描述符。
addr 一般是一个指向struct sockaddr_in 结构的指针;里面存储着远程连接过来的计算机的信息(比如远程计算机的IP 地址和端口)。
l addrlen 是一个本地的整型数值,在它的地址传给accept() 前它的值应该是sizeof(struct sockaddr_in);accept()不会在addr 中存储多余addrlen bytes 大小的数据。如果
accept()函数在addr 中存储的数据量不足addrlen,则accept()函数会改变addrlen 的值来反应这个情况。
6.  send()、recv()函数
#include <sys/types.h>
#include <sys/socket.h>
int send(int sockfd, const void *msg, int len, int flags);
send 的参数含义如下:
l sockfd 是代表你与远程程序连接的套接字描述符。
l msg 是一个指针,指向你想发送的信息的地址。
l len 是你想发送信息的长度。
l flags 发送标记。一般都设为0(你可以查看send 的man pages 来获得其他的参数
值并且明白各个参数所代表的含义)。
send()函数在调用后会返回它真正发送数据的长度
注意:send() 所发送的数据可能少于你给它的参数所指定的长度!因为如果你给send()的参数中包含的数据的长度远远大于send()所能一次发送的数据,则send()函数
只发送它所能发送的最大数据长度,然后它相信你会把剩下的数据再次调用它来进行第二次发送。所以,记住如果send()函数的返回值小于len 的话,则你需要再次发送剩下的数据。幸运的是,如果包足够小(小于1K),那么send()一般都会一次发送光的。像上面的函数一样,send()函数如果发生错误,则返回 –1 ,错误代码存储在全局变量errno 中。
函数recv()调用在许多方面都和send()很相似,下面是recv()函数的声明:
#include <sys/types.h>
#include <sys/socket.h>
int recv(int sockfd, void *buf, int len, unsigned int flags);
recv()的参数含义如下:
l sockfd 是你要读取数据的套接字描述符。
l buf 是一个指针,指向你能存储数据的内存缓存区域。
l len 是缓存区的最大尺寸。
l flags 是recv() 函数的一个标志,一般都为0 (具体的其他数值和含义请参考recv()
的man pages)。
recv() 返回它所真正收到的数据的长度。(也就是存到buf 中数据的长度)。如果返回–1 则代表发生了错误(比如网络以外中断、对方关闭了套接字连接等),全局变量errno 里面存储了错误代码。
7.  close()和shutdown()函数
程序进行网络传输完毕后,你需要关闭这个套接字描述符所表示的连接。实现这个非常简单,只需要使用标准的关闭文件的函数:close()。
使用方法:
close(sockfd);
执行close()之后,套接字将不会在允许进行读操作和写操作。任何有关对套接字描述符进行读和写的操作都会接收到一个错误。
如果你想对网络套接字的关闭进行进一步的操作的话,你可以使用函数shutdown()。
它允许你进行单向的关闭操作,或是全部禁止掉。
shutdown()的声明为:
#include <sys/socket.h>
int shutdown(int sockfd, int how);
它的参数含义如下:
l sockfd 是一个你所想关闭的套接字描述符.
l how 可以取下面的值。0 表示不允许以后数据的接收操;1 表示不允许以后数据的发送操作;2 表示和close()一样,不允许以后的任何操作(包括接收,发送数据)
shutdown() 如果执行成功将返回0,如果在调用过程中发生了错误,它将返回–1,全局变量errno 中存储了错误代码.
如果你在一个未连接的数据报套接字上使用shutdown() 函数(还记得可以对数据报套接字UDP 进行connect()操作吗?),它将什么也不做.
8.  setsockopt() 和getsockopt() 函数
Linux 所提供的socket 库含有一个错误(bug)。此错误表现为你不能为一个套接字重
新启用同一个端口号,即使在你正常关闭该套接字以后。问题就是Linux 内核在一个绑定套接字的进程结束后从不把端口标记为未用。
在Linux 中绕开这个问题的办法是,当套接字已经打开但尚未有连接的时候用
setsockopt()系统调用在其上设定选项(options)。setsockopt() 调用设置选项而getsockopt()
从给定的套接字取得选项。
这里是这些调用的语法:
#include<sys/types.h>
#include<sys/socket.h>
int getsockopt(int sockfd, int level, int name, char *value, int *optlen);
int setsockopt(int sockfd, int level, int name, char *value, int *optlen);

下面是两个调用的参数说明:
l sockfd 必须是一个已打开的套接字。
l level 是函数所使用的协议标准(protocol level)(TCP/IP 协议使用IPPROTO_TCP,
套接字标准的选项实用SOL_SOCKET)。
l name 选项在套接字说明书中(man page)有详细说明。
l value 指向为getsockopt()函数所获取的值,setsockopt()函数所设置的值的地址。
l optlen 指针指向一个整数,该整数包含参数以字节计算的长度。
9. getpeername()函数
这个函数可以取得一个已经连接上的套接字的远程信息(比如IP 地址和端口),告诉你在远程和你连接的究竟是谁.
它的声明为:
#include <sys/socket.h>
int getpeername(int sockfd, struct sockaddr *addr, int *addrlen);
下面是参数说明:
l sockfd 是你想取得远程信息的那个套接字描述符。
l addr 是一个指向struct sockaddr (或是struct sockaddr_in)的指针。
l addrlen 是一个指向int 的指针,应该赋于sizeof(struct sockaddr)的大小。
如果在函数执行过程中出现了错误,函数将返回 –1 ,并且错误代码储存在全局变量
errno 中。
当你拥有了远程连接用户的IP 地址,你就可以使用inet_ntoa() 或gethostbyaddr()来输
出信息或是做进一步的处理。
10. gethostname()函数
gethostname()函数可以取得本地主机的信息.它比getpeername()要容易使用一些。
它返回正在执行它的计算机的名字。返回的这个名字可以被gethostbyname()函数使用,
由此可以得到本地主机的IP 地址。
下面是它的声明:
#include <unistd.h>
int gethostname(char *hostname, size_t size);
参数说明如下:
l hostname 是一个指向字符数组的指针,当函数返回的时候,它里面的数据就是本
地的主机的名字.
l size 是hostname 指向的数组的长度.
函数如果成功执行,它返回0,如果出现错误,则返回–1,全局变量errno 中存储着错
误代码。
11. gethostbyname()函数
#include <netdb.h>
struct hostent *gethostbyname(const char *name);
正如你所看见的,它返回了一个指向struct hostent 的指针.Struct hostent 是这样定义
的:
struct hostent {
char *h_name;
char **h_aliases;
int h_addrtype;
int h_length;
char **h_addr_list;
};
#define h_addr h_addr_list[0]
下面是上面各个域代表含义的解释:
l h_name 是这个主机的正式名称。
l h_aliases 是一个以NULL(空字符)结尾的数组,里面存储了主机的备用名称。
l h_addrtype 是返回地址的类型,一般来说是“AF_INET”。
l h_length 是地址的字节长度。
l h_addr_list 是一个以0 结尾的数组,存储了主机的网络地址。
注意:网络地址是以网络字节顺序存储的。
l h_addr - h_addr_list 数组的第一个成员.
gethostbyname() 返回的指针指向结构struct hostent ,如果发生错误,它将会返回NULL
(但是errno 并不代表错误代码,h_errno 中存储的才识错误代码。参考下面的herror()函数)。
使用gethostbyname()函数,你不能使用perror()来输出错误信息(因为错误代码存储在
h_errno 中而不是errno 中。所以,你需要调用herror()函数。
######################################################################################################################################################################
2. 服务器进程中系统调用的顺序
          socket()————bind()————listen()————accept()
在面向连接的协议的程序中,服务器执行以下函数:
l 调用socket()函数创建一个套接字。
l 调用bind()函数把自己绑定在一个地址上。
l 调用listen()函数侦听连接。
l 调用accept()函数接受所有引入的请求。
l 调用recv()函数获取引入的信息然后调用send()回答
     TCP三次握手协议:
(1)客户端先用connect()向服务器发出一个要求连接的信号SYN1。
(2)服务器进程接收到这个信号后,发回应答信号ack1,同时这也是一个要求回答的信号SYN2。
(3)客户端收到应答信号ack1和SYN2后,再次应答ack2。
(4)服务器收到应答信号ack2,一次连接才算建立完成。
3.使用完一个套接口后,一定要记得将它关掉,使用函数close(int sockfd)
4.Linux系统调用-- getsockname函数详解

当不用bind()或调用bind()没有指定本地协议地址时,可以调用getsockname()来返回内核分配给此连接的本地IP地址和端口号,还可以获得某套接口的协议族。当一个新的连接建立时,服务器也可以调用getsockname()来获得分配给此连接的本地IP地址。
 当一个服务器的子进程调用exec函数启动执行时,只能调用getpeername()函数来获得客户的Ip地址和端口号。

【 getsockname系统调用】   
    
功能描述: 
返回指定套接字的名称。

用法: 
#include <sys/socket.h>

int getsockname(int sockfd, struct sockaddr *name, socklen_t *namelen);

参数:   
sockfd:需要获取名称的套接字。
name:存放所获取套接字名称的缓冲区。
nemalen:作为入口参数,name指向空间的最大长度。作为出口参数,name的实际长度。

返回说明:   
成功执行时,返回0。失败返回-1,errno被设为以下的某个值   
EBADF:sock不是有效的文件描述词
EFAULT:name指向的内存并非有效的进程空间
EINVAL:namelen无效,可能为负值
ENOBUFS:执行操作时,系统资源不足
ENOTCONN:套接字尚未连接上
ENOTSOCK:sock描述的不是套接字

功能:
getsockname: 返回本地协议地址
getpeername:返回远程协议地址
定义:
#include <sys/unistd.h>

int getsockname (int sockfd, struct sockaddr *localaddr, int *addrlen);
int getpeername(int sockfd, struct sockaddr *peeraddr, int *addrlen);

getsockname()函数用于获取一个套接口的名字。它用于一个已捆绑或已连接套接口s,本地地址将被返回。本调用特别适用于如下情况:未调用bind()就调用了connect(),这时唯有getsockname()调用可以获知系统内定的本地地址。在返回时,namelen参数包含了名字的实际字节数。
   若一个套接口与INADDR_ANY捆绑,也就是说该套接口可以用任意主机的地址,此时除非调用connect()或accept()来连接,否则getsockname()将不会返回主机IP地址的任何信息。除非套接口被连接,WINDOWS套接口应用程序不应假设IP地址会从INADDR_ANY变成其他地址。这是因为对于多个主机环境下,除非套接口被连接,否则该套接口所用的IP地址是不可知的。

Open C 套接字: getsockname 方法

getsockname - 获取套接字名称

int getsockname (int s, struct sockaddr * restrict name, socklen_t * restrict namelen);

getsockname系统调用返回指定套接字的当前名称namelen应被初始化指出name所指向的空间容量。返回时,该参数含有返回名称

的实际大小(按字节)。

下面是getsockname函数的用法:

#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
TInt GetSockName()
{
int sock_fd;
struct sockaddr_in addr,ss;
unsigned int len;
sock_fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
addr.sin_family = AF_INET;
addr.sin_addr.s_addr = htonl(INADDR_ANY);
addr.sin_port = htons(5000);
bind(sock_fd,(struct sockaddr*)&addr,sizeof(addr));
len=sizeof(ss);
getsockname(sock_fd,(struct sockaddr*)&ss,&len);
close(sock_fd);
}

***********************************************************************************
LINUX函数查询: http://www.opengroup.org/search/
***********************************************************************************
***********************************************************************************
LINUX下Socket编程笔记:http://blog.chinaunix.net/u/19185/article_56798.html
***********************************************************************************
程序实例:
###################################################################################
//使用方法:定义的服务器的远端端口号是4000,故编译运行该程序后,需要使用以下命令在终端上显示:Hello World!
//在cmd命令行中输入:telnet 远端服务器地址 端口号
//我的实际运行 telnet 192.168.12.94 4000?
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/wait.h>
// 服务器要监听的本地端口
#define MYPORT 4000
// 能够同时接受多少没有accept 的连接
#define BACKLOG 10
main()
{// 在sock_fd 上进行监听,new_fd 接受新的连接int sockfd, new_fd ;// 自己的地址信息struct sockaddr_in my_addr;// 连接者的地址信息struct sockaddr_in their_addr;int sin_size;// 这里就是我们一直强调的错误检查.如果调用socket() 出错,则返回if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1){// 输出错误提示并退出perror("socket");exit(1);}// 主机字节顺序my_addr.sin_family = AF_INET;// 网络字节顺序,短整型my_addr.sin_port = htons(MYPORT);// 将运行程序机器的IP 填充入s_addrmy_addr.sin_addr.s_addr = INADDR_ANY;// 将此结构的其余空间清零bzero(&(my_addr.sin_zero), 8);// 这里是我们一直强调的错误检查!!if (bind(sockfd, (struct sockaddr *)&my_addr,sizeof(struct sockaddr)) == -1){// 如果调用bind()失败,则给出错误提示,退出perror("bind");exit(1);}// 这里是我们一直强调的错误检查!!if (listen(sockfd, BACKLOG) == -1){// 如果调用listen 失败,则给出错误提示,退出perror("listen");exit(1);}while(1){// 这里是主accept()循环sin_size = sizeof(struct sockaddr_in);// 这里是我们一直强调的错误检查!!if ((new_fd = accept(sockfd, (struct sockaddr *)&their_addr, &sin_size)) == -1){// 如果调用accept()出现错误,则给出错误提示,进入下一个循环perror("accept");continue;}// 服务器给出出现连接的信息printf("server: got connection from %s\n", inet_ntoa(their_addr.sin_addr));// 这里将建立一个子进程来和刚刚建立的套接字进行通讯if (!fork()){// 这里是子进程// 这里就是我们说的错误检查!if (send(new_fd, "Hello, world!\n", 14, 0) == -1){// 如果错误,则给出错误提示,然后关闭这个新连接,退出perror("send");close(new_fd);exit(0);}// 关闭new_fd 代表的这个套接字连接close(new_fd);}}// 等待所有的子进程都退出while(waitpid(-1,NULL,WNOHANG) > 0);
}
###################################################################################
 
###################################################################################
/* include fig01 */
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netdb.h>
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <sys/poll.h>
#include <errno.h>
#define MAXLINE 512
#define NOTDEF
int
main(int argc, char **argv)
{int      i, maxi, maxfd, listenfd, connfd, sockfd;int      nready, client[FD_SETSIZE];ssize_t     n;fd_set     rset, allset;char     buf[MAXLINE];socklen_t    clilen;struct sockaddr_in cliaddr, servaddr;
 listenfd = socket(AF_INET, SOCK_STREAM, 0);
 bzero(&servaddr, sizeof(servaddr));servaddr.sin_family       = AF_INET;servaddr.sin_addr.s_addr = htonl(INADDR_ANY);servaddr.sin_port         = htons(4563);
 bind(listenfd, (struct sockaddr *) &servaddr, sizeof(servaddr));
 listen(listenfd, 12);
 maxfd = listenfd;    /* initialize */maxi = -1;      /* index into client[] array *///for (i = 0; i < FD_SETSIZE; i++)for (i = 0; i < 3; i++)client[i] = -1;    /* -1 indicates available entry *//*void FD_ZERO(fd_set *fdset)Initialises the file descriptor set fdset to have zero bits for all file descriptors. 初始化所有的文件描述符fd_set为0*/FD_ZERO(&allset);/*void FD_SET(int fd, fd_set *fdset)Sets the bit for the file descriptor fd in the file descriptor set fdset. */FD_SET(listenfd, &allset);
/* end fig01 */
/* include fig02 */for ( ; ; ) {rset = allset;   /* structure assignment */nready =select(maxfd+1, &rset, NULL, NULL, NULL);/*定义函数  int select(int n,fd_set * readfds,fd_set * writefds,fd_set *       
                     exceptfds,struct timeval * timeout);
   select()用来等待文件描述词状态的改变。参数n代表最大的文件描述词加1,参数readfds、writefds 和exceptfds 称为描述词组,是用来回传该描述词的读,写或例外的状况。底下的宏提供了处理这三种描述词组的方式:FD_CLR(inr fd,fd_set* set);用来清除描述词组set中相关fd 的位FD_ISSET(int fd,fd_set *set);用来测试描述词组set中相关fd 的位是否为真FD_SET(int fd,fd_set*set);用来设置描述词组set中相关fd的位FD_ZERO(fd_set *set); 用来清除描述词组set的全部位参数  timeout为结构timeval,用来设置select()的等待时间,其结构定义如下struct timeval{time_t tv_sec;time_t tv_usec;};返回值  如果参数timeout设为NULL则表示select()没有timeout。错误代码  执行成功则返回文件描述词状态已改变的个数,如果返回0代表在描述词状态改变前已超过timeout时间,当有错误发生时则返回-1,错误原因存于errno,此时参数readfds,writefds,exceptfds和timeout的值变成不可预测。EBADF 文件描述词为无效的或该文件已关闭EINTR 此调用被信号所中断EINVAL 参数n 为负值。ENOMEM 核心内存不足常见的程序片段:fs_set readset;FD_ZERO(&readset);FD_SET(fd,&readset);select(fd+1,&readset,NULL,NULL,NULL);if(FD_ISSET(fd,readset){……}
   */
   if (FD_ISSET(listenfd, &rset)) { /* new client connection *//*int FD_ISSET(int fd, fd_set *fdset)Returns a non-zero value if the bit for the file descriptor fd is set in the file descriptor set by fdset, and 0 otherwise. */clilen = sizeof(cliaddr);connfd = accept(listenfd, (struct sockaddr *) &cliaddr, &clilen);printf("Welcome!\n");sleep(1);
#ifndef NOTDEFprintf("new client: %s, port %d\n",inet_ntop(AF_INET, &cliaddr.sin_addr, NULL,4 ),ntohs(cliaddr.sin_port));
#endif
    //for (i = 0; i < FD_SETSIZE; i++)for (i = 0; i < 3; i++)if (client[i] < 0) {client[i] = connfd; /* save descriptor */break;}if (i == FD_SETSIZE)printf("too many clients");
    FD_SET(connfd, &allset); /* add new descriptor to set */if (connfd > maxfd)maxfd = connfd;    /* for select */if (i > maxi)maxi = i;     /* max index in client[] array */
    if (--nready <= 0)continue;     /* no more readable descriptors */}
   for (i = 0; i <= maxi; i++) { /* check all clients for data */if ( (sockfd = client[i]) < 0)continue;if (FD_ISSET(sockfd, &rset)) {if ( (n = read(sockfd, buf, MAXLINE)) == 0) {/*4connection closed by client */close(sockfd);FD_CLR(sockfd, &allset);/*void FD_CLR(int fd, fd_set *fdset)Clears the bit for the file descriptor fd in the file descriptor set fdset. */client[i] = -1;} elsewrite(sockfd, buf, n);
     if (--nready <= 0)break;     /* no more readable descriptors */}}}
}
/* end fig02 */
###################################################################################

LINUX下Socket编程 函数格式详解相关推荐

  1. linux下socket编程读写函数

    linux下socket编程,实现服务器与客户端的通信之后,在同一个虚拟机上,打开两个shell,一个运行服务器程序,一个运行客户端程序,课相互发送数据. 如果使用的是recv接收函数,当关闭客户端或 ...

  2. linux下防火墙iptables用法规则详解

    linux下防火墙iptables用法规则详解 分享者: du52.com 邮件: wangaibo168@163.com 主页: http://www.du52.com linux下防火墙iptab ...

  3. linux paste 变量,Linux下的paste合并命令详解

    paste单词意思是粘贴.该命令主要用来将多个文件的内容合并,与cut命令完成的功能刚好相反. 粘贴两个不同来源的数据时,首先需将其分类,并确保两个文件行数相同.paste将按行将不同文件行信息放在一 ...

  4. Linux下Socket编程

    Linux下Socket编程    网络的Socket数据传输是一种特殊的I/O,Socket也是一种文件描述符.Socket也具有一个类似于打开文件的函数调用Socket(),该函数返回一个整型的S ...

  5. Linux下fdisk命令操作磁盘详解--添加、删除、转换分区

    linux下fdisk命令操作磁盘详解--添加.删除.转换分区等 fdisk 操作硬盘的命令格式如下: [root@localhost beinan]# fdisk 设备 比如我们通过 fdisk - ...

  6. Linux下暴力破解工具Hydra详解

    Linux下暴力破解工具Hydra详解 一.简介 Number one of the biggest security holes are passwords, as every password s ...

  7. linux电脑关机命令是什么问题,linux下正常关机之命令详解 -电脑资料

    系统启动的时候生成一个文件,正常关机的时候会删除这个文件,管理过程中出现故障的机率. 步骤: 在/etc/rc.d/init.d/下编程脚本. 判断是否正常关机,和生成文件的脚本:touch-file ...

  8. 一文了解linux下socket编程

    一文了解linux下socket编程 文章目录 一文了解linux下socket编程 1 网络编程的相关简述 1.1 引言 1.2 Tcp和Udp简介 1.3 TCP三次握手和四次挥手 1.4 网络编 ...

  9. Linux下sysstat安装使用图文详解

    文章目录 Linux下sysstat安装使用图文详解 1.iostat 2.mpstat 3.sadc 4.sadf 5.sar 6.pidstat Linux下sysstat安装使用图文详解 Sys ...

最新文章

  1. Java课程寒假之开发记账本软件(网页版)之二
  2. Tokyo Tyrant基本规范(4)--协议
  3. 求数组中的最小值以及最小值的序列号
  4. 西安电子科技大学计算机录取分数,2021年西安电子科技大学投档线及各省最低录取分数线统计表...
  5. 一篇搞定,分布式系统中唯一主键生成
  6. 思科Webex与下一代视频会议
  7. 常见的NoSQL数据库
  8. PoPo数据可视化第8期
  9. innodb存储引擎 - 锁
  10. 结巴分词关键词相似度_jieba+gensim 实现相似度
  11. (BookxNote Pro)Windows版Marginnote 3 阅读神器 自动生成脑图/思维导图
  12. 8数码的各种版本-搜索
  13. 记一次渗透测试某路由器
  14. 计算机校友讲座,计算机系举办优秀校友返校讲座
  15. python mysql library,python调用mysql报错解决方案
  16. 华为机试真题 C++ 实现【最大化控制资源成本】【100%通过率】【2022.11 Q4 新题】
  17. 学习WPF之解决方案和项目结构
  18. Android X86更改屏幕分辨率
  19. MyEclipse创建jsp项目
  20. DGA 域名生成和检测算法

热门文章

  1. 模拟多线程并发订单处理功能实现
  2. IEEE T PAMI投稿注意事项
  3. 宝塔同时安装苹果cms海洋cms_苹果cms用宝塔定时采集+添加百度推送教程
  4. 小红书笔记发布软件 批量上传视频
  5. iOS开发:图标生成器Prepo 的使用,讲的明明白白
  6. R语言在图上标出点坐标_R语言绘制平行坐标图(PCP)示例
  7. 快速了解K4B2G1646F-BYK0
  8. int数据类型的取值范围是多少?怎么计算的?
  9. otg烧写linux内核,Linux——OTG方式烧写镜像文件步骤总结
  10. USB OTG原理简述