Socket网络编程笔记(三)

本文将记录如何封装基于socket的网络发送与接收接口(非阻塞)

1. 接收

参数:void *buffer, int length

当我们需要从网络中接收一定长度的数据时,不能单纯只调用相应的socket recv就可以了,通常我们

需要考虑当前系统及网络的情况:

1)一次性接收成功

这是最简单和理想的情况,所期望接收的数据通过socket能够一次性成功,即recv返回长度和期望接收length一致。

此时可直接返回;

2)接收成功,但未完全接收期望的数据

针对这一种情况,可以有两种处理方式:

a. 可以立马返回,由更上层调用者负责处理是否重新调用此接口来完成剩余数据的接收;

b. 如果想在此接口中处理,则通常的做法是在while循环中处理接收操作,只至全部数据接收完成后退出循环后返回。具体操作示例

如下:

char * pos = (char*)buffer;
do
{
recvLength = recv(pos, length);

length -= recvLength;
//buffer的指针移位
pos += recvLength;
}while(length>0)

3) 接收等待,设置超时

当socket接收函数返回EWOULDBLOCK的状态时,表示接收并未成功,需要等待。此时,我们需要对socket进行

监听,必要时加入超时机制,以下展示了如何操作:

if (ret == EWOULDBLOCK )
{
int selectRet = select(socket + 1, xxx, xxx);  //对socket读FD进行监听
if ( selectRet == 0 ) // timeout
{
 // do something
}
else if ( selectRet < 0 ) // error
{
// do something
}
}
else //接收成功
{
<pre name="code" class="cpp">//do something,通常做
<pre name="code" class="cpp">length -= recvLength;
//buffer的指针移位
pos += recvLength;

}


当然,以上几种情况在真实写代码时,需要有机结合起来,成为一体。结构如下:

do
{
// call recv function;
if ( EWOULDBLOCK)
{
do select()
if( selectRet == 0 )
{
return;
}
else if(selectRet < 0 )
{
return; //error
}
}
else //接收成功
{
pos += recvLength;
length -= recvLength;
}
}while(length > 0 )
return ok;

2.发送

发送的流程情况和接收类似,操作也雷同,不同的地方是当遇到EWOULDBLOCK时,需要select socket的写FD。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值