C语言-Windows网络编程-实验 基于UDP的Sockets编程:服务器和客户端 实现传输文件

和一个烂人合作的代码。其实上一个实验也有合作
代码我没仔细看了。代码风格也没纠正过来 不管他了
先贴上来

模块1可以将服务器端的一个文件使用UDP传输到客户端
客户端需要输入正确密码才能接收
模块2是服务器输入文本信息 传输过去 要定义文件名
同样要输密码

服务器端

#include 
#include 
#include 
#include 
#include 

#pragma comment (lib,"Ws2_32.lib")

void Stop_Connect(SOCKET &s)         //关闭连接
{
	closesocket(s);						//关闭套接字
	WSACleanup();						//释放套接字库
}

void File_InFo(char FileRoute[],char FileName[],int &RouteLen,int &NameLen)
{
	int i=0,j=0;
	printf("\n输入文件的路径(驱动盘:\\文件夹\\文件名):");
	scanf("%s",FileRoute);
	printf("%s\n",FileRoute);

	RouteLen=strlen(FileRoute);
	for(i=RouteLen-1;i>=0;i--)
	{
		if(FileRoute[i]=='\\')
			break;
		else
			NameLen++;
	}
	for(i=RouteLen-NameLen;i<RouteLen;i++)
	{
		FileName[j]=FileRoute[i];
		j++;
	}
}

