负载均衡服务器
来源:互联网 发布:主播都用什么唱歌软件 编辑:程序博客网 时间:2024/05/16 05:55
每次有客户端连接时选择当前连接数(CR)最小的http服务器进行连接,然后转发请求和应答,用线程实现:
#include"unp.h"#include <semaphore.h>#include<stdlib.h>#include <errno.h>#include <fcntl.h>#include <unistd.h>#include <pthread.h>#include <time.h>#include<syslog.h>#define gettid() syscall(__NR_gettid)#define SESSIONNUM 10000int myreadline(int fd, char *buf, int n);static void *http(void* connfd);void init();struct httpServerInfo{ char ip[20]; char port[10]; char OS[10];volatile int CR; double ACR; double cpuUse; int memUse;} httpServer[4];struct SessionAdhesions{ int ip; int choice;} sessionList[SESSIONNUM];int sessionIndex;char balanceServerIp[20];char balanceServerPort[10];volatile int CR;double ACR;double cpuUse;int memUse;static pthread_mutex_t mutex;struct eachThreadInfo{int choice;int fd;};int main(int argc, char **argv){ intlistenfd, connfd; pthread_t tid; socklen_tclilen; struct sockaddr_in cliaddr, servaddr; listenfd = Socket(AF_INET, SOCK_STREAM, 0); bzero(&servaddr, sizeof(servaddr)); servaddr.sin_family = AF_INET;//-------------------初始化结构体---------------------------- init();//---------------------------------------------------------- inet_pton(AF_INET,balanceServerIp,&servaddr.sin_addr); servaddr.sin_port=htons(atoi(balanceServerPort)); Bind(listenfd, (SA *) &servaddr, sizeof(servaddr)); Listen(listenfd, LISTENQ); signal(SIGPIPE,SIG_IGN); for ( ; ; ) { clilen = sizeof(cliaddr); if ( (connfd = accept(listenfd, (SA *) &cliaddr, &clilen)) < 0) { if (errno == EINTR) continue; else err_sys("accept error"); } // printf("connected from %s:%u...http\n",inet_ntoa(cliaddr.sin_addr),cliaddr.sin_port);struct eachThreadInfo *arg=malloc(sizeof(struct eachThreadInfo));arg->fd=connfd;//-------------------------------------SessionAdhesions--------------------------------------------------------- /* int j=0;int clientIp=cliaddr.sin_addr.s_addr; for(j=0; j<sessionIndex; j++) { if(clientIp!=sessionList[j].ip) { arg->choice=sessionList[j].choice; break; } } if(j==sessionIndex) { sessionList[sessionIndex].ip=clientIp;*///---------------------------------------balance connect-------------------------------------------------------- int i; int eachCR=99999; for(i=0; i<4; i++) { if(httpServer[i].CR<eachCR) { arg->choice=i; eachCR=httpServer[i].CR; } } sessionList[sessionIndex].choice=arg->choice; sessionIndex=(sessionIndex+1)%SESSIONNUM; printf("choose httpServer %d!\n\n",arg->choice); pthread_create(&tid,NULL,http,(void*)arg); }}static void *http(void* arg){ pthread_detach(pthread_self()); struct eachThreadInfo *each=arg; pthread_mutex_lock(&mutex); httpServer[each->choice].CR++; CR++; pthread_mutex_unlock(&mutex); int httpd; struct sockaddr_inhttpservaddr; httpd = Socket(AF_INET, SOCK_STREAM, 0); bzero(&httpservaddr, sizeof(httpservaddr)); httpservaddr.sin_family = AF_INET; httpservaddr.sin_port = htons(atoi(httpServer[each->choice].port)); Inet_pton(AF_INET, httpServer[each->choice].ip, &httpservaddr.sin_addr); connect(httpd, (SA *) &httpservaddr, sizeof(httpservaddr)); //perror("connect"); char receiveline[MAXLINE]; ssize_t n; char temp[50]; while((n=myreadline(each->fd,receiveline,MAXLINE))>2) { sscanf(receiveline,"%s",temp); writen(httpd,receiveline,n); } writen(httpd,"\r\n",2); char judge[100]; unsigned long intfileLength=0; while((n=myreadline(httpd,receiveline,MAXLINE))>2) { writen(each->fd,receiveline,n); sscanf(receiveline,"%s",judge); if(!strcmp(judge,"Content-Length:")){ sscanf(receiveline,"%*s%lu",&fileLength);} } writen(each->fd,"\r\n",2); while(1) { if(MAXLINE<fileLength) { fileLength-=read(httpd, receiveline, MAXLINE);; writen(each->fd,receiveline,MAXLINE); } else { read(httpd, receiveline, fileLength); writen(each->fd,receiveline,fileLength); break; } } pthread_mutex_lock(&mutex); httpServer[each->choice].CR--; CR--; pthread_mutex_unlock(&mutex); close(each->fd); close(httpd); free(arg); return NULL;}int myreadline(int fd, char *buf, int n){ char ch; char *base=buf; while(1) { if(read(fd, &ch, 1)!=1) { if(errno==EINTR) continue; return -1; } if((*(buf++)=ch)=='\n') break; } *buf='\0'; return buf-base;}void init(){ int conf=open("balance.conf",O_RDONLY); char temp[40]; myreadline(conf,temp,40); sscanf(temp,"%*s%s",balanceServerIp); myreadline(conf,temp,40); sscanf(temp,"%*s%s",balanceServerPort); int i=0,j=0; int num=4; num=num*2; for(; i<num; i++) { myreadline(conf,temp,30); if(!(i%2)) sscanf(temp,"%*s%s",httpServer[j].ip); else sscanf(temp,"%*s%s",httpServer[j++].port); } close(conf);}
把webbench改为线程版本,用10W连接测试1300k.jpg请求,时间50秒,结果如下:
0 0
- 什么是服务器负载均衡
- 实现服务器负载均衡
- 服务器负载均衡技术
- 服务器 集群 负载均衡
- 服务器的负载均衡
- 服务器的负载均衡
- 负载均衡服务器简介
- 服务器负载均衡
- 服务器负载均衡解决方案
- 负载均衡服务器简介
- Nginx 负载均衡服务器
- 负载均衡服务器
- 应用服务器负载均衡
- 服务器负载均衡技术
- 服务器负载均衡概述
- 负载均衡服务器简介
- 服务器负载均衡技术
- F5负载均衡服务器
- 实现自动识别OpenCV的版本号
- css 实现 lightbox
- 采用“迭代器”和“行变量替换”进行多个点数据的连通
- java动态加载jar包,并运行其中的类和方法
- struts2 json 输出日期格式不正确
- 负载均衡服务器
- String.getBytes()的问题
- 架构图汇总
- samba是什么
- MongoDB MapReduce
- vc 使用COM
- iOS中画图表 使用HighChart
- MATLAB函数句柄(@),feval与内连函数(inline)
- HDS USP系列存储(一)专业名词解释(持续添加中..)