您的位置:首页 > 理论基础 > 计算机网络

【网络编程】UDP数据传输及文件传输实验

2017-02-24 09:44 615 查看

实验要求:

内容1:利用数据报套接字实现数据传输

1.    客户端创建UDP套接字,向指定的服务端发送数据;
2.    服务端接收到新数据,显示是谁发送过来的,并把该数据回传给发送方;
3.    服务端使用多线程来实现并发。
4.    观察在服务端启动和不启动时,客户端的运行情况。

内容2:使用UDP套接字实现文件传输

1.    客户端向服务端发送文件名
2.    客户端向服务端传输文件内容;
3.    双方关闭套接字。
4.    注意收发速度对文件传输结果的影响。

源码


客户端

#include "stdafx.h"
#include <iostream>
#include <stdio.h>
#include <winsock2.h>
#include <windows.h>
using namespace std;
#pragma comment(lib, "ws2_32.lib")
const int MAX_IP_PATH = 15;
const int  MAX_BUFFER = 10240;
const int NAME = 10240;

int main(int argc, char* argv[])
{
WORD socketVersion = MAKEWORD(2, 2);
WSADATA wsaData;
if (WSAStartup(socketVersion, &wsaData) != 0)
{
return 0;
}
SOCKET ClientSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (ClientSocket == INVALID_SOCKET)
{
cout << "Create Socket Failed::" << GetLastError() << endl;
WSACleanup();
return -1;
}

char IP_ADDRESS[MAX_IP_PATH];
unsigned int PORT;
cout << "connect IP:";
cin >> IP_ADDRESS;
cout << endl;
cout << "connect port:";
cin >> PORT;
cout << endl;

sockaddr_in sin;
sin.sin_family = AF_INET;
sin.sin_port = htons(PORT);
sin.sin_addr.S_un.S_addr = inet_addr(IP_ADDRESS);

//消息发送回传
unsigned int msglen;
char SendBuffer[MAX_BUFFER];
int len = sizeof(sin);
cout << "input message:";
cin >> SendBuffer;
cout << endl;
msglen = strlen(SendBuffer);
sendto(ClientSocket, SendBuffer, strlen(SendBuffer), 0, (sockaddr *)&sin, len);

int Ret;
char RecvBuffer[MAX_BUFFER];
Ret = recvfrom(ClientSocket, RecvBuffer, msglen, 0, (sockaddr *)&sin, &len);
if (Ret <0)
{
cout << "receive error:" << WSAGetLastError();
closesocket(ClientSocket);
WSACleanup();
return -1;
}
RecvBuffer[Ret] = 0;
cout << "receive message: " << RecvBuffer << endl;

unsigned int ThreadPORT;
Ret = recvfrom(ClientSocket, (char *)&ThreadPORT, msglen, 0, (sockaddr *)&sin, &len);
if (Ret <0)
{
cout << "receive post error " << WSAGetLastError();
system("pause");
return -1;
}
cout << "receive post:" <<ThreadPORT << endl;
sin.sin_port = htons(ThreadPORT);
//文件传输
char filename[NAME];
cout << "file name:\n";
cin >> filename;
sendto(ClientSocket, filename, strlen(filename), 0, (sockaddr *)&sin, len);

FILE *fp = fopen(filename, "rb");
if (fp == NULL)
{
printf("create file failed\n");
system("pause");
return -1;
}
fseek(fp, 0L, SEEK_END);
unsigned int size = ftell(fp);
cout << "file size:" << size << endl;
fseek(fp, 0, SEEK_SET);
sendto(ClientSocket, (char *)&size, 4, 0, (sockaddr *)&sin, len);

int cnt = 1;
unsigned int Length;
cout << "begin to send file...." << endl;
while (size > 0)
{
memset(SendBuffer, 0, sizeof(char));
if (size >= MAX_BUFFER)
{
Length = fread(SendBuffer, sizeof(char), MAX_BUFFER, fp);
size-= MAX_BUFFER;
}
else
{
Length = fread(SendBuffer, sizeof(char), Length, fp);
size=0;
}
sendto(ClientSocket, SendBuffer, (int)Length, 0, (sockaddr *)&sin, len);
cout << "pack " << cnt++ << ", file " << size << endl;
}

closesocket(ClientSocket);
cout << "send file ok" << endl;;
system("pause");
WSACleanup();
return 0;
}


服务端

#include "stdafx.h"
#include <iostream>
#include <cstdio>
#include <winsock2.h>
#include <windows.h>

using namespace std;
#pragma comment(lib, "ws2_32.lib")
const unsigned int POST = 8000;
const int MAX_BUFFER = 10240;
const int NAME = 10240;

