⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 peer.c

📁 计算机网络编程
💻 C
字号:
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <stdlib.h>
#include <arpa/inet.h>
#include <signal.h>
#include <sys/ioctl.h>
#include <net/if.h>
#include <setjmp.h>
#include<time.h>
#define BUFMAX 100
jmp_buf env_alrm;
int pong_sockfd;
struct sockaddr_in pong_addr, recv_addr;
int recv_addr_len;
char recv_buf[BUFMAX], *send_buf = "pres\n";
int recv_len;
char buf[BUFMAX];
void alarm_handler(int signo)
{
    longjmp(env_alrm, 1);
}
int main()
{
	int len1,len2,len3,i,j;
	char ip[50];
	char portnumber[50];
	//产生随机数
    srand((unsigned)time(NULL)); 
    int sockfd;
	struct sockaddr_in target_addr;
    struct sockaddr_in send_addr, bcast_addr;
    int ping_sockfd;
    int on;
    struct sockaddr_in recv_addr;
    int recv_addr_len;
    int recv_len;
    char *send_buf = "ping\n", recv_buf[BUFMAX];
	char buf2[BUFMAX];
	int buflen;
    char *username;
	char *password;
	char port[50];
	int  pong;
	pid_t pid;
	pid_t pid1;
	if ((sockfd = socket(AF_INET, SOCK_STREAM, 0)) < -1) {
		perror("create socket error");
	}
	
	bzero(&target_addr, sizeof(target_addr));
	target_addr.sin_family = AF_INET;
	target_addr.sin_addr.s_addr = inet_addr("127.0.0.1");
	target_addr.sin_port = htons(8000115);
	
	printf("Welcome, hello!\n");
	
	if (connect(sockfd, (struct sockaddr *)&target_addr, sizeof(target_addr)) < -1) {
		perror("connect error");
	}
	memset(buf, '\0', sizeof(buf));
	
	memset(buf2, '\0', sizeof(buf2));
	char buf3[BUFMAX];
    memset(buf3, '\0', sizeof(buf3));
	strcpy(buf3,"LGIN");
	printf("输入用户名: ");
	gets(buf);
	username=buf;
	buflen = strlen(buf);
	buf[buflen]='#';
	printf("输入密码:");
	gets(buf2);
	//加密密码 
	int val=rand()%10;
	int length=strlen(buf2);
	int g;
	for(g=0;g<length;g++){
		buf2[g]=buf2[g]-val;
	}
	password=buf2;
	char d[BUFMAX];memset(d, '\0', sizeof(d));
	d[0]=val+'0';
	strcat(d,buf2);
	strcat(buf,d);
	buflen = strlen(buf);
	buf[buflen]='\n';
	strcat(buf3,buf);
	buflen=sizeof(buf3);//发送登陆的用户名和加密的密码 
	if (write(sockfd, buf3, buflen) != buflen) {
		perror("write error");}
	if ((ping_sockfd = socket(AF_INET, SOCK_DGRAM, 0)) == -1){
		perror("create socket error");}
	
	bzero((char *) &send_addr, sizeof(send_addr));
	send_addr.sin_family = AF_INET;
	send_addr.sin_addr.s_addr = htonl(INADDR_ANY);
	send_addr.sin_port = htons(0);
				
	if (bind(ping_sockfd, (struct sockaddr *) &send_addr, sizeof(send_addr)) < 0) {
		perror("bind socket error");}
		if ((pong_sockfd = socket(AF_INET, SOCK_DGRAM, 0)) < 0) {
        perror("create socket error!");
	}
	int flag=0;
    for (;;) 
	{
		buflen=0;
        memset(buf, '\0', sizeof(buf));
		memset(buf3, '\0', sizeof(buf3));
        memset(buf2, '\0', sizeof(buf2));
        memset(port, '\0', sizeof(port));
        buflen = read(sockfd, buf, BUFMAX);  //登陆成功进行选择分享文件,查找文件,退出等功能
        if((buf[0]=='L')&&(buf[1]=='R')&&(buf[2]=='E')&&(buf[3]=='S'))
		{
			char *ptr;
			ptr=strstr(buf,"S");
            ptr=ptr+1;
			printf("world say: %s", ptr);
			printf("选择a:共享文件;选择b:搜寻文件;选择c:退出\n");
			char choose;
			scanf("%c",&choose); 
			getchar();
			if(choose=='a')//分享文件,分享的端口号,和文件。
			{
				printf("分享文件\n");
				strcpy(buf3,"SHRE");
				printf("输入端口号\n");
				gets(port); 
				buflen=strlen(port);
				port[buflen]='#';
				char ans='y'; //可以选择分享一个或多个文件。
				do
				{
					printf("输入文件名(注意:.txt文件):\n");
					gets(buf);
					strcat(buf2,buf);
					buflen = strlen(buf2);
					buf2[buflen]='#';
					printf("继续分享?,'y'or'Y'继续,'n'or'N'结束\n");
					memset(buf, '\0', sizeof(buf));
					scanf("%c",&ans); 
					getchar();
				}while((ans!='n')&&(ans!='N'));
				buflen = strlen(buf2);
				buf2[buflen-1]='\n';
				strcat(port,buf2);
				strcat(buf3,port);
				printf("%s\n",buf3);
				buflen=strlen(buf3);
				write(sockfd, buf3, BUFMAX) ;
	              break;
			}
			else if(choose=='b')//搜索文件,输入文件名称
			{
				strcpy(buf3,"SRCH");
				printf("搜寻文件:\n");
				printf("输入文件名:\n");
				gets(buf);
				strcat(buf3,buf);
				buflen=strlen(buf3);
				if (write(sockfd, buf3, buflen) != buflen)
				{
					perror("upload file error");
				}
				break;
			}
			else if(choose=='c')//退出 
			{
				strcpy(buf3,"QUIT\n");
				write(sockfd, buf3, BUFMAX) ;
			    close(sockfd);
			    return 0;
			}	
			else
			{
				 close(sockfd);
			    return 0;
			}
	          
		}
		//处理Server端传来的用户名或密码错误信息
		else if((buf[0]=='E')&&(buf[1]=='R')&&(buf[2]=='O')&&(buf[3]=='R'))
		{
            char *ptr;
            ptr=strstr(buf,"EROR");
            ptr=ptr+4;
            printf("%s",ptr);
			close(sockfd);
			return 0;
		}
	}		
	//处理登陆后的信息
	for(;;)
	{
		buflen=0;
        memset(buf, '\0', sizeof(buf));
		memset(buf3, '\0', sizeof(buf3));
        memset(buf2, '\0', sizeof(buf2));
        memset(port, '\0', sizeof(port));
        buflen = read(sockfd, buf, BUFMAX);  
		//处理上传成功后的信息,提供给client选择三种功能
	    if((buf[0]=='S')&&(buf[1]=='H')&&(buf[2]=='O')&&(buf[3]=='K'))
		{
			memset(buf, '\0', sizeof(buf));
            printf("上传文件成功\n");
			printf("选择a:共享文件;选择b:搜寻文件;选择c:退出\n");
			char choose;
			scanf("%c",&choose); 
			getchar();
			if(choose=='a')
			{
				printf("分享文件\n");
				strcpy(buf3,"SHRE");
				printf("输入端口号\n");
				gets(port); 
				buflen=strlen(port);
				port[buflen]='#';
				char ans='y'; 
				do
				{
					printf("输入文件名(注意:.txt文件):\n");
					gets(buf);
					strcat(buf2,buf);
					buflen = strlen(buf2);
					buf2[buflen]='#';
					printf("继续分享?,'y'or'Y'继续,'n'or'N'结束\n");
					memset(buf, '\0', sizeof(buf));
					scanf("%c",&ans); 
					getchar();
				}while((ans!='n')&&(ans!='N'));
				buflen = strlen(buf2);
				buf2[buflen-1]='\n';
				strcat(port,buf2);
				strcat(buf3,port);
				printf("%s\n",buf3);
				buflen=strlen(buf3);
				write(sockfd, buf3, BUFMAX) ;
			}
			
			else if(choose=='b')
			{
				strcpy(buf3,"SRCH");
				printf("搜寻文件:\n");
				printf("输入文件名:\n");
				gets(buf);
				strcat(buf3,buf);
				buflen=strlen(buf3);
				if (write(sockfd, buf3, buflen) != buflen)
				{
					perror("upload file error");
				}
			}
			else if(choose=='c')
			{
				strcpy(buf3,"QUIT\n");
				write(sockfd, buf3, BUFMAX) ;
              	close(sockfd);
				return 0;
			}		

			
		}
		//处理出错信息
       	else if((buf[0]=='E')&&(buf[1]=='R')&&(buf[2]=='O')&&(buf[3]=='R'))
		{
            char *ptr;
            ptr=strstr(buf,"EROR");
            ptr=ptr+4;
            printf("%s",ptr);
			break;
		}
		//处理搜索到所有的文件的结束标志。提供三种选择
		else if((buf[0]=='S')&&(buf[1]=='R')&&(buf[2]=='E')&&(buf[3]=='S')&&(buf[4]=='\n'))
		{
	
			memset(buf, '\0', sizeof(buf));
            printf("查找文件完成\n");

			printf("选择a:共享文件;选择b:搜寻文件;c:退出\n");
			char choose;
			scanf("%c",&choose); 
			getchar();
			
			if(choose=='a')
			{
				printf("分享文件:\n");
				strcpy(buf3,"SHRE");
				printf("输入端口号:\n");
				gets(port);
				buflen=strlen(port);
				port[buflen]='#';
				char ans='y'; 
				do
				{
					printf("输入文件名(注意:.txt文件):\n");
					gets(buf);
					strcat(buf2,buf);
					buflen = strlen(buf2);
					buf2[buflen]='#';
					printf("继续分享?,'y'or'Y'继续,'n'or'N'结束\n");
					memset(buf, '\0', sizeof(buf));
					scanf("%c",&ans); 
					getchar();
				}while((ans!='n')&&(ans!='N'));
				buflen = strlen(buf2);
				buf2[buflen-1]='\n';
				strcat(port,buf2);
				strcat(buf3,port);
				printf("%s\n",buf3);
				buflen=strlen(buf3);
				write(sockfd, buf3, BUFMAX) ;
				
			}
			
			else if(choose=='b')
			{
				strcpy(buf3,"SRCH");
				printf("搜寻文件:\n");
				printf("输入文件名:\n");
				gets(buf);
				strcat(buf3,buf);
				buflen=strlen(buf3);
				if (write(sockfd, buf3, buflen) != buflen)
				{
					perror("upload file error");
				}
				
			}
             else if(choose=='c')
			{
				strcpy(buf3,"QUIT\n");
				write(sockfd, buf3, BUFMAX) ;
			    close(sockfd);
			    return 0;
			}	
			
		}
		//多进程PING的过程
		else if((buf[0]=='S')&&(buf[1]=='R')&&(buf[2]=='E')&&(buf[3]=='S'))
		{
				memset(ip, '\0', sizeof(ip));
				memset(portnumber , '\0', sizeof(port));
				char *ptr;
				ptr=strstr(buf,"SRES");
				ptr=ptr+4;
				char *print=ptr;
				ptr=strstr(ptr,"#");
				ptr=ptr+1;	
				ptr=strstr(ptr,"#");
				ptr=ptr+1;
				len1=strlen(ptr);
				char *str;
				str=strstr(ptr,"#");
				len2=strlen(str);	
				strncpy(ip,ptr,len1-len2);
				char *a;
				str=str+1;
				a=strstr(str,"#");
				len3=strlen(a);
				strncpy(portnumber,str,len2-len3-1);			
				bzero((char *) &recv_addr, sizeof(recv_addr));
				recv_addr.sin_family = AF_INET;
				recv_addr.sin_addr.s_addr = inet_addr(ip);
				int g; 
				int len=strlen(portnumber);
				int val=10;
				int total=0;
				for(i=0;i<len;i++)
				{
					g=portnumber[i]-'0';
					for(j=len-i-1;j>=1;j--)
					{
						g=g*10;
					}
					total=total+g;
					
				}
				recv_addr.sin_port = htons(total);
				pong=0;
				//多进程PING,PING到文件所在的端口上。但只有7000的端口在监听。
				pid= fork();
				if(pid>0){}
				else if(0==pid)//建立UDP
				{
					if (sendto(ping_sockfd, send_buf, strlen(send_buf), 0, (struct sockaddr *) &recv_addr, sizeof(recv_addr)) < 0) {
						perror("sendto error"); 
					}
					
					signal(SIGALRM, alarm_handler);
					
					alarm(5);
					for(;;)
					{
						if (setjmp(env_alrm) != 0) {
							break;
						}//提供时间限制。
						
						bzero((char *) &recv_addr, sizeof(recv_addr));
						
						recv_len = recvfrom(ping_sockfd, recv_buf, BUFMAX, 0, (struct sockaddr *) &recv_addr, &recv_addr_len);
						recv_buf[recv_len] = '\0';
						if (0 == strcmp(recv_buf, "pres\n")) {
							printf("找到文件的位置:\n");	
							printf("%s",print);
							printf("pong\n");
							pong = 1;
							
						}   
						
						
					}
			
					if (!pong) {
						printf("找到文件的位置:\n");	
						printf("%s",print);						
						printf("time out!\n");
						printf("not pong\n");
					}  
		
				}

		}  
		
    }
	close(sockfd);
	
    return 0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -