选择套接字调用send和recv同步

时间:2012-02-16 16:13:48

标签: sockets network-programming

我正在使用select调用并接受来自“X”no客户端的连接。 我做了双工连接,即服务器到客户端和客户端到服务器。 当两个实体之间建立连接时,我将发送 从一个实体到另一个实体的数据块。 在发送过程中,我以块的形式读取一个文件并以块的形式发送数据。

while(file_size !=0)
{
    read_bytes = read(fd, buff, sizeof(buff));
    cnt_ = send(_sock_fd,buff,actually_read,0);
    file_size = file_size - cnt_;
    printf("total sent remaining %d : %d\n",size,actually_read);
}

在接收方 //首先我发送包含已被接受的大小的标题但在下面的发送调用中我使用了“get_readable_bytes”(使用ioctl),它返回了到达套接字的字节数 `while(size!= 0)     {         int test_ = 0;

    while(((cnt_= get_readable_bytes(_sock_fd))== 0) )//&& test_ == 0
    {
        cnt_= get_n_readable_bytes(_sock_fd);
        printf("Total bytes recved %d\n",cnt_);
        //test_ = test_ + 1;
    }

    while(cnt_ != 0)
    {
        actually_read = recv(_sock_fd, buff, sizeof(buff),0);
        int _cnt = get_n_readable_bytes(_sock_fd);
        printf("Total bytes recved %d\n",cnt_-_cnt);
        write(_fd,buff,actually_read);
        cnt_ = cnt_ - actually_read;
        test_ = 0;
    }

`现在的问题是 1.在执行接收功能控制时自动进入选择功能并尝试再次执行整个接收功能,这样就可以同步发送方和接收方,以便发送方完成后再启动接收方或发送方启动接收器? 2.如何保持发送和接收的字节数。 这是我的选择电话

`is_read_availble = select(maxfd + 1,&read_set,NULL,NULL,&timeout)`

超时10秒。

1 个答案:

答案 0 :(得分:0)

描述您需要的缓冲区代码类型。 (为了允许部分读/写,缓冲区需要在调用之间持久)BTW:你真的需要处理read()和write()的-1返回,因为它们会严重干扰你的缓冲区-簿记。 EINTR + EAGAIN / EWOULDBLOCK很常见。

struct buff {
        unsigned size;
        unsigned bot;
        unsigned top;
        char *buff;
        };
struct buff bf = {0,0,0,NULL};

initialisation:

bf.buff = malloc(SOME_SIZE);
        /* ... error checking omitted */
bp.size = SOME_SIZE;
bp.bot = bp.top =0;

reading:

unsigned todo;
int rc;

        /* (maybe) shift the buffer down to make place */
todo =  bf.top - bf.bot;
if (todo) {
        memmove (bf.buff, bf.buff + bf.bot, todo);
        bf.top = todo; bf.bot = 0;
        }

todo = bf.size - bf.top;

if (!todo) { /* maybe throttle? ... */ return; }
rc = read (fd, bf.buff+bp.top, todo);
        /* ... error checking omitted */
if (rc == -1) switch (errno) {...}
else if (rc == 0) {...}
else    {
        total_read += rc;
        bp.top +=  rc;
        }


writing:

unsigned todo; 
int rc;

todo =  bf.top - bf.bot;
if (!todo) { /* maybe juggle fd_set ... */ return; }
rc = write (fd, bf.buff+bp.bot, todo);
        /* ... error checking omitted */
if (rc == -1) switch (errno) {...}
else if (rc ==0) { ...}
else    {
        bp.bot += rc;
        total_written += rc;
        if (bp.bot == bp.top) bp.bot = bp.top =0;
        }
/* ... this is the place to juggle the fd_set for writing */