DWORD WINAPI ClientThread(LPVOID lpParameter)
{
SOCKET ClientSocket = (SOCKET)lpParameter;
sockaddr_in remoteAddr;
int nAddrLen = sizeof(remoteAddr);
int Ret = 0;

char name[NAME];
Ret = recvfrom(ClientSocket, name, MAX_BUFFER, 0, (sockaddr *)&remoteAddr, &nAddrLen);
if (Ret <= 0)
{
cout << "Receive Error£¡" << WSAGetLastError();
return -1;
}
name[Ret] = 0;
printf("Receive FileName From Client :: %s\n", name);

unsigned int length;
recvfrom(ClientSocket, (char*)&length, 4, 0, (sockaddr *)&remoteAddr, &nAddrLen);
cout << "flie length :" << length << endl;

FILE *fp = NULL;
fp = fopen(name, "ab");
if (fp == NULL)
{
printf("Open File Error£¡\n");
return -1;
}
cout << "begin to get file...." << endl;
int cnt = 0;
char RecvBuffer[MAX_BUFFER];
while (length>0)
{
memset(RecvBuffer, 0, sizeof(RecvBuffer));
Ret = recvfrom(ClientSocket, RecvBuffer, MAX_BUFFER, 0, (sockaddr *)&remoteAddr, &nAddrLen);
if (Ret <= 0)
{
cout << "receive error " << WSAGetLastError() << endl;;
closesocket(ClientSocket);
fclose(fp);
return -1;
}
fwrite(RecvBuffer, sizeof(char), Ret, fp);
fflush(fp);
length -= Ret;
cout << "pack " << ++cnt << "file " << length << endl;
}
cout << "get file" << endl;
closesocket(ClientSocket);
fclose(fp);
}

int main(int argc, char* argv[])
{
WORD sockVersion = MAKEWORD(2, 2);
WSADATA wsaData;
if (WSAStartup(sockVersion, &wsaData) != 0)
{
return 0;
}

SOCKET serSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (serSocket == INVALID_SOCKET)
{
printf("socket error !");
WSACleanup();
return 0;
}

sockaddr_in serAddr;
serAddr.sin_family = AF_INET;
serAddr.sin_port = htons(POST);
serAddr.sin_addr.S_un.S_addr = INADDR_ANY;
if (bind(serSocket, (sockaddr *)&serAddr, sizeof(serAddr)) == SOCKET_ERROR)
{
printf("bind error !");
closesocket(serSocket);
WSACleanup();
return 0;
}

cout << "listening the client" << endl;

sockaddr_in remoteAddr;
int nAddrLen = sizeof(remoteAddr);
int cnt = 0;
char RecvBuffer[MAX_BUFFER];
while (true)
{
memset(RecvBuffer, 0, sizeof(RecvBuffer));
int Ret = recvfrom(serSocket, RecvBuffer, MAX_BUFFER, 0, (sockaddr *)&remoteAddr, &nAddrLen);
if (Ret < 0)
{
cout << "receive error " << WSAGetLastError();
continue;
}
RecvBuffer[Ret] = 0x00;
cout << "client " << ++cnt << ": " << inet_ntoa(remoteAddr.sin_addr) << endl;
printf("say:%s\n", RecvBuffer);

sendto(serSocket, RecvBuffer, strlen(RecvBuffer), 0, (sockaddr *)&remoteAddr, nAddrLen);
SOCKET ClientSocket;
ClientSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
if (ClientSocket == INVALID_SOCKET)
{
printf("socket error !");
WSACleanup();
continue;
}

sockaddr_in ClientAddr;
unsigned int ThreadPORT = POST;
while (ThreadPORT <= 65535)
{
++ThreadPORT;
ClientAddr.sin_family = AF_INET;
ClientAddr.sin_port = htons(ThreadPORT);
ClientAddr.sin_addr.S_un.S_addr = INADDR_ANY;
if (bind(ClientSocket, (sockaddr *)&ClientAddr, sizeof(ClientAddr)) != SOCKET_ERROR)
break;
}
if (ThreadPORT > 65535)
{
cout << "creat thread failed" << endl;
continue;
}
cout << "the post " << ThreadPORT << " to client " << cnt << endl;
sendto(serSocket, (const char*)&ThreadPORT, sizeof(unsigned int), 0, (sockaddr *)&remoteAddr, nAddrLen);

HANDLE hThread = CreateThread(NULL, 0, ClientThread, (LPVOID)ClientSocket, 0, NULL);
if (hThread == NULL)
{
cout << "Create Thread Failed!" << endl;
continue;
}
CloseHandle(hThread);
}
closesocket(serSocket);
WSACleanup();
return 0;
}



内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: