linux简单的TCP与UDP的socket程序以及机器大小端的判断程序

分类: linux编程 C/C++随笔 149人阅读 评论(0) 收藏 举报

本文只是总结一下linux下tcp与udp程序的编写,其实不管平台如何,简单的tcp与udp程序的结构还是不会变的。如下所示:



linux简单的TCP与UDP的socket程序以及机器大小端的判断程序_第1张图片

tcp(基于链接)的简单程序结构

linux简单的TCP与UDP的socket程序以及机器大小端的判断程序_第2张图片

udp(无连接)的程序结构

过程不在赘述,看看一个基于上面过程的简单udp代码:

udpserver.c

[cpp] view plain copy print ?
  1. #include<stdlib.h>   
  2. #include<stdio.h>   
  3. #include<string.h>   
  4. #include<sys/types.h>   
  5. #include<sys/socket.h>   
  6. #include<netinet/in.h>   
  7. #include<netdb.h>   
  8.   
  9.   
  10. #define PORT 8900   
  11.   
  12.   
  13. int main()  
  14. {  
  15.   
  16.     int sockfd;  
  17.     struct sockaddr_in server;  
  18.     struct sockaddr_in client;  
  19.     char send_buf[2048];  
  20.     char recv_buf[2048];  
  21.     int length;  
  22.     int sendnum;  
  23.     int recvnum;  
  24.     int port;  
  25.   
  26.   
  27.     port = PORT;  
  28.     int opt = SO_REUSEADDR;  
  29.       
  30.   
  31.   
  32. /*The first stage:initnial phase*/  
  33.   
  34. /*1.1 generating socket  phrahse*/  
  35.   
  36.     if (-1==(sockfd=socket(AF_INET,SOCK_DGRAM,0)))  
  37.     {  
  38.         perror("error in generate socket\n");  
  39.         exit(1);  
  40.   
  41.     }  
  42.   
  43.     #ifdef DEBUG   
  44.         printf("the sokcet id is %d\n",sockfd);  
  45.         printf("enter binding phrase....\n");  
  46.     #endif   
  47.     setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,&opt,sizeof(opt));  
  48.   
  49. /*1.2 binding the socket*/  
  50.   
  51.     memset(&server,0,sizeof(struct sockaddr));  
  52.     server.sin_family = AF_INET;  
  53.     server.sin_addr.s_addr = htonl(INADDR_ANY);  
  54.     server.sin_port = htons(port);  
  55.   
  56.     if (-1==bind(sockfd,(struct sockaddr*)&server,sizeof(struct sockaddr)))  
  57.     {  
  58.         perror("error in binding phrase\n");  
  59.         close(sockfd);  
  60.         exit(1);  
  61.   
  62.     }  
  63.   
  64.   
  65.     #ifdef DEBUG   
  66.         printf("leaving binding phrase\n");  
  67.         printf("entering data exchange phrase\n");  
  68.     #endif   
  69.   
  70.     length = sizeof(struct sockaddr_in);   
  71.   
  72. /* The Second Stage: data exchange phrase */  
  73.     while(1)  
  74.     {  
  75.         memset(&send_buf,0,sizeof(send_buf));  
  76.         memset(&recv_buf,0,sizeof(recv_buf));  
  77.           
  78.         /* receive the data from the client*/  
  79.   
  80.         recvnum=recvfrom(sockfd,recv_buf,sizeof(recv_buf),0,(struct sockaddr*)&client,&length);  
  81.       
  82.         recv_buf[recvnum]='\0';  
  83.         printf("the message from the client is %s:\n",recv_buf);  
  84.       
  85.   
  86.         sendnum = sprintf(send_buf,"hello,the guest from %s",inet_ntoa(client.sin_addr));  
  87.         sendto(sockfd,send_buf,sendnum,0,(struct sockaddr*)&client,sizeof(struct sockaddr));  
  88.   
  89.         if (0==strcmp(recv_buf,"quit"))  
  90.         {  
  91.             perror("the server is terminted by client\n");  
  92.             close(sockfd);  
  93.             return 0;  
  94.               
  95.               
  96.         }  
  97.   
  98.     }  
  99.   
  100.       
  101.       
  102. }  


udpclient.c

