1、機械臂
#include <myhead.h>
#define SER_IP "192.168.125.32" //服務器端IP
#define SER_PORT 8888 //服務器端端口號#define CLI_IP "192.168.68.148" //客戶端IP
#define CLI_PORT 9999 //客戶端端口號
/**********************TCP客戶端********************/
int main(int argc, const char *argv[])
{//1.創建用于通信的套接字int cfd=-1;if((cfd=socket(AF_INET,SOCK_STREAM,0))==-1){perror("socket error");return -1;}printf("cfd=%d\n",cfd);//將端口號快速重用int reuse = 1;if(setsockopt(cfd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)) == -1){perror("reuse error");return -1;}printf("reuse success\n");//2.綁定服務器IP地址和端口號(非必須)//2.1填充地址信息結構體struct sockaddr_in cin;cin.sin_family=AF_INET;cin.sin_port=htons(CLI_PORT);cin.sin_addr.s_addr=inet_addr(CLI_IP);//2.2綁定if(bind(cfd,(struct sockaddr*)&cin,sizeof(cin))==-1){perror("bind error");}printf("bind success\n");//3.連接服務器//3.1填充要連接的服務器的地址信息結構體struct sockaddr_in sin;sin.sin_family=AF_INET;sin.sin_port=htons(SER_PORT);sin.sin_addr.s_addr=inet_addr(SER_IP);//3.2連接到服務器if(connect(cfd,(struct sockaddr*)&sin,sizeof(sin))==-1){perror("connect error");return -1;}//4.進行數據的收發操作char rbuf[5]={0xff,0x02,0x00,0x00,0xff}; //紅色機械臂unsigned char bbuf[5]={0xff,0x02,0x01,0x00,0xff}; //藍色機械臂//發送給服務器當做初始值send(cfd,rbuf,sizeof(rbuf),0);sleep(1); //防止沾包send(cfd,bbuf,sizeof(bbuf),0);char key=0; //定義鍵盤輸入的值while(1){scanf("%c",&key); getchar(); //吸收垃圾字符switch(key){case 'w':{rbuf[3] += 2; //紅色機械臂每次增加3度if(rbuf[3]>=90){rbuf[3]=90;}send(cfd,rbuf,sizeof(rbuf),0); //將鍵盤控制的結果發送到服務器端}break;case 's':{rbuf[3] -= 2; if(rbuf[3]<=-90){rbuf[3]=-90;}send(cfd,rbuf,sizeof(rbuf),0);}break;case 'd':{bbuf[3]+=2; if(bbuf[3]>=180){bbuf[3]=180;}send(cfd,bbuf,sizeof(bbuf),0);}break;case 'a':{bbuf[3]+=2; if(bbuf[3]<=0){bbuf[3]=0;}send(cfd,bbuf,sizeof(bbuf),0);}break;default:printf("error\n");break;}}//5.關閉套接字close(cfd);return 0;
}
2、基于UDP的tftp通信
#include<myhead.h>
#define SER_IP "192.168.125.32"
#define SER_PORT 69//定義下載函數
int download(int cfd, struct sockaddr_in sin)
{//組件協議包:下載請求char pack[516]="";short *p1 = (short *)pack;*p1 = htons(1); //設置操作碼char *p2 = pack+2;char file[20] = "";printf("請輸入要下載的文件名:");fgets(file, sizeof(file), stdin);file[strlen(file)-1] = 0;strcpy(p2, file); //文件名char *p4 = p2 +strlen(p2) + 1;strcpy(p4, "octet"); //模式位int packlen = 4 + strlen(p2) + strlen(p4); //請求包的大小//向服務器發送請求包sendto(cfd, pack ,packlen,0, (struct sockaddr*)&sin, sizeof(sin));struct sockaddr_in cin;socklen_t socklen = sizeof(cin); //計算客戶端地址信息結構體的大小//打開文件int wfd = -1;if((wfd = open(file,O_WRONLY|O_CREAT|O_TRUNC,0664)) == -1){perror("open error");return -1;}while(1){//收取服務器發來的數據包//清空協議包bzero(pack, sizeof(pack));int res = recvfrom(cfd, pack, sizeof(pack), 0, (struct sockaddr*)&cin,&socklen);//判斷操作碼是否為3 以及數據包數據內容是否為512字節if(*p1 == ntohs(3)){//將數據包寫入文件write(wfd, pack+4, res-4);//回復一個應答包sendto(cfd, pack, 4, 0,(struct sockaddr*)&cin, sizeof(cin));//若數據內容小于512字節,讀取數據后結束接受數據if(res-4 < 512){printf("download success\n");break;}}else if(*p1 == ntohs(5)){printf("error\n");break;}}//關閉文件close(wfd);return 0;}
int upload(int cfd,struct sockaddr_in sin)
{//組件協議包:下載請求char pack[516]="";short *p1 = (short *)pack;*p1 = htons(1); //設置操作碼char *p2 = pack+2;char file[20] = "";printf("請輸入要下載的文件名:");fgets(file, sizeof(file), stdin);file[strlen(file)-1] = 0;strcpy(p2, file); //文件名char *p4 = p2 +strlen(p2) + 1;strcpy(p4, "octet"); //模式位int packlen = 4 + strlen(p2) + strlen(p4); //請求包的大小//向服務器發送請求包sendto(cfd, pack ,packlen, 0, (struct sockaddr*)&sin, sizeof(sin));struct sockaddr_in cin;socklen_t socklen = sizeof(cin); //計算客戶端地址信息結構體的大小//以只讀的方式打開文件int rfd = -1;if((rfd = open(file,O_RDONLY|O_CREAT|O_TRUNC,0664)) == -1){perror("open error");return -1;}//定義一個塊編號short num = 0;while(1){//清空協議包bzero(pack,sizeof(pack));//接受服務器發來的應答包int res = recvfrom(cfd,pack,sizeof(pack),0,(struct sockaddr*)&cin,&socklen);if(*p1 == ntohs(4)){//發送一個數據包*p1 = htons(3);num++;*(p1 + 1) = htons(num);//讀取數據res = read(rfd, p1+2,512);sendto(cfd, pack, sizeof(pack),0,(struct sockaddr*)&cin,sizeof(cin));if(res == 0){printf("upload success\n");break;}}//判斷是否為錯誤包else if(*p1 == ntohs(5)){printf("error\n");return -1;}}close(rfd);return 0;
}
int main(int argc, const char *argv[])
{//創建用于通信的套接字int cfd = socket(AF_INET, SOCK_DGRAM, 0);if(cfd == -1){perror("socket error");return -1;}//2、收發數據//填充服務器的地址信息結構體struct sockaddr_in sin;sin.sin_family = AF_INET;sin.sin_port = htons(SER_PORT);sin.sin_addr.s_addr = inet_addr(SER_IP);int key = 0;while(1){system("clear");printf("\t************1、下載**********\t\n");printf("\t************2、上傳**********\t\n");printf("\t************3、退出**********\t\n");printf("請輸入要執行的功能:");scanf("%d",&key);getchar();switch(key){case 1:{download(cfd,sin);}break;case 2:{upload(cfd,sin);}case 3:{goto END;}break;default:printf("error\n");break;}}
END://關閉套接字close(cfd);return 0;
}
思維導圖: