From 2540b743241e1d64090d7c90a4baf4a880dd3a09 Mon Sep 17 00:00:00 2001 From: yzc Date: Tue, 31 Dec 2019 11:19:08 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BB=A3=E7=A0=81=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- http_check/src/http_check.c | 229 ++++++++++++++++++++---------------- 1 file changed, 127 insertions(+), 102 deletions(-) diff --git a/http_check/src/http_check.c b/http_check/src/http_check.c index 5c24e6a..bd85281 100644 --- a/http_check/src/http_check.c +++ b/http_check/src/http_check.c @@ -25,20 +25,23 @@ #include "MESA/MESA_handle_logger.h" #include "MESA/MESA_htable.h" #include "MESA/MESA_list.h" +#include #define BUFSIZE 8192 -#define MAX_LOG_PATH_LEN 256 -#define CPU_START_POS 14 /* stat文件的有效起始行数 */ -int g_http_port; -char g_http_address[MAX_LOG_PATH_LEN]=""; -//const char *http_check_conf_file = "./conf/http_check/http_check.conf"; -const char *http_check_conf_file = "/home/mesasoft/sapp/plug/business/http_check/http_check.conf"; +#define MAX_STR_LEN 256 +#define MAX_BUF_LEN 1024 +#define MAX_NAME_LEN 32 +#define CPU_START_POS 14//stat文件的有效起始行数 +#define HTTP_TIMEOUT 100 +uint16_t g_http_port; +char g_http_address[MAX_STR_LEN]=""; +const char *http_check_conf_file = "./plug/business/http_check/http_check.conf"; struct route_info { - u_int dstAddr; - u_int srcAddr; - u_int gateWay; + uint32_t dstAddr; + uint32_t srcAddr; + uint32_t gateWay; char ifName[IF_NAMESIZE]; }; @@ -51,8 +54,8 @@ struct route_info //在字符串中寻找第N次空格出现的地方 char *get_items_by_pos(char *buff, unsigned int numb) { - char *crpos; - int i, ttlen, count; + char *crpos = NULL; + int i, ttlen, count; crpos = buff; ttlen = strlen(buff); @@ -60,11 +63,11 @@ char *get_items_by_pos(char *buff, unsigned int numb) for (i = 0; i < ttlen; i++) { - if (' ' == *crpos) - { /* 以空格为标记符进行识别 */ + if (' ' == *crpos)//以空格为标记符进行识别 + { count++; - if (count == (numb - 1)) - { /* 全部个数都找完了 */ + if (count == (numb - 1))//全部个数都找完了 + { crpos++; break; } @@ -78,20 +81,24 @@ char *get_items_by_pos(char *buff, unsigned int numb) //获取当前进程的CPU时间 long get_pro_cpu_time(unsigned int pid) { - FILE *fd; - char *vpos, buff[1024]; - long utime, stime, cutime, cstime; + FILE *fp = NULL; + char *vpos, buff[MAX_BUF_LEN] = ""; + long utime, stime, cutime, cstime; sprintf(buff, "/proc/%d/stat", pid); - fd = fopen(buff, "r"); - assert(fd != NULL); - assert(fgets(buff, sizeof(buff), fd) != NULL); - + fp = fopen(buff, "r"); + if(fp == NULL) + { + printf("file open /proc/self/stat error!"); + return -1; + } + fgets(buff, sizeof(buff), fp); + vpos = get_items_by_pos(buff, CPU_START_POS); sscanf(vpos, "%ld %ld %ld %ld", &utime, &stime, &cutime, &cstime); - //printf("get_data2:%ld %ld %ld %ld\n", utime, stime, cutime, cstime); - fclose(fd); + //printf("get_data_process:%ld %ld %ld %ld\n", utime, stime, cutime, cstime); + fclose(fp); return (utime + stime + cutime + cstime); //return (utime + stime); @@ -100,17 +107,20 @@ long get_pro_cpu_time(unsigned int pid) //获取整个系统的CPU时间 long get_sys_cpu_time(void) { - FILE *fd; - char name[32], buff[1024]; - long user, nice, syst, idle; - - fd = fopen("/proc/stat", "r"); - assert(fd != NULL); - assert(fgets(buff, sizeof(buff), fd) != NULL); + FILE *fp; + char name[MAX_NAME_LEN] = "", buff[MAX_BUF_LEN] = ""; + long user, nice, syst, idle; + fp = fopen("/proc/stat", "r"); + if(fp == NULL) + { + printf("file open /proc/stat error!"); + return -1; + } + fgets(buff, sizeof(buff), fp); sscanf(buff, "%s %ld %ld %ld %ld", name, &user, &nice, &syst, &idle); - //printf("get_data1:%s %ld %ld %ld %ld\n", name, user, nice, syst, idle); - fclose(fd); + //printf("get_data_system:%s %ld %ld %ld %ld\n", name, user, nice, syst, idle); + fclose(fp); return (user + nice + syst + idle); //return (user + syst); @@ -119,20 +129,26 @@ long get_sys_cpu_time(void) //获取进程的CPU使用率 float get_cpu_stat(unsigned int pid) { - float ratio; - long s_cur_pro_cpu, s_pre_pro_cpu; /* 指定程序的本轮/前轮CPU时间 */ - long s_cur_sys_cpu, s_pre_sys_cpu; /* 整个系统的本轮/前轮CPU时间 */ + float ratio = 0; + long s_cur_pro_cpu, s_pre_pro_cpu;//指定程序的本轮/前轮CPU时间 + long s_cur_sys_cpu, s_pre_sys_cpu;//整个系统的本轮/前轮CPU时间 s_pre_pro_cpu = get_pro_cpu_time(pid); s_pre_sys_cpu = get_sys_cpu_time(); - + if(s_pre_pro_cpu < 0 || s_pre_sys_cpu < 0) + return 0; sleep(1); s_cur_pro_cpu = get_pro_cpu_time(pid); s_cur_sys_cpu = get_sys_cpu_time(); + if(s_cur_pro_cpu < 0 || s_cur_sys_cpu < 0) + return 0; if ((s_cur_pro_cpu == s_pre_pro_cpu) || (s_cur_sys_cpu == s_pre_sys_cpu) || (s_cur_pro_cpu == 0) || (s_cur_sys_cpu == 0)) { ratio = 0; - } else { - ratio = (100.0 * (s_cur_pro_cpu - s_pre_pro_cpu)) / (s_cur_sys_cpu - s_pre_sys_cpu); + } + else + { + if((s_cur_sys_cpu - s_pre_sys_cpu) != 0) + ratio = (100.0 * (s_cur_pro_cpu - s_pre_pro_cpu)) / (s_cur_sys_cpu - s_pre_sys_cpu); } return ratio; @@ -141,7 +157,7 @@ float get_cpu_stat(unsigned int pid) //获取默认网关地址 int readNlSock(int sockFd, char *bufPtr, int seqNum, int pId) { - struct nlmsghdr *nlHdr; + struct nlmsghdr *nlHdr = NULL; int readLen = 0, msgLen = 0; do{ //收到内核的应答 @@ -183,12 +199,10 @@ void parseRoutes(struct nlmsghdr *nlHdr, struct route_info *rtInfo,char *gateway { struct rtmsg *rtMsg; struct rtattr *rtAttr; - int rtLen; - char *tempBuf = NULL; + int rtLen; struct in_addr dst; struct in_addr gate; - - tempBuf = (char *)malloc(100); + unsigned char *bytes = NULL; rtMsg = (struct rtmsg *)NLMSG_DATA(nlHdr); // If the route is not for AF_INET or does not belong to main routing table //then return. @@ -217,26 +231,27 @@ void parseRoutes(struct nlmsghdr *nlHdr, struct route_info *rtInfo,char *gateway } } dst.s_addr = rtInfo->dstAddr; - if (strstr((char *)inet_ntoa(dst), "0.0.0.0")) + //if (strstr((char *)inet_ntoa(dst), "0.0.0.0")) + if (dst.s_addr == 0) { //printf("oif:%s",rtInfo->ifName); gate.s_addr = rtInfo->gateWay; - sprintf(gateway, (char *)inet_ntoa(gate)); + //sprintf(gateway, (char *)inet_ntoa(gate)); + bytes = (unsigned char *) &gate.s_addr; + sprintf(gateway, "%d.%d.%d.%d", bytes[0], bytes[1], bytes[2], bytes[3] ); //printf("%s\n",gateway); gate.s_addr = rtInfo->srcAddr; //printf("src:%s\n",(char *)inet_ntoa(gate)); gate.s_addr = rtInfo->dstAddr; //printf("dst:%s\n",(char *)inet_ntoa(gate)); } - free(tempBuf); return; } int get_gateway(char *gateway) { - struct nlmsghdr *nlMsg; - //struct rtmsg *rtMsg; + struct nlmsghdr *nlMsg; struct route_info *rtInfo; char msgBuf[BUFSIZE]; int sock, len, msgSeq = 0; @@ -248,13 +263,12 @@ int get_gateway(char *gateway) } memset(msgBuf, 0, BUFSIZE); - nlMsg = (struct nlmsghdr *)msgBuf; - //rtMsg = (struct rtmsg *)NLMSG_DATA(nlMsg); + nlMsg = (struct nlmsghdr *)msgBuf; nlMsg->nlmsg_len = NLMSG_LENGTH(sizeof(struct rtmsg)); // Length of message. - nlMsg->nlmsg_type = RTM_GETROUTE; // Get the routes from kernel routing table . - nlMsg->nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST; // The message is a request for dump. - nlMsg->nlmsg_seq = msgSeq++; // Sequence of the message packet. - nlMsg->nlmsg_pid = getpid(); // PID of process sending the request. + nlMsg->nlmsg_type = RTM_GETROUTE; // Get the routes from kernel routing table + nlMsg->nlmsg_flags = NLM_F_DUMP | NLM_F_REQUEST; // The message is a request for dump + nlMsg->nlmsg_seq = msgSeq++; // Sequence of the message packet + nlMsg->nlmsg_pid = getpid(); // PID of process sending the request if(send(sock, nlMsg, nlMsg->nlmsg_len, 0) < 0) { @@ -293,19 +307,12 @@ void http_handler_status_msg(struct evhttp_request *req,void *arg) //启动时间,启动时长 if (sysinfo(&info)) { - fprintf(stderr, "Failed to get sysinfo, errno:%u, reason:%s\n", - errno, strerror(errno)); + printf("====line:%d,%s\n",__LINE__,"Failed to get sysinfo!"); return ; } time(&cur_time); - if (cur_time > info.uptime) - { - boot_time = cur_time - info.uptime; - } - else - { - boot_time = info.uptime - cur_time; - } + boot_time = cur_time - info.uptime; + ptm = localtime(&boot_time); /*printf("System boot time:%d-%-d-%d %d:%d:%d\n", ptm->tm_year + 1900, ptm->tm_mon + 1, ptm->tm_mday, ptm->tm_hour, ptm->tm_min, ptm->tm_sec);*/ @@ -321,35 +328,34 @@ void http_handler_status_msg(struct evhttp_request *req,void *arg) //printf("process id:%d\n", process_id); //默认网关地址 - char buff[256]; - get_gateway(buff); + char default_gateway_tmp[MAX_STR_LEN]=""; + get_gateway(default_gateway_tmp); //printf("gateway:%s\n",buff); //内存(虚存,实存) unsigned int n_rss, n_resident, n_share, n_text, n_lib, n_data, n_dt; - char buf[256]; - char buf1[256]; - char buf2[256]; - char buf3[256]; - FILE *f = fopen("/proc/self/statm","r"); + char mem_buf_tmp[MAX_STR_LEN]; + char boot_time_tmp[MAX_STR_LEN]; + char running_time_tmp[MAX_STR_LEN]; + char cpu_usage_tmp[MAX_STR_LEN]; + FILE *fp = fopen("/proc/self/statm","r"); - if(f) + if(fp) { - fscanf(f,"%u%u%u%u%u%u%u",&n_rss,&n_resident,&n_share,&n_text,&n_lib,&n_data,&n_dt); - fclose(f); + fscanf(fp,"%u%u%u%u%u%u%u",&n_rss,&n_resident,&n_share,&n_text,&n_lib,&n_data,&n_dt); + fclose(fp); } else { - printf("open /proc/self/statm failed!"); + printf("====line:%d,%s\n",__LINE__,"open /proc/self/statm failed!"); return; } - n_rss = n_rss * 4; - n_resident = n_resident *4; - - sprintf(buf, "VmSize=%ukB, VmRss=%ukB", n_rss, n_resident); + n_rss = n_rss * (getpagesize()/1024); + n_resident = n_resident * (getpagesize()/1024); + sprintf(mem_buf_tmp, "VmSize=%ludkB, VmRss=%lukB\n", n_rss, n_resident); //printf("memory info:%s\n",buf); - //cpu + //当前进程cpu占用 float cpu_rate; unsigned int cpu_num; cpu_rate = get_cpu_stat(process_id); @@ -363,20 +369,23 @@ void http_handler_status_msg(struct evhttp_request *req,void *arg) printf("====line:%d,%s\n",__LINE__,"retbuff is null."); return; } - sprintf(buf1, "%d-%-d-%d %d:%d:%d", ptm->tm_year + 1900,ptm->tm_mon + 1, ptm->tm_mday, ptm->tm_hour, ptm->tm_min, ptm->tm_sec); - sprintf(buf2, "%ddays %dhours %dminutes %dseconds", run_days,run_hour,run_minute,run_second); - sprintf(buf3, "%f", cpu_rate*cpu_num); + sprintf(boot_time_tmp, "%d-%-d-%d %d:%d:%d", ptm->tm_year + 1900,ptm->tm_mon + 1, ptm->tm_mday, ptm->tm_hour, ptm->tm_min, ptm->tm_sec); + sprintf(running_time_tmp, "%ddays %dhours %dminutes %dseconds", run_days,run_hour,run_minute,run_second); + sprintf(cpu_usage_tmp, "%f", cpu_rate*cpu_num); cJSON * root = cJSON_CreateObject(); - + if(!root) + { + printf("====line:%d,%s\n",__LINE__,"cJSON_CreateObject error!"); + return; + } //根节点下添加 - cJSON_AddItemToObject(root, "boot time", cJSON_CreateString(buf1)); - cJSON_AddItemToObject(root, "running time", cJSON_CreateString(buf2)); + cJSON_AddItemToObject(root, "boot time", cJSON_CreateString(boot_time_tmp)); + cJSON_AddItemToObject(root, "running time", cJSON_CreateString(running_time_tmp)); cJSON_AddItemToObject(root, "process id", cJSON_CreateNumber(process_id)); cJSON_AddItemToObject(root, "server ip", cJSON_CreateString(g_http_address)); - cJSON_AddItemToObject(root, "default gateway", cJSON_CreateString(buff)); - cJSON_AddItemToObject(root, "memory info", cJSON_CreateString(buf)); - cJSON_AddItemToObject(root, "cpu usage", cJSON_CreateString(buf3)); - + cJSON_AddItemToObject(root, "default gateway", cJSON_CreateString(default_gateway_tmp)); + cJSON_AddItemToObject(root, "memory info", cJSON_CreateString(mem_buf_tmp)); + cJSON_AddItemToObject(root, "cpu usage", cJSON_CreateString(cpu_usage_tmp)); printf("cjson_status_print:%s\n", cJSON_Print(root)); //evbuffer_add_printf(retbuff,"System boot time: %d-%-d-%d %d:%d:%d\r\nsystem running time:%dday %dhour %dminute %dsecond\r\nprocess id:%d\r\ngateway:%s\r\nmemory info:%s\r\ncpu% = %f\r\n", @@ -395,7 +404,7 @@ void http_handler_status_msg(struct evhttp_request *req,void *arg) //keepalive回响应 void http_handler_keepalive_msg(struct evhttp_request *req,void *arg) { - struct tm *local; + struct tm *local = NULL; time_t tt; tt=time(NULL); local=localtime(&tt); @@ -409,6 +418,11 @@ void http_handler_keepalive_msg(struct evhttp_request *req,void *arg) } cJSON * root = cJSON_CreateObject(); + if(!root) + { + printf("====line:%d,%s\n",__LINE__,"cJSON_CreateObject error!"); + return; + } cJSON_AddItemToObject(root, "current time", cJSON_CreateString(asctime(local))); printf("cjson_keepalive_print:%s\n", cJSON_Print(root)); @@ -423,16 +437,15 @@ void http_handler_keepalive_msg(struct evhttp_request *req,void *arg) return; } -//int main() -int http_check_init() +void *pthread(void *arg) { struct evhttp *http_server = NULL; //short http_port = 10000; //char *http_addr = "0.0.0.0"; - MESA_load_profile_int_def(http_check_conf_file, "HTTP", "SERVER_PORT", &g_http_port, 0); - MESA_load_profile_string_def(http_check_conf_file, "HTTP", "SERVER_IP", g_http_address, MAX_LOG_PATH_LEN, NULL); - printf("*v1*******read_ip:%s,read_port:%d\n",g_http_address, g_http_port); + MESA_load_profile_int_def(http_check_conf_file, "HTTP", "SERVER_PORT", (int *)(&g_http_port), 0); + MESA_load_profile_string_def(http_check_conf_file, "HTTP", "SERVER_IP", g_http_address, MAX_STR_LEN, NULL); + printf("*v2*******read_ip:%s,read_port:%d\n",g_http_address, g_http_port); //初始化 event_init(); //启动http服务端 @@ -440,19 +453,31 @@ int http_check_init() if(http_server == NULL) { printf("====line:%d,%s\n",__LINE__,"http server start failed."); - return -1; + return NULL; } //设置请求超时时间(s) - evhttp_set_timeout(http_server,100); - //设置事件处理函数,evhttp_set_cb针对每一个事件(请求)注册一个处理函数, - //区别于evhttp_set_gencb函数,是对所有请求设置一个统一的处理函数 - evhttp_set_cb(http_server,"/status",http_handler_status_msg,NULL);//为特定的URI指定callback + evhttp_set_timeout(http_server,HTTP_TIMEOUT); + //设置事件处理函数,针对每一个事件(请求)注册一个处理函数,为特定的URI指定callback + evhttp_set_cb(http_server,"/status",http_handler_status_msg,NULL); evhttp_set_cb(http_server,"/keepalive",http_handler_keepalive_msg,NULL); //循环监听 event_dispatch(); evhttp_free(http_server); + + return NULL; +} + +int http_check_init() +{ + pthread_t tidp; + if ((pthread_create(&tidp, NULL, pthread, NULL)) == -1) + { + printf("====line:%d,%s\n",__LINE__,"http_check thread create error!"); + return 0; + } + return 0; }