windows网络编程实验4采用C++进行TCP通信之多线程文件传输

该代码示例展示了如何使用Winsock2库让服务器接收多个客户端的文件上传。服务器通过监听套接字接受连接请求,然后为每个客户端创建新线程进行文件传输。客户端则向服务器发送文件名和文件长度信息,等待服务器确认后发送文件内容。

实验要求:使服务器与多个客户端进行通信,同时接收多个客户端上传的文件。

服务端代码:

#include"iostream"
#include"afxmt.h"
#include"process.h"
#include"winsock2.h"
#include"fstream"
#include"WS2tcpip.h"
#include"direct.h"


#define PORT 65432
#pragma comment(lib,"ws2_32.lib")

using namespace std;
struct fileMessage
{
	char fileName[256];
	long int fileSize;
};


/*主程序和线程函数共用的全局变量定义*/
char fname[128] = { 0 };			//发送给客户端的无路径信息的文件名
ifstream inFile;					//定义文件的输入流
CMutex Section;						//创建互斥对象
void rdFile(void* par);			//发送文件的线程函数声明

/*主函数*/

int main()
{
	SOCKET sock_server;						//定义监听套接字
	struct sockaddr_in addr;
	struct sockaddr_in client_addr;	//存放本地地址和客户地址的变量
	SOCKET newsock;							//储存accept()返回的套接字描述符
	/*初始化winsock DLL*/
	WSADATA wsaData;
	if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0)
	{
		cout << "加载winSock动态链接库失败!\n";
		return 0;
	}

	/*创建监听套接字*/
	if ((sock_server = socket(AF_INET, SOCK_STREAM, 0)) < 0)
	{
		cout << "创建套接字失败!\n";
		WSACleanup();
		return 0;
	}

	/*绑定IP地址与端口*/
	memset((void*)&addr, 0, sizeof(addr));
	addr.sin_family = AF_INET;
	addr.sin_port = htons(65432);
	addr.sin_addr.s_addr = htonl(INADDR_ANY);
	if (bind(sock_server, (struct sockaddr*)&addr, sizeof(addr)) != 0)
	{
		cout << "绑定失败!\n";
		closesocket(sock_server);
		WSACleanup();
		return 0;
	}
	if (listen(sock_server, 5) != 0)
	{
		cout << "listen函数调用失败!\n";
		closesocket(sock_server);
		WSACleanup();
		return 0;
	}
	else
	{
		cout << "listenning.....\n";
	}

	/*接收客户连接请求*/
	int addr_len = sizeof(struct sockaddr_in);
	while (true)
	{
		newsock = accept(sock_server, (LPSOCKADDR)&client_addr, &addr_len);
		if (newsock != INVALID_SOCKET)
		{
			cout << "一个客户连接成功!" << endl;
			_beginthread(rdFile, 0, (LPVOID)newsock);

		}
		else
		{
			break;
		}

	}

	closesocket(newsock);
	closesocket(sock_server);
	WSACleanup();
	return 0;

}

void rdFile(void* par)
{
	/*定义文件传输所需变量*/
	struct fileMessage fileMsg;
	SOCKET sock = (SOCKET)par;
	long int filelen;
	char filename[500] = "C:\\Users\\86152\\source\\repos\\textfile"; //指定文件的保存目录
	char ok[3] = "OK";
	char fileBuffer[1000];		//接收文件数据的缓冲区
	_mkdir(filename);		//_mkdir()用于创建文件夹,其声明包含在direct.h中

	/*接收文件名及文件长度信息*/
	if ((filelen = recv(sock, (char*)&fileMsg, sizeof(fileMsg), 0)) &
评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值