Multi-process network service
1. High-performance network service program
One of the application advantages of Linux is that it can be used to design a variety of high-performance network service programs. One of the characteristics of high performance is to achieve concurrent access processing and provide services for multiple online users at the same time; multi-process network services, multi-thread network services, thread pool network services
2. Multi-process network service
It is a popular concurrent service technology to provide concurrent services for multiple users by using the parent-child process relationship in Linux system. Its basic idea is to start a service process with one user. If a new connection arrives, the promoter process interacts with it, and its child process automatically exits after the end of the service.
The model is as follows:
3. Code implementation:
Use an integer operation to simulate multi-process network services.
(1), utili.h
# include#include#include#include#include#include#include#include#define SERVER_PORT 9090#define SERVER_IP "127.0.0.1" # define LISTEN_QUEUE 5#define BUFFER_SIZE 255typedef enum {ADD,SUB,MUL,DIV,MOD, QUIT} OPER_TYPE;typedef struct OperStruct {int op1; int op2; OPER_TYPE oper;} OperStruct
(2), ser.c
# include ".. / utili.h" void Process_Handler (int sockConn); void Process_Handler (int sockConn) {OperStruct op; int result; while (1) {int res = recv (sockConn, & op, sizeof (op), 0); if (res = =-1) {printf ("recv data fail.\ n"); continue } if (op.oper = = ADD) {result = op.op1 + op.op2;} else if (op.oper = = SUB) {result = op.op1-op.op2;} else if (op.oper = = MUL) {result = op.op1 * op.op2 } else if (op.oper = = DIV) {result = op.op1 / op.op2;} else if (op.oper = = QUIT) {break;} res = send (sockConn, & result, sizeof (result), 0); if (res = =-1) {printf ("send data fail.\ n"); continue } close (sockConn);} int main (void) {int sockSer = socket (AF_INET, SOCK_STREAM, 0); if (sockSer =-1) {perror ("socket"); return-1;} struct sockaddr_in addrSer, addrCli; addrSer.sin_family = AF_INET; addrSer.sin_port = htons (SERVER_PORT); addrSer.sin_addr.s_addr = inet_addr (SERVER_IP) Socklen_t len = sizeof (struct sockaddr); int res = bind (sockSer, (struct sockaddr*) & addrSer, len); if (res = =-1) {perror ("bind"); close (sockSer); return-1;} listen (sockSer, LISTEN_QUEUE); int sockConn; while (1) {printf ("Server Wait Client Connect.\ n") SockConn = accept (sockSer, (struct sockaddr*) & addrCli, & len); if (sockConn = =-1) {printf ("Server Accept Client Connect Fail.\ n"); continue;} else {printf ("Server Accept Client Connect Success.\ n"); printf ("Client IP: >% s\ n", inet_ntoa (addrCli.sin_addr)) Printf ("Client Port: >% d\ n", ntohs (addrCli.sin_port));} pid_t pid; pid = fork (); if (pid = = 0) {close (sockSer); Process_Handler (sockConn); exit (0);} else if (pid > 0) {close (sockConn); continue } else {printf ("Create Process Fail.\ n"); continue;}} close (sockSer); return 0;}
(3), cli.c
# include "utili.h" void InputData (OperStruct * pt); void InputData (OperStruct * pt) {printf ("please input op1 and op2:"); scanf ("d% d", & (pt- > op1), & (pt- > op2));} / / Cliint main (void) {int sockCli = socket (AF_INET, SOCK_STREAM, 0); if (sockCli =-1) {perror ("socket"); return-1 } struct sockaddr_in addrSer; addrSer.sin_family = AF_INET; addrSer.sin_port = htons (SERVER_PORT); addrSer.sin_addr.s_addr = inet_addr (SERVER_IP); socklen_t len = sizeof (struct sockaddr); int res = connect (sockCli, (struct sockaddr*) & addrSer, len); if (res = =-1) {perror ("connect"); close (sockCli) Return-1;} else {printf ("Client Connect Server Success.\ n");} char cmd [2]; OperStruct op; int result; while (1) {printf ("Please input operator:"); scanf ("% s", cmd); if (strcmp (cmd, "+") = = 0) {op.oper = ADD; InputData (& op) } else if (strcmp (cmd, "-") = = 0) {op.oper = SUB; InputData (& op);} else if (strcmp (cmd, "*") = = 0) {op.oper = MUL; InputData (& op);} else if (strcmp (cmd, "/") = = 0) {op.oper = DIV; InputData (& op) } else if (strcmp (cmd, "quit") = = 0) {op.oper = QUIT;} else {printf ("Cmd invalid.\ n");} res = send (sockCli, & op, sizeof (op), 0); if (res = =-1) {printf ("send data fail.\ n"); continue } if (op.oper = = QUIT) break; res = recv (sockCli, & result, sizeof (result), 0); if (res = =-1) {printf ("recv data fail.\ n"); continue;} printf ("result =% d\ n", result);} close (sockCli); return 0;}
Running result:
Server side
Customer 1
Customer 1
Customer 2
4. Result analysis
(1) utili.h is in the upper level directory of ser.c, and utili.h and cli.c are in the same layer directory.
(2) process server: socker is the reference counter model, close () is reduced by one, and is not really closed. Every time a process is created, it will add 1 to the socker reference counter.
(3) disadvantages: a, starting and closing child processes bring a lot of overhead; b, the system can only generate a maximum of 512 processes, that is, a maximum of 512 customers, which can not handle large-scale access