int main()
{
	char FileName[50]={0};    //文件名字
	char FileRoute[100]={0};
	int NameLen=0;          //文件名字长度
	int RouteLen=0;         //文件路径长度
	char flag;              //判断是否继续下一步操作
	int i=0;
	int j=0;
	int n=1;
	int x;
	int y;
	char c[20]={0};

	int TransMode=0;            //选择发送已经存在的文件输入(1);选择发送即时数据输入(2)
	int FileSize=0;         //文件大小;
	int SendTimes=0;
	int Size=0;
	
	system("title UDP服务器");
	//system("mode con cols=49 lines=30");

	char sendbuf[65000] = {0};		// 发送数据缓冲区
	char recvbuf[1500] = {0};		// 接收数据缓冲区

	char password[7];				// 存放最长6位密码

	WSADATA wsaData;									// 创建类型为WSADATA的对象
	int iResult = WSAStartup(MAKEWORD(2,2),&wsaData);	// 初始化winsock并根据返回值判断错误信息
	if(iResult!=0)
	{
		printf("初始化失败。错误代码:%d\n",iResult);
		return 1;
	}

	SOCKET s;											// 定义套接字句柄
	s = socket(AF_INET, SOCK_DGRAM,0);					// 创建UDP套接字

	sockaddr_in addr,addr2;								// 套接字地址结构变量
	addr.sin_family=AF_INET;
	addr.sin_port=htons(75);
	addr.sin_addr.S_un.S_addr=INADDR_ANY;

	int addr2Len = sizeof(addr2);						// 套接字地址结构大小

	bind( s,(sockaddr*)&addr,sizeof(addr) );			// 绑定套接字

	if(iResult==0)										// 输出提示信息
	{
		printf("UDP服务器初始化完成\n");
		
	}

	char str[] = "\n正在等待UDP客户端连接...\n";
	for(i=0;str[i]!='\0';i++)							// 以打字机效果输出等待提示信息
	{
		printf("%c",str[i]);
		Sleep(35);
	}

	iResult = recvfrom( s,recvbuf,sizeof(recvbuf),0,(sockaddr*)&addr2,&addr2Len );		// 接收客户端名以获取来源ip
	if(iResult != 0)
	{
		printf("  客户端%s[%s]已上线!\n",recvbuf,inet_ntoa(addr2.sin_addr) );
		memset(recvbuf,0,sizeof(recvbuf));
	}
//	puts(recvbuf);


	printf("\n发送现有文件输入(1)\n发送文字信息输入(2)\n请选择:");
	scanf("%d",&TransMode);
	


	if(TransMode==1)
	{
		File_InFo(FileRoute,FileName,RouteLen,NameLen);
		FILE *fp;
		while(1)
		{
			if((fp=fopen(FileRoute,"r"))==NULL)
			{
				printf("文件不存在!输入Y重新输入,输入N结束输入,结束程序:");
				getchar();
				scanf("%c",&flag);
				
				if(flag=='N' || flag=='n')
				{
					Stop_Connect(s);
					return -1;
				}
				else 
				{
					File_InFo(FileRoute,FileName,RouteLen,NameLen);
				}
			}
			else break;
		}

		fseek(fp,0,SEEK_END);
		FileSize=ftell(fp);              //文件大小
		fclose(fp);
		if(float(FileSize/65000.0)==int(FileSize/65000))
			SendTimes=FileSize/65000;
		else
			SendTimes=FileSize/65000+1;
		printf("文件字符大小:%d",FileSize);
		printf("文件需要发送的次数:%d\n",SendTimes);

		

		x=SendTimes;
		i=1;
		while(1)     //传送次数,转换成字符串传送
		{
			y=x%10;
			x=x/10;
			c[i]=y+48;
			if(x==0)
				break;
			i++;
		}
		c[0]=i+48;
		
		sendto(s,c,sizeof(c),0,(sockaddr*)&addr2,addr2Len);	  //发送传送的次数
		getchar();
		printf("\n输入不超过6字符/3汉字的接收密码:");
		gets(password);
		sendto(s,password,sizeof(password),0,(sockaddr*)&addr2,addr2Len);
	    sendto(s,FileName,sizeof(FileName),0,(sockaddr*)&addr2,addr2Len);

		printf("\n文件已准备好发送至客户端!\n  客户端需输入密码才可接收文件\n");
		
		int num=4;

		printf("\n正在接收客户端回执信息...\n");
		while(num!=0)
		{
			recvfrom( s,recvbuf,sizeof(recvbuf),0,(sockaddr*)&addr2,&addr2Len );
				
			if(recvbuf[0] =='*')
				printf("%s\n",recvbuf);
			if(recvbuf[0]=='#')
			{
				puts(recvbuf);
				break;
			}
			if(recvbuf[0] =='!')
			{
				puts(recvbuf);
				Stop_Connect(s);      //关闭连接
				return 0;
			}
				
			memset(recvbuf,0,sizeof(recvbuf));
			num--;	
		}
		
		n=SendTimes;
		FILE *fp1;
		int i=1;
		fp1=fopen(FileRoute,"rb");
		while(1)
		{
			
			
			fseek(fp1, (i-1)*65000, SEEK_SET);
			fread(sendbuf, 65000,1,fp1);
			sendto(s,sendbuf,sizeof(sendbuf),0,(sockaddr*)&addr2,addr2Len);
			i++;
			Sleep(100);
			if(i>n)
				break;
		
		}
		fclose(fp1);


		printf("程序结束,传输完成...\n");
		Stop_Connect(s); 
		return 0;

	}






	getchar();

	if(TransMode==2)
	{
		printf("\n输入要传送的文件名称:");
		gets(FileName);
		printf("输入需要加密发送的文本信息:");
		gets(sendbuf);
		printf("输入不超过6字符/3汉字的密码:");
		gets(password);
		
		Size=strlen(sendbuf);
	
		x=1;
		i=1;
		while(1)     //传送次数,转换成字符串传送
		{
			y=x%10;
			x=x/10;
			c[i]=y+48;
			if(x==0)
				break;
			i++;
		}
		c[0]=i+48;
		sendto(s,c,sizeof(SendTimes),0,(sockaddr*)&addr2,addr2Len);	  //发送传送的次数
		sendto(s,password,sizeof(password),0,(sockaddr*)&addr2,addr2Len);// 发送密码到客户端
		sendto(s,FileName,sizeof(FileName),0,(sockaddr*)&addr2,addr2Len);
		printf("\n文件已准备好发送至客户端!\n  客户端需输入密码才可接收文件\n");
		
		int num=4;

			
			printf("\n正在接收客户端回执信息...\n");
			while(num!=0)
			{
				recvfrom( s,recvbuf,sizeof(recvbuf),0,(sockaddr*)&addr2,&addr2Len );
				if(recvbuf[0] =='*')
					printf("%s\n",recvbuf);
				if(recvbuf[0] =='#')
				{	
					puts(recvbuf);
					break;
				}
				 if(recvbuf[0] =='!')
				{
					puts(recvbuf);
					Stop_Connect(s);      //关闭连接
					return 0;
				}
				 
			
		
				memset(recvbuf,0,sizeof(recvbuf));
				num--;
			}

		 

        sendto(s,sendbuf,Size,0,(sockaddr*)&addr2,addr2Len);			// 发送密文到客户端
		
			
		printf("\n程序结束,传输完成...\n");
	}
	printf("\n相关资源已释放!\n");
	Stop_Connect(s);      //关闭连接
	return 0;
}

