首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

高级I/O函数

Posted on 2009-12-11 17:09  放飞自我  阅读(466)  评论(0编辑  收藏  举报

高级I/O函数

 

以下这两个函数是最通用的I/O函数,recvmsg可以代替read, readv, recv recvfrom 同样,sendmsg可以代替其他的发送函数。

#include < sys/socket.h >

ssize_t recvmsg(int sockfd, struct msghdr * msg, int flags)

ssize_t sendmsg(int sockfd, struct msghdr * msg, int flags)

            返回:成功是为读入或写出的字节数, 出错时为-1

 

以下是参数结构体的描述:

 

           struct iovec {                    /* Scatter/gather array items */

               void *iov_base;              /* Starting address */

               size_t iov_len;               /* Number of bytes to transfer */

           };

 

           struct msghdr {

               void         *msg_name;       /* optional address */

               socklen_t     msg_namelen;    /* size of address */

               struct iovec   *msg_iov;        /* scatter/gather array */

              size_t        msg_iovlen;     /* # elements in msg_iov */

               void         *msg_control;    /* ancillary data, see below */

               socklen_t     msg_controllen; /* ancillary data buffer len */

               int           msg_flags;      /* flags on received message */

           };

 

           struct cmsghdr {

               socklen_t      cmsg_len;     /* data byte count, including hdr */

               int           cmsg_level;   /* originating protocol */

               int           cmsg_type;    /* protocol-specific type */

           /* followed by

               unsigned char  cmsg_data[]; */

           }

 

1.      首先对struct msghdr结构体进行解释:

msg_name 指向一个套接口地址的结构,msg_namelen是其长度。他和recvfrom sendto的第五和第六个参数类似。比如指向一个sockaddr_in结构,里面填充相应的数值。对于sendmsg来说是目的方的协议地址,recvmsg的是发送方的协议地址。

msg_iov msg_iovlen成员指明输入或输出的缓冲区数组。举个简单例子,比如我要发送buf1[100],buf2[50],两个数组(当让也可以是你自定义的结构体),如果发送Udp报文,要发送两次。但可以用msg_iov[2],每个结构体中的iov_base指向各自数组的起始地址,iov_len表示大小。这样发送一个udp报文就可以把这两个数组发送出去。接收也是同样的道理。

我们可以看到函数入口有一个flag,参数结构体里有msg_flags成员。msg_flags只用于recvmsg。调用recvmsg时,flags参数被拷贝到msg_flags成员,内核用这个值进行接受处理。sendmsg会忽略msg_flags成员,因为他在进行输出处理时使用flags参数,比如我们在调用sendmsg成员是设置MSG_DONTWAIT标志,要设置参数flags,而不是msg_flags.

       msg_controlmsg_controllen成员指明可选的辅助数据的位置和大小,msg_controllenrecvmsg是一个值——结果参数。这个结构体会在其他地方提到。

 

flags的定义有:可以使多个的或

MSG_DONTROUTE:不要使用网关来发送封包,只发送到直接联网的主机。这个标志主要用于诊断或者路由程序。
MSG_DONTWAIT
:操作不会被阻塞。
MSG_EOR
:终止一个记录。
MSG_MORE
:调用者有更多的数据需要发送。
MSG_NOSIGNAL
:当另一端终止连接时,请求在基于流的错误套接字上不要发送SIGPIPE信号。
MSG_OOB
:发送out-of-band数据(需要优先处理的数据),同时现行协议必须       支持此种操作。