/* 发布时间: 2008-12-27 程序版本: vtcp.dll ver1.0.0(beta0) 模块下载BIN: http://www.cnasm.com/down/vtcp.dll 测试程序BIN: http://www.cnasm.com/down/vtcptest.exe 测试程序SRC: http://www.cnasm.com/down/vtcptest.rar
吹一下: 别看vtcp程序小(17KB)但几乎模拟了TCP的一切,滑动窗口...目前他提供阻塞模式与异步完成模式API支持.
目前局网效率: 以UDP可靠传输文件为例,10OMbps局网传输极限速度(6MB/S),网络占有率50% 高于TCP协议(5MB/S),网络占有率50%,如何进一步提高UDP传输效率,还需要研究实验,我想我应该接近极限了, 目前要做的就是提高vtcp的稳定性与兼容winsock编程接口.
目前外网效率: 以UDP可靠传输文件为例,外网与TCP协议相当,TCP(50KB/S)时,测试VTCP(30-110KB/S).
vtcptest -s port : 打开服务端口 vtcptest -c host port path 下载文件
例如: 开服务执行: vtcptest -s 8080 下文件执行: vtcptest -c 192.168.0.102 8080 c:\1234.rmvb
connect... connect ok! save to: c:\1234.rmvb.download recv: 214245376 bytes, rapid: 6152 kb/s download ok ( 214592451 bytes )!!!
quit... */
//API接口
#pragma once
int WINAPI vtcp_startup(); int WINAPI vtcp_cleanup(); int WINAPI vtcp_socket(int type);//0=tcp client socket,1=tcp service socket int WINAPI vtcp_bind(int s,PSOCKADDR_IN sai,int sailen); int WINAPI vtcp_listen(int s,int backlog); int WINAPI vtcp_accept(int s); int WINAPI vtcp_connect(int s,PSOCKADDR_IN sai,int sailen,int timeo); int WINAPI vtcp_sendex(int s,LPWSABUF lpBuffers,DWORD dwBufferCount,LPDWORD lpNumberOfBytesSent, DWORD dwFlags,LPWSAOVERLAPPED lpOverlapped,LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine); int WINAPI vtcp_recvex(int s,LPWSABUF lpBuffers,DWORD dwBufferCount,LPDWORD lpNumberOfBytesRecvd, LPDWORD lpFlags,LPWSAOVERLAPPED lpOverlapped,LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine); int WINAPI vtcp_send(int s,PCHAR buf,int len); int WINAPI vtcp_recv(int s,PCHAR buf,int len); int WINAPI vtcp_closesocket(int s); int WINAPI vtcp_getlasterror(int s);
////////////////////////////////////////////////////////////////////////// //int WINAPI vtcp_setkeepalive(int keepalive,int keepaliveinternal); //int WINAPI vtcp_setsendtimeo(int timeo); //int WINAPI vtcp_setrecvtimeo(int timeo); //////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////// //测试程序VC++ console 代码 //////////////////////////////////////////////////////////////////////////
// vtcptest.cpp : 定义控制台应用程序的入口点。 // #include "stdafx.h" ULONG WINAPI TA(LPVOID p) { int s=int(p);char buffer[8192];while(true){int rcb=vtcp_recv(s,buffer,sizeof(buffer));if(rcb<0){vtcp_closesocket(s); return0;}HANDLE hfile=CreateFile(buffer,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,0,NULL); if(INVALID_HANDLE_VALUE==hfile){vtcp_closesocket(s); return0;}DWORD cb=(-1); while(true){if(!ReadFile(hfile,buffer,8192,&cb,NULL)){break;}if(cb==0){break;}if(0>=vtcp_send(s,buffer,cb)){break;}}CloseHandle(hfile); if(cb==0){if(0>=vtcp_send(s,"X",1)){vtcp_closesocket(s); return0;}}else{vtcp_closesocket(s); return0;}}return0;} ULONG WINAPI TS(DWORD port) { SOCKADDR_IN sai; sai.sin_family=AF_INET; sai.sin_addr.S_un.S_addr=0; sai.sin_port=htons(WORD(port)); int s=vtcp_socket(1);if(0==s){return SOCKET_ERROR;}if(0!=vtcp_bind(s,&sai,sizeof(sai))){return SOCKET_ERROR;}if(0!=vtcp_listen(s,5)){return SOCKET_ERROR;}printf("listen success...\r\n"); while(true){int as=vtcp_accept(s);if(0!=as){DWORD dwtid; CloseHandle(CreateThread(NULL,0,TA,LPVOID(as),0,&dwtid)); printf("accept success...\r\n"); }}vtcp_closesocket(s); return0;} ULONG WINAPI TC(PCHAR host,DWORD port,PCHAR path) { PHOSTENT ph=gethostbyname(host); if(NULL==ph){return0;}SOCKADDR_IN sai; sai.sin_family=AF_INET; sai.sin_addr.S_un.S_addr=*LPDWORD(ph->h_addr_list[0]); sai.sin_port=htons(WORD(port)); int s=vtcp_socket(0);printf("connect...\r\n"); if(vtcp_connect(s,&sai,sizeof(sai),1000*30)){vtcp_closesocket(s); return0;}printf("connect ok!\r\n"); if(0>=vtcp_send(s,path,1024)){vtcp_closesocket(s); return0;}char buffer[8192];lstrcpy(buffer,path); lstrcat(buffer,".download"); printf("save to: %s\r\n",buffer); HANDLE hfile=CreateFile(buffer,GENERIC_WRITE,FILE_SHARE_READ,NULL,CREATE_ALWAYS,0,NULL); if(INVALID_HANDLE_VALUE==hfile){vtcp_closesocket(s); return0;}DWORD wcb,count=0; DWORD dw=GetTickCount(); DWORD dwsize=0,dwrapid; while(true){int rcb=vtcp_recv(s,buffer,sizeof(buffer));if(rcb==1){if(buffer[0]==$1$X$1$){break;}}if(!WriteFile(hfile,buffer,rcb,&wcb,NULL)){break;}count=count+rcb; DWORD dw2=GetTickCount(); dwsize=dwsize+rcb; if(dw2-dw>1000){dwrapid=dwsize/(dw2-dw); dwsize=0; dw=dw2; printf("recv: %d bytes, rapid: %d kb/s \r",count,dwrapid); }}CloseHandle(hfile); vtcp_closesocket(s); printf("\r\n"); printf("download ok ( %d bytes )!!!\r\n",count); printf("\r\n"); return0;} int main(int argc,char* argv[]){ vtcp_startup(); if(argc==3)if(!lstrcmpi(argv[1],"-s")){TS(atoi(argv[2])); }if(argc==5)if(!lstrcmpi(argv[1],"-c")){TC(argv[2],atoi(argv[3]),argv[4]); }vtcp_cleanup(); printf("quit...\r\n"); return0;} |