编写一个简陋的tcp协议server与client(无fork)
注释写在服务器端了,用户端的就懒得写了
tcp_ser.c
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <unistd.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <string.h>
#define ERR_MSG(msg) do{\
printf("line %d\n",__LINE__);\
perror(msg);\
return -1;\
}while(0)
#define SUC_MSG(msg) do{\
printf("%s success\n",msg);\
}while(0)
#define PORT 1991
#define IP "192.168.10.23"
int main(int argc, const char *argv[])
{
//create the socket
int sfd = socket(AF_INET,SOCK_STREAM,0);
if(sfd < 0){
ERR_MSG("socket");
}
//man 2 bind
//man 7 ip
//the actual structure passed for the second argument of bind method will be
//depend on the address family
//in this case,it will be AF_INET,aka ipv4
//the actual one should be (after checking manual) struct sockaddr_in.
//we define a variable in struct sockaddr_in then convert it into
//struct sockaddr
struct sockaddr_in sin;
sin.sin_family = AF_INET; //address family
sin.sin_port = htons(PORT); //port in network byte order
sin.sin_addr.s_addr = inet_addr(IP); //internet address(in network byte order)
//bind the sockaddr with the sfd
if(bind(sfd,(struct sockaddr*)&sin,sizeof(struct sockaddr_in)) < 0){
ERR_MSG("bind");
}
printf("bind success\n");
//mark the socket sfd as the one specifically used on listening
if(listen(sfd,128) < 0){
ERR_MSG("listen\n");
}
SUC_MSG("listen");
//create a new sockaddr_in structrue to store the client sock address info
struct sockaddr_in cin;
socklen_t len = sizeof(cin);
//create a new file descriptor to be actually communicated with
int newfd = accept(sfd,(struct sockaddr*)&cin,&len);
if(newfd < 0){
ERR_MSG("accept");
}
SUC_MSG("accept");
printf("[%s:%d]Client is successfully connected. newfd = %d\n",inet_ntoa(cin.sin_addr),ntohs(cin.sin_port),newfd);
char buf[128];
while(1){
bzero(buf,sizeof(buf));
//receive data
int res = recv(newfd,buf,sizeof(buf),0);
if(res < 0){
ERR_MSG("recv");
}
else if(res == 0)
{
printf("Client offline\n");
break;
}
SUC_MSG(buf);
//send data
strcat(buf," is received\n");
res = send(newfd,buf,sizeof(buf),0);
if(res < 0){
ERR_MSG("send");
}
}
//close the socket
if(close(sfd) < 0){
ERR_MSG("close");
}
return 0;
}
tcp_cli.c
#include <stdio.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <signal.h>
#include <string.h>
#include <unistd.h>
#define ERR_MSG(msg) do{\
perror(msg);\
return -1;\
}while(0)
#define SUC_MSG(msg) do{\
printf("%s success\n",msg);\
}while(0)
#define PORT 1997
#define IP "192.168.10.23"
#define SERVERPORT 1991
#define SERVERIP "192.168.10.23"
static int *ifAlarm = NULL;
void handler(int signal){
*ifAlarm = signal;
}
int main(int argc, const char *argv[])
{
int myAlarm = 0;
ifAlarm = &myAlarm;
if(signal(14,handler) == SIG_ERR){
ERR_MSG("signal");
}
int sfd = socket(AF_INET,SOCK_STREAM,0);
if(sfd < 0){
ERR_MSG("socket");
}
SUC_MSG("socket");
struct sockaddr_in cin;
cin.sin_family = AF_INET;
cin.sin_port = htons(PORT);
cin.sin_addr.s_addr = inet_addr(IP);
if(bind(sfd,(struct sockaddr*)&cin,sizeof(struct sockaddr_in)) < 0){
ERR_MSG("bind");
}
SUC_MSG("bind");
struct sockaddr_in sin;
sin.sin_family = AF_INET;
sin.sin_port = htons(SERVERPORT);
sin.sin_addr.s_addr = inet_addr(SERVERIP);
if(connect(sfd,(struct sockaddr*)&sin,sizeof(struct sockaddr_in)) < 0){
ERR_MSG("connect");
}
SUC_MSG("connect");
alarm(5);
char buf[128];
while(1){
bzero(buf,sizeof(buf));
printf("Enter something to send:");
scanf("%s",buf);
int res = send(sfd,buf,sizeof(buf),0);
if(res < 0){
ERR_MSG("send");
}
bzero(buf,sizeof(buf));
res = recv(sfd,buf,sizeof(buf),0);
printf("%s\n",buf);
if(myAlarm == 14){
break;
}
}
if(close(sfd) < 0){
ERR_MSG("close");
}
return 0;
}