这个一个基于win32程序做的一个网络监控的服务端中的发送数据的代码,其中
typedef struct tagFileInfo
{
char filename[512];
DWORD filesize;
bool dir;
}FILEINFO;
这是用于传输文件信息的结构体,
这个TerminalSendDataS和下面的重叠模式发送数据的TerminalSendData是分别怎么实现将上面这个自定义的结构体和其他一些结构体发送到客服端的,还有就是这两个函数什么区别,谢谢
/////////////////////////////////////////////////////
/////////////////////////////////////////////////////
/////////////////////////////////////////////////////
bool TerminalSendDataS(SOCKET socket,char *data,DWORD len,DWORD *retlen,WSAEVENT hSendEvent,DWORD time)
{
DWORD left,idx,thisret;
left=len;
idx=0;
int oflag=0;
while(left>0)
{
if(!TerminalSendData(socket,&data[idx],left,&thisret,hSendEvent,time))
{
*retlen=0;
return false;
}
WSAResetEvent(hSendEvent);
left-=thisret;
idx+=thisret;
if(thisret==0)
{
oflag++;
if(oflag>5)
break;
}
}
*retlen=idx;
return (idx==len)?true:false;
}
//////////////////////////////////////////////////
//////////////////////////////////////////////////
//////////////////////////////////////////////////
//重叠模式发送数据
bool TerminalSendData(SOCKET socket,char *data,DWORD len,DWORD *retlen,WSAEVENT hSendEvent,DWORD time)
{
WSABUF DataBuf;
WSAEVENT hEvents[2];
WSAOVERLAPPED SendOverLapp;
DWORD flag; hEvents[0]=hExitEvent;
hEvents[1]=hSendEvent;
DataBuf.buf=data;
DataBuf.len=len;
memset(&SendOverLapp,0,sizeof(WSAOVERLAPPED));
SendOverLapp.hEvent=hSendEvent;
flag=0;
/////////////////////////////////////
int ret;
if((ret=WSASend(socket,&DataBuf,1,retlen,flag,&SendOverLapp,NULL))==0)
return true;
else if((ret==SOCKET_ERROR)&&(WSAGetLastError()==WSA_IO_PENDING))
{
DWORD EventCaused=WSAWaitForMultipleEvents(2,hEvents,FALSE,time,FALSE);
WSAResetEvent(hSendEvent);
if(EventCaused == WSA_WAIT_FAILED || EventCaused == WAIT_OBJECT_0)
{
if(EventCaused == WAIT_OBJECT_0)
SetLastError(TERMINAL_FUNERROR);
return false;
}
flag=0;
return WSAGetOverlappedResult(socket,&SendOverLapp,retlen,false,&flag)?
true:false;
}
else
return false;
}//////////////////////////////////////////////////
/////////////////////////////////////////////////
//////////////////////////////////////////////////
………………
………………
DWORD retLen;
HANDLE hFile;
FILEATTRIB attrib;
WIN32_FIND_DATA WFD;
//得到需返回那个目录的文件信息
if(!TerminalRecvDataS(s,(char*)&attrib,sizeof(attrib),&retLen,
 hEvent,SENDRECV_TIMEOUT))
 return false;
………………
………………

解决方案 »

  1.   

    FILEINFO fInfo;
    if(!TerminalRecvDataS(s,(char*)&fInfo,sizeof(fInfo),&retLen,hEvent,SENDRECV_TIMEOUT))
    return false;
    就可以把一个FILEINFO结构体发出去了呀。bool TerminalSendData(SOCKET socket,char *data,DWORD len,DWORD *retlen,WSAEVENT hSendEvent,DWORD time)
    这是发送网络数据的核心部分,但它不能保证data缓冲区中的所有数据都被发送出去了,在只发送出去一部分数据时,这个函数也会返回TRUE,真正发送出去的字节数在参数retlen中返回。bool TerminalSendDataS(SOCKET socket,char *data,DWORD len,DWORD *retlen,WSAEVENT hSendEvent,DWORD time)
    这个函数多次调用TerminalSendData(),保证data缓冲区的数据全部被发送出去的,否则就返回FALSE,真正发送出去的字节数在参数retlen中返回。
      

  2.   

    TerminalSendDataS()中主要是一些字节计数和指针偏移的逻辑,自己慢慢分析一下吧。
    oflag是发送失败后的重复尝试发送的计数,重试次数上限为5次