客户端

#include 
#include 
#include 
#pragma comment (lib,"Ws2_32.lib")

int main()
{
	system("title UDP客户端");

	char FileName[50]={0};

	char sendbuf[1500] = {0};		// 发送数据缓冲区
	char recvbuf[65000] = {0};		// 接收数据缓冲区
	char Name[] = "Client";			// 客户端名
	char password[7];				// 存储最长6位密码
	int RecvTimes=0;
	char c[20]={0};
	int n=0;
	int i;
	int x;
	int flag=0;
	char SendInFo[2]={0};
	int Size;

	WSADATA wsaData;									// 创建类型为WSADATA的对象
	int iResult = WSAStartup(MAKEWORD(2,2),&wsaData);	// 初始化winsock并根据返回值判断错误信息
	if(iResult!=0)
	{
		printf("初始化失败。错误代码:%d\n",iResult);
		return 1;
	}

	SOCKET s;											// 定义套接字句柄
	s = socket(AF_INET, SOCK_DGRAM,0);					// 创建UDP套接字

	sockaddr_in addr,addr2;								// 套接字地址结构变量
	addr.sin_family=AF_INET;
	addr.sin_port=htons(75);
	addr.sin_addr.S_un.S_addr=inet_addr("127.0.0.1");

	int addr2Len = sizeof(addr2);						// 套接字地址结构大小

	if(s!=0)										// 输出提示信息
	{
		printf("UDP客户端已经启动\n");
		
	}

	sendto(s,Name,sizeof(Name),0,(sockaddr*)&addr,addr2Len);		// 发送客户端名至服务器
	recvfrom(s,c,sizeof(c),0,(sockaddr*)&addr2,&addr2Len);
	x=c[0]-48; //次数数组元素个数
	int z;
	int j=0;
	for(i=1;i<=x;i++)
	{
		z=c[i]-48;
		for(j=1;j<i;j++)
		{
			z=z*10;
		}
		n+=z;
	}
	printf("传送次数:%d\n",n);
	recvfrom(s,password,sizeof(password),0,(sockaddr*)&addr2,&addr2Len);	// 接收密码
	recvfrom(s,FileName,sizeof(FileName),0,(sockaddr*)&addr2,&addr2Len);
/* RecvTimes=int(c[0]);
	n=RecvTimes;
	
*/
	char test1[]="*  客户端输入密码错误...";
	char test2[]="#  客户端已将输入正确密码,进行传输";
	char test3[]="!  客户端密码尝试次数耗尽,取消传输";
	int num=3;

	while(num!=0)
	{

		printf("\n输入密码接收查看原文:");
		char temp[6];
		gets(temp);
		if( strcmp(temp,password)==0 )
		{
			printf("  密码正确\n");
			printf("\n正在进行传输...\n");
			sendto(s,test2,sizeof(test2),0,(sockaddr*)&addr,addr2Len);
			
			flag=1;
			break;
		}
		else
		{
			num--;
			printf("  密码错误!");
			sendto(s,test1,sizeof(test1),0,(sockaddr*)&addr,addr2Len);
			if(num==0)
			{
				printf("尝试次数耗尽,断开连接,取消传送!\n");
				sendto(s,test3,sizeof(test1),0,(sockaddr*)&addr,addr2Len);
				printf("\n相关资源已释放!\n");
				closesocket(s);						// 关闭套接字
				WSACleanup();						// 释放套接字库
				return 0;
			}
			else
				printf("剩余%d次机会\n",num);
			
		}
	}





	FILE *fp1=fopen(FileName,"ab");
	for(i=1;i<=n;i++)
	{
	memset(recvbuf,0,sizeof(recvbuf));
	Size=recvfrom(s,recvbuf,sizeof(recvbuf),0,(sockaddr*)&addr,&addr2Len);
	
	fseek(fp1, (i-1)*65000, SEEK_SET);
	fwrite(recvbuf,Size,1,fp1);
	}
	
	
	fclose(fp1);
//	puts(recvbuf);
//	puts(password);

	
	
	printf("\n-------------------------------------------------\n\n");
	printf("服务器发送的文件已保存到目录%s中!\n",FileName);
	printf("\n-------------------------------------------------\n");

	
	

	printf("\n相关资源已释放!\n");
	closesocket(s);						// 关闭套接字
	WSACleanup();						// 释放套接字库
	return 0;
}

以上。
烦躁。

你可能感兴趣的:(C/C++)