1. 程式人生 > >linux socket程式設計示例

linux socket程式設計示例

===============================================

=======server.c==================================

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>
#include <dirent.h>
#include <sys/types.h>          /* See NOTES */
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <errno.h>


#define N 128


typedef struct sockaddr SA;




void ProcessList(int connfd)
{
char buf[N];
DIR *mydir;
struct dirent *myitem;


mydir = opendir(".");
while ((myitem = readdir(mydir)) != NULL)
{
if ((strcmp(myitem->d_name, ".") == 0) || (strcmp(myitem->d_name, "..") == 0)) continue;
strcpy(buf, myitem->d_name);
send(connfd, buf, N, 0);
}
closedir(mydir);


return;
}




void ProcessGet(int connfd, char buf[])
{
int fd, nbyte;


if ((fd = open(buf+1, O_RDONLY)) < 0)
{
fprintf(stderr, "fail to open %s : %s\n", buf+1, strerror(errno));
buf[0] = 'N';
send(connfd, buf, N, 0);
return;
}

buf[0] = 'Y';
send(connfd, buf, N, 0);
while ((nbyte = read(fd, buf, N)) > 0)
{
send(connfd, buf, nbyte, 0);
}
close(fd);


return;
}




void ProcessPut(int connfd, char buf[])
{
int fd, nbyte;


if ((fd = open(buf+1, O_WRONLY|O_CREAT|O_TRUNC, 0666)) < 0)
{
printf("fail to create %s on server\n", buf+1);
return;
}


while ((nbyte = recv(connfd, buf, N, 0)) > 0)
{
write(fd, buf, nbyte);
}
close(fd);


return;
}




