Server端
#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <string.h>
#include <netinet/in.h>
#define SERVPORT 4444
#define BACKLOG 10
#define MAXDATASIZE 1024
int main() {
struct sockaddr_in server_sockaddr;//声明服务器socket存储结构
int sin_size,recvbytes;
int sockfd,client_fd;//socket描述符
char buf[MAXDATASIZE];//传输的数据
//1.建立socket
//AF_INET 表示IPV4
//SOCK_STREAM 表示TCP
if((sockfd = socket(AF_INET,SOCK_STREAM,0)) < 0) {
perror("Socket");
exit(1);
}
printf("Socket successful!,sockfd=%d\n",sockfd);
//以sockaddt_in结构体填充socket信息
server_sockaddr.sin_family = AF_INET;//IPv4
server_sockaddr.sin_port = htons(SERVPORT);//端口
server_sockaddr.sin_addr.s_addr = INADDR_ANY;//本主机的任意IP都可以使用
bzero(&(server_sockaddr.sin_zero),8);//保留的8字节置零
int so_reuseaddr = 1;
setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,&so_reuseaddr,sizeof(so_reuseaddr));
//2.绑定 fd与 端口和地址
if((bind(sockfd,(struct sockaddr *)&server_sockaddr,sizeof(struct sockaddr))) < 0) {
perror("bind");
exit(-1);
}
printf("bind successful !\n");
//3.监听
if(listen(sockfd,BACKLOG) < 0) {
perror("listen");
exit(1);
}
printf("listening ... \n");
while(1){
//4.接收请求,函数在有客户端连接时返回一个客户端socket fd,否则则阻塞
//优化:这里同样可以使用select,以及poll来实现异步通信
if((client_fd = accept(sockfd,NULL,&sin_size)) == -1) {
perror("accept");
exit(1);
}
printf("accept success! client_fd:%d\n",client_fd);
FILE *pFile = fopen("recv.dat","wb+");
//5.接收数据
//注意:这里传入的fd,不是建立的socket fd,而是accept返回的连接客户端 socket fd
while(1)
{
if((recvbytes = recv(client_fd,buf,MAXDATASIZE,0)) == -1) {
perror("recv");
//exit(1);
break;
}
printf("the recv buf size is %d\n",recvbytes);
if(recvbytes > 0)
{
fwrite(buf,1,recvbytes,pFile);
fflush(pFile);
}
else
{
printf("break from the recv\n");
break;
}
}
fclose(pFile);
//printf("received data : %s\n",buf);
}
//6.关闭
close(sockfd);
}
=========================================================================
Client端
#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <unistd.h>
#include <string.h>
#include <netdb.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#define SERVPORT 4444
int main(int argc,char *argv[]) {
int sockfd,sendbytes;
struct sockaddr_in serv_addr;//需要连接的服务器地址信息
if(argc < 4){
printf("Usage: %s <server_ip> <port-default is 4444> <filename>\n",argv[0]);
exit(-1);
}
//1.创建socket
//AF_INET 表示IPV4
//SOCK_STREAM 表示TCP
if((sockfd = socket(AF_INET,SOCK_STREAM,0)) < 0) {
perror("socket");
exit(1);
}
int port = atoi(argv[2]);
char *ip = argv[1];
if(!ip)
{
printf("recv an error ip\n");
return -1;
}
printf("the server ip is %s, the port is %d\n",ip,port);
//填充服务器地址信息
serv_addr.sin_family = AF_INET; //网络层的IP协议: IPV4
serv_addr.sin_port = htons(port); //传输层的端口号
serv_addr.sin_addr.s_addr = inet_addr(ip); //网络层的IP地址: 实际的服务器IP地址
bzero(&(serv_addr.sin_zero),8); //保留的8字节置零
if((connect(sockfd,(struct sockaddr *)&serv_addr,sizeof(struct sockaddr))) < 0) {
perror("connect failed!");
exit(1);
}
printf("connect successful! \n");
char *filename = argv[3];
if(!filename)
{
printf("recv an error filename\n");
return -1;
}
FILE *pFile = fopen(filename,"rb");
if(!pFile)
{
printf("recv an error filename\n");
return -1;
}
char msg[1024];
while(!feof(pFile))
{
int ret = fread(msg,1,1024,pFile);
if(ret < 1024)
{
if(ret > 0)
{
sendbytes = send(sockfd,msg,ret,0);
if(sendbytes < 0)
{
break;
}
}
}
else
{
sendbytes = send(sockfd,msg,ret,0);
if(sendbytes < 0)
{
break;
}
printf("send data length is %d\n",sendbytes);
usleep(1000);
}
}
fclose(pFile);
printf("send %s successful! %d \n",filename,sendbytes);
usleep(10000);
//4.关闭
close(sockfd);
printf("exit this program\n");
return 0;
}