[cpp] view plain copy print ?
  1. #include<stdlib.h>   
  2. #include<stdio.h>   
  3. #include<string.h>   
  4. #include<sys/types.h>   
  5. #include<sys/socket.h>   
  6. #include<netinet/in.h>   
  7. #include<netdb.h>   
  8.   
  9.   
  10. void print_usage(char* str)  
  11. {  
  12.     printf("the command %s usage is:\n",str);  
  13.     printf("%s Ip_Address [port] \n");  
  14.   
  15. }  
  16.   
  17.   
  18.   
  19.   
  20. int main(int argc,char**argv)  
  21. {  
  22.   
  23.     int sockfd;  
  24.     struct sockaddr_in server;  
  25.     struct sockaddr_in reply;  
  26.     char send_buf[2048];  
  27.     char recv_buf[2048];  
  28.     int length;  
  29.     int sendnum;  
  30.     int recvnum;  
  31.     int port;  
  32.   
  33.     port =  atoi(argv[2]);  
  34.   
  35.   
  36.     if ((2>argc) ||(argc>3))  
  37.     {  
  38.         print_usage(argv[0]);  
  39.         exit(1);  
  40.   
  41.   
  42.     }  
  43.   
  44. /*The first stage:initnial phase*/  
  45.   
  46. /*1.1 generating socket  phrahse*/  
  47.   
  48.     if (-1==(sockfd=socket(AF_INET,SOCK_DGRAM,0)))  
  49.     {  
  50.         perror("error in generate socket\n");  
  51.         exit(1);  
  52.   
  53.     }  
  54.   
  55.     #ifdef DEBUG   
  56.         printf("the sokcet id is %d\n",sockfd);  
  57.         printf("enter data exchange  phrase....\n");  
  58.     #endif   
  59.   
  60. /*1.2 setting the destinate address */  
  61.   
  62.     memset(&server,0,sizeof(struct sockaddr));  
  63.     server.sin_family = AF_INET;  
  64.     server.sin_addr.s_addr = inet_addr(argv[1]);  
  65.     server.sin_port = htons(port);  
  66.   
  67.   
  68. /* The Second Stage: data exchange phrase */  
  69.       
  70.     memset(&send_buf,0,sizeof(send_buf));  
  71.     memset(&recv_buf,0,sizeof(recv_buf));  
  72.   
  73.     printf("what words do you want to tell to server:\n");  
  74.     gets(send_buf);  
  75.       
  76.           
  77.     /* send  the data to the server*/  
  78.       
  79.     sendnum = strlen(send_buf);  
  80.     if(0>sendto(sockfd,send_buf,sendnum,0,(struct sockaddr*)&server,sizeof(struct sockaddr)))  
  81.     {  
  82.         perror("send data error\n");  
  83.         close(sockfd);  
  84.         exit(0);  
  85.     }  
  86.       
  87.     recvnum = recvfrom(sockfd,recv_buf,sizeof(recv_buf),0,(struct sockaddr *)&server,&length);  
  88.       
  89.     if (0>recvnum)  
  90.     {  
  91.           
  92.         perror("receive data error\n");  
  93.         close(sockfd);  
  94.         exit(0);  
  95.     }     
  96.   
  97.     recv_buf[recvnum]='\0';  
  98.     printf("the message from the server is :%s\n",recv_buf);  
  99.   
  100.     close(sockfd);  
  101.     exit(0);  
  102. }  

以上即完成了简单的udp程序。另一个tcp程序在 此处下载。同样比较简单,不解释!

在文章后面说一下大小端(big endian于little endian)的问题吧,相信大家都知道大小端到底使什么东西,这里也不多说,现在要提到的是如何如何编程实现判断所用机器是大端机器还是小端机器。我们知道,在C语言中,union中的字段是“共享内存”的,在一个union结构中,它的大小取决于其字段中最大的那个并且与之相等。其实想到这儿相信大家都已经知道了怎么来判断机器的大小端了,没错,就是使用union类型的特点进行判断。现在就基于C中的union写一个判断机器是大小端的程序。如下:

[cpp] view plain copy print ?
  1. #include<stdio.h>   
  2.   
  3. union Nate  
  4. {  
  5.     unsigned short s;  
  6.     char cs[2];  
  7. }nate;  
  8.   
  9. void main()  
  10. {  
  11.     nate.s = 1;  
  12.     printf("nate.s is : %x\n",nate.s);  
  13.     printf("nate.cs[0] is : %d\n",nate.cs[0]);  
  14.     printf("nate.cs[1] is : %d\n",nate.cs[1]);  
  15.     if(nate.cs[0] == 1)  
  16.     {  
  17.         printf("little endian!\n");  
  18.     }  
  19.     else if(nate.cs[0] == 0)  
  20.     {  
  21.         printf("big endian!\n");  
  22.     }  
  23. }  

在gcc中编译运行程序即可看到本机器是大端还是小端了!这可以说是使用C中union的特性的一个好的应用,对于理解C中union类型也不错!

文中包含程序在此处可以下载:http://download.csdn.net/detail/Natepan/3636259

你可能感兴趣的:(linux,socket,struct,server,tcp,Exchange,Linux编程,C/C++随笔)