linux守护进程模型 之 代理功能

来源:互联网 发布:c语言运算符结合方向 编辑:程序博客网 时间:2024/05/05 10:13

守护进程(服务器端):daemon.h daemon.c daemon_mod.c/****************daemon.h***************/#ifndef  _DAEMON_H_#define  _DAEMON_H_#include<stdio.h>#include<unistd.h>#include<string.h>#ifdef __cpluscplusextern "C" {#endif#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))#define VANSTOR_DAEMON_PORT 6686int printf_cgi(int sockfd,char*fmt,...); /***  服务器端添加一个代理功能,只需在此添加一个函数名声明,并在结构体数组中加入对应的一项***/void* nas_resouce_create_func(int sockfd,char*s);/**********msg struct [modename,func_name ,args]*/typedef  void* Func_point(int n,char*s);static const struct msg_par{char * name;int func_num;Func_point *vanstor_function;}vanstor_daemon_array[]={{"samba",1,nas_resouce_create_func},//calling nas_resouce_create(device,fstype,path)};#ifdef __cplusplus}#endif#endif/*************daemon.c********************/#include<stdio.h>#include<unistd.h>#include<string.h>#include<stdlib.h>#include<stdarg.h>#include<sys/types.h>#include<sys/socket.h>#include<sys/un.h>#include<syslog.h>#include<signal.h>#include<sys/wait.h>#include<sys/mount.h>#include <netinet/in.h> #include "vanstor_daemon.h"int printf_cgi(int fd,char*fmt,...){va_list args;char buf[1024];int n=0;va_start(args,fmt);n=vsprintf(buf,fmt,args);va_end(args);write(fd,buf,n);return n;};/***** in:src  按数据结构分解***** out: modename,*****   func_num,******/int msg_parse_dispatch(char *src,char *modename,int *func_num){char c=' ';char *result=strtok(src,&c);strcpy(modename,result);// modename<24result=strtok(NULL,&c);*func_num=atoi(result);return strlen(modename)+strlen(result);}int vanstor_recv(int fd){char recv_buf[1024];int num;char modename[24]={0};int func_num,i;memset(recv_buf,0,1024);num=read(fd,recv_buf,sizeof(recv_buf));//printf("vanstor_recv:%s\n",recv_buf);//syslog(LOG_INFO,"recv message:[%s]\n",recv_buf);int n=msg_parse_dispatch(recv_buf,modename,&func_num);for(i=0;i<ARRAY_SIZE(vanstor_daemon_array);i++){if((0==strcmp(modename,vanstor_daemon_array[i].name))&&(func_num==vanstor_daemon_array[i].func_num)){vanstor_daemon_array[i].vanstor_function(fd,recv_buf+n+2);break;}}close(fd);return 0;}int ipc_daemon(){int fd,connect_fd,err;struct sockaddr_in local_addr,client_addr;socklen_t len;fd = socket(AF_INET, SOCK_STREAM, 0);if (fd < 0) {syslog(LOG_ERR,"can't create a listen socket!\n");return -1;}memset(&local_addr, 0, sizeof(local_addr));local_addr.sin_family=AF_INET;local_addr.sin_addr.s_addr=htonl(INADDR_ANY);local_addr.sin_port=htons(VANSTOR_DAEMON_PORT);err = bind(fd, (struct sockaddr *) &local_addr, sizeof(local_addr));if (err) {syslog(LOG_ERR,"can't bind local socket!\n");return -1;}err = listen(fd, 32);if (err) {syslog(LOG_ERR,"can't listen in local socket !\n");return -1;}while(1){len = sizeof(client_addr);connect_fd = accept(fd, (struct sockaddr *) &client_addr, &len);if(connect_fd>0){pid_t pid;   pid=fork();if(pid<0){syslog(LOG_ERR,"fork failed!");}else if(pid==0){vanstor_recv(connect_fd);exit(0);}}}close(fd);return 0;}void handler(int num){int status;//int pid=waitpid(-1,&status,WNOHANG);/*if(WIFEXITED(status)){printf("the child %d exit with %d \n",pid,WIFEXITED(status));}*/}int main(){int pid;if((pid=fork()))exit(0);if(pid<0){printf("vanstor_daemon start failed!\n");exit(1);}signal(SIGCHLD,handler);openlog("vanstor_daemon",LOG_PID|LOG_CONS,LOG_USER);ipc_daemon();closelog();return 0;}/*************daemon_mod.c**********************************例:数据结构数组 第一项 的实现,其它代理功能可以在此文件中实现添加,也可以新建文件********************************/#include "daemon.h"//args=device+fstype+pathvoid* nas_resouce_create_func(int sockfd,char*s){char *device,*fstype,*path;int ret=0;char *res=strtok(s," ");device=res;res=strtok(NULL," ");fstype=res;res=strtok(NULL," ");path=res;ret=nas_resource_create(device,fstype,path); //此为库函数if(ret){printf_cgi(sockfd,"%s mount %s seccess!",device,path);}else{printf_cgi(sockfd,"%s mount %s failed!",device,path);}return 0;}/**********客户端:daemon_client.h********想要与守护进程通信只需调用此函数*********/#include<stdio.h>#include<unistd.h>#include<sys/types.h>#include<sys/socket.h>#include<sys/un.h>#include<errno.h>#include<netinet/in.h>#define VANSTOR_IPC_CONNECTION "/var/vanstor.ipc"       // 本地通信AF_LOCAL//sendmsg必需与守护进程定义的数据结构格式一样  sendmsg= "modename  func_num  args"int daemon_send(char*sendmsg,char*recv_msg){    int connect_fd;       int ret;       char snd_buf[1024];       int i;       //static struct sockaddr_un srv_addr;       static struct sockaddr_in srv_addr;       connect_fd=socket(AF_INET,SOCK_STREAM,0);       if(connect_fd<0)       {           printf("cannot create communication socket!\n");           return -1;       }     memset(&srv_addr,0,sizeof(srv_addr));         //srv_addr.sun_family=AF_UNIX;       //strcpy(srv_addr.sun_path,VANSTOR_IPC_CONNECTION);   srv_addr.sin_family=AF_INET;srv_addr.sin_port=htons(6686);if(inet_pton(AF_INET,"127.0.0.1",&srv_addr.sin_addr)<0){printf("inet_pton error !\n");return 0;}    ret=connect(connect_fd,(struct sockaddr*)&srv_addr,sizeof(srv_addr));       if(ret==-1)       {           printf("cannot connect to the server!%d,%d:%s\n",connect_fd,errno,strerror(errno));           close(connect_fd);           return -1;       }       memset(snd_buf,0,1024);       strcpy(snd_buf,sendmsg);       write(connect_fd,snd_buf,sizeof(snd_buf));    i=read(connect_fd,recv_msg,1024);    close(connect_fd);       return i; }


原创粉丝点击