int main(int argc, char *argv[])
{
   int listenfd, connfd;
char buf[N];
   struct sockaddr_in server_addr;


  // XXX:step 1  int socket(int domain, int type, int protocol);
   if ((listenfd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
   {
      fprintf(stderr, "fail to socket : %s\n", strerror(errno));
      exit(-1);
   }
#ifdef _DEBUG_
   printf("socket is %d\n", listenfd);
#endif  


  // XXX:step 2  int bind(int sockfd, const struct sockaddr *serv_addr, socklen_t addrlen);
   memset(&server_addr, 0, sizeof(server_addr));
   server_addr.sin_family = PF_INET;
   server_addr.sin_port = htons(7008);
   //server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
   server_addr.sin_addr.s_addr = INADDR_ANY;
if (bind(listenfd, (SA *)&server_addr, sizeof(server_addr)) < 0)
{
perror("fail to bind");
exit(-1);
}


listen(listenfd, 5);
  
   while ( 1 )
{
if ((connfd = accept(listenfd, NULL, NULL)) < 0)
{
perror("fail to accept");
break;
}
recv(connfd, buf, N, 0);
switch (buf[0])
{
case 'L' :
ProcessList(connfd);
break;
case 'G' :
ProcessGet(connfd, buf);
break;
case 'P' :
ProcessPut(connfd, buf);
break;
}
close(connfd);
}


   return 0;
}

=============================================================

=========client.c===============================================

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <fcntl.h>
#include <sys/types.h>          /* See NOTES */
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <errno.h>




//#include <string.h>
//#include <netdb.h>


#define N 128


typedef struct sockaddr SA;




void PrintHelp()
{
   printf("help : display help info\n");
   printf("list : get file list of server\n");
   printf("get  : get <file>\n");
   printf("put  : put <file>\n");
printf("quit : quit the client\n");


return;
}




void ProcessList(struct sockaddr_in server_addr)
{
 int sockfd, nbyte;
char buf[N];


if ((sockfd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
{
printf("fail to list\n");
return;
}


if (connect(sockfd, (SA *)&server_addr, sizeof(server_addr)) < 0)
   {
      printf("fail to connect server\n");
goto ERROR_1;
   }


strcpy(buf, "L");
send(sockfd, buf, N, 0);
   while ((nbyte = recv(sockfd, buf, N, 0)) != 0)
{
printf("%s\n", buf);
}


ERROR_1:
close(sockfd);
   
return;
}




void ProcessGet(struct sockaddr_in server_addr, char command[])
{
int sockfd, nbyte, fd;
   char buf[N];


if ((sockfd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
{
  printf("fail to get\n");
return;
}


if (connect(sockfd, (SA *)&server_addr, sizeof(server_addr)) < 0)
   {
      printf("fail to connect server\n");
goto ERROR_2;
       
   }


sprintf(buf, "G%s", command+4);
send(sockfd, buf, N, 0);
   recv(sockfd, buf, N, 0);
if (buf[0] == 'N') // no such file
{
printf("No such file on server\n");
goto ERROR_2;
}


   if ((fd = open(command+4, O_WRONLY|O_CREAT|O_TRUNC, 0666)) < 0)
{
  printf("fail to create local file %s\n", command+4);
goto ERROR_2;
}
 
while ((nbyte = recv(sockfd, buf, N, 0)) > 0)
{
write(fd, buf, nbyte);
}
close(fd);


ERROR_2:
close(sockfd);


return;
}




void ProcessPut(struct sockaddr_in server_addr, char command[])
{
int sockfd, fd, nbyte;
char buf[N];


   if ((sockfd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
{
  printf("fail to get\n");
return;
}


if (connect(sockfd, (SA *)&server_addr, sizeof(server_addr)) < 0)
   {
      printf("fail to connect server\n");
goto ERROR_3;
       
   }


   if ((fd = open(command+4, O_RDONLY)) < 0)
{
printf("fail to open %s\n", command+4);
goto ERROR_3;

sprintf(buf, "P%s", command+4);
send(sockfd, buf, N, 0);


while ((nbyte = read(fd, buf, N)) > 0)
{
send(sockfd, buf, nbyte, 0);
}
close(fd);


ERROR_3:
close(sockfd);


return;
}




int main(int argc, char *argv[])
{
   int sockfd, fd, nbyte;
   char command[32];
   struct sockaddr_in server_addr;
   
   //struct hostent *he;


   if (argc < 3)
{
printf("Usage : %s <server_ip> : <port>\n", argv[0]);
exit(-1);
}
  
  // XXX:step 1  int socket(int domain, int type, int protocol);
   if ((sockfd = socket(PF_INET, SOCK_STREAM, 0)) < 0)
   {
      fprintf(stderr, "fail to socket : %s\n", strerror(errno));
      exit(-1);
   }
#ifdef _DEBUG_
   printf("socket is %d\n", sockfd);
#endif  
/*  取得主機資訊 */
//if ((he=gethostbyname(argv[1])) == NULL)
//{
/*  如果gethostbyname()發生錯誤,則顯示錯誤資訊並退出 */
//herror("gethostbyname");
//exit(1);
//}
  // XXX:step 2  int connect(int sockfd, const struct sockaddr *serv_addr, socklen_t addrlen);
   memset(&server_addr, 0, sizeof(server_addr));
   server_addr.sin_family = PF_INET;
   server_addr.sin_port = htons(atoi(argv[2]));
   //server_addr.sin_port = htons(4000);
   server_addr.sin_addr.s_addr = inet_addr(argv[1]);
   //server_addr.sin_addr = *((struct in_addr *)he->h_addr);
   //server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
  

  
   while ( 1 )
{
      printf("<client> ");
fgets(command, 32, stdin);
command[strlen(command)-1] = '\0';  // overwrite the '\n' 
if (strcmp(command, "help") == 0)
{
  PrintHelp();
}
else if (strcmp(command, "list") == 0)
{
ProcessList(server_addr);
}
else if (strncmp(command, "get ", 4) == 0)
{
ProcessGet(server_addr, command);
}
else if (strncmp(command, "put ", 4) == 0)
{
ProcessPut(server_addr, command);
}
else if (strcmp(command, "quit") == 0)
{
printf("Bye\n");
break;
}
else
{
printf("wrong command, 'help' for command list\n");
}
}


   return 0;
}