[原创]linux c项目配置文件

时间:2023-01-16 11:09:56
  config.h

/*
* File:   config.h:整个程序的配置文件头文件
* Author: netpet
* Flower net server
* 本程序是为一体化web server产品专用设计,具有部分代码为具体产品优化而不代表普遍通用性的特性
* 程序在linux 2.46下调试通过,编辑工具netbeans 6.1 for c
* 联系方式:Email:netpetboy@163.com QQ:51977431
* Created on 2008年5月26日, 下午4:18
*/
#ifndef _CONFIG_H
#define    _CONFIG_H

#ifdef    __cplusplus
extern "C" {
#endif
#define CONLINELENGTH 1024
    #include <stdio.h>
    #include <arpa/inet.h>
   
    extern struct config_t *config;
    extern struct timeval current_time;
   
    /*
     *结构体功能:定义基本的系统配置信息
     *由config Init函数初始化
     */
    struct config_t {

        struct {
            int DebugModel;
            char DebugPath[400];
            FILE *debug_log;
            char LogPath[400];
            FILE *log_log;
            char AccessPath[400];
            FILE *access_log;
        } log;

        struct {
            int port;
            struct in_addr localIP;
            int debug_mode;
            long long MaxMem;
        } server;

        struct {
            time_t client_life;
            time_t server_life;
            time_t request;
            time_t reply;
            time_t connect;
        } timeout;

        struct {
            int MinIndex; //pool
            int Align;//对齐步进单位,4,8,16等等,每项所能容纳的最大内存为Align*index,index为shortint,所以单项最大容量为Align*255*255字节,4字节对齐最大为260K,8字节对齐为512K
            int InitMemItem; //初始化池所能拥有的数量不能超过255*255
            int ExpendMemItem; //每次扩展池多少项。不能超过255*255
            long MaxMemory; //内存池最大容量 300M
        } memory;
    };
    /*
     *函数功能:将当前时间压入时间容器,以求达到定时获取时间而不影响性能的目的
     */
    extern void CurrentTimeGet(void);
    /*
     *函数功能:获取服务器端时间
     *返回的值为时间的格式化后的字符串
     */
    extern char *ServerTime(void) ;
    /*
     *函数功能:从给定的文件中获取指定项的配置值
     *返回的值为堆内存,需要显示释放
     */
   extern char *ReadConfigfile(char *fileName, char *item);
     /*
     *函数功能:初始化服务器配置文件
     *返回值:void
     */
   extern void InitConf();
    /*
     *函数功能:测试config各函数的功能
     *返回值:void
     */
   extern void TestConf();
   /*
    *销毁系统,为重新加载作准备
    */
   extern void DestroySystem();




#ifdef    __cplusplus
}
#endif

#endif    /* _CONFIG_H */

config.c

/*
* File:   config.c:整个程序文件的配置文件实现
* Author: netpet
* Flower net server
* 本程序是为一体化web server产品专用设计,具有部分代码为具体产品优化而不代表普遍通用性的特性
* 程序在linux 2.46下调试通过,编辑工具netbeans 6.1 for c
* 联系方式:Email:netpetboy@163.com QQ:51977431
* Created on 2008年5月26日, 下午4:18
*/
#include "config.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <assert.h>
#include <sys/time.h>
#include <time.h>
#include <errno.h>

#include "log.h"

struct timeval current_time;
struct config_t *config;

/*
*函数功能:将当前时间压入时间容器,以求达到定时获取时间而不影响性能的目的
*/
void CurrentTimeGet(void) {
     gettimeofday(&current_time, NULL);
}
/*
*函数功能:获取服务器端时间
*返回的值为时间的格式化后的字符串
*/
char *ServerTime(void) {
    CurrentTimeGet();
    static char timestr[128];
    struct tm *tm = gmtime(&(current_time.tv_sec));
    if (tm == NULL)
        return NULL;

    strftime(timestr, 127, "%Y/%m/%d %H:%M:%S", tm);
    return timestr;
}
/*
*函数功能:从给定的文件中获取指定项的配置值
*返回的值为堆内存,需要显示释放
*/
char *ReadConfigfile(char *fileName, char *item) {
    FILE *fp;
    char *locate = NULL;
    char *pmove = NULL;
    char confLine[CONLINELENGTH] = {};
    char context[CONLINELENGTH] = {};
    int result = 1;
    char *pline;
    int itl;


    if ((fp = fopen(fileName, "r")) == NULL) {
        printf("打开文件 : %s 失败!!/n", fileName);
        return NULL;
    }

    while (fgets(confLine, CONLINELENGTH, fp) != NULL) {
        pline = confLine;
        if (*pline == '#'||*pline == '/'||*pline == '*') {
            memset(confLine, '0', CONLINELENGTH);
            continue;
        }
        while (isspace(*pline) != 0)pline++;
        locate = strchr(pline, '=');
        if (locate == NULL) {
            memset(confLine, '0', CONLINELENGTH);
            continue;
        }
        pmove = locate;
        pmove--;
        while (isspace(*pmove) != 0)pmove--;
        itl = pmove - pline + 1;
        if (itl == strlen(item)) {
            result = strncasecmp(pline, item, itl);
            if (result == 0) {
                locate++;
                while (isspace(*locate) != 0)locate++;
                pmove = locate;
                while (isspace(*pmove) == 0)pmove++;
                if (pmove - locate + 1 > 0) {
                    strncpy(context, locate, pmove - locate + 1);
                    break;
                } else {
                    fclose(fp);
                    return NULL;
                }
            } else {
                memset(confLine, '0', CONLINELENGTH);
                continue;
            }
        } else {
            memset(confLine, '0', CONLINELENGTH);
            continue;
        }
    }
    fclose(fp);
    char * rtn=(char *)malloc(strlen(context)+1);
    strcpy(rtn,context);

    char *tmp=rtn;
    while(*tmp   !=   '/n')           //去掉字符串结束符'/0'前的'/n'   
                          tmp++;
                  *tmp   =   '/0';

    return rtn;
}
/*
*获得配置文件的Int值
*/
int GetConfInt(char * confPath,char *name)
{
    int rtn=0;
    char *readname=ReadConfigfile(confPath,name);
    if(readname!=NULL)
    {
        rtn=atol(readname);
        int len=strlen(readname);
        char * ls=readname;
        ls+=len-1;
        *ls=tolower(*ls);
        //内存单位换算,结果为byte
        if(*ls=='m')//M
            rtn=rtn*1024*1024;
        if(*ls=='k')//K
            rtn=rtn*1024;
        if(*ls=='g')//G
            rtn=rtn*1024*1024*1024;
        //时间单位换算,结果为秒
        if(*ls=='s')//分
            rtn=rtn*60;
        if(*ls=='h')//小时
            rtn=rtn*60*60;
        if(*ls=='d')//天
            rtn=rtn*60*60*24;
    }
    else
    {
        printf("配置文件中找不到叫:%s的项!",name);
    }
    free(readname);
    return rtn;
}
/*
*内部函数:初始化Log
*/
void InitLog(char * confPath)
{
     //设置logPath,如果成功就打开log文件
    char *logpath=ReadConfigfile(confPath,"LogPath");
    if(logpath!=NULL)
    {
        strcpy(config->log.LogPath,logpath);
        config->log.log_log = fopen(logpath, "a");
        setvbuf(config->log.log_log, NULL, _IONBF, 0);
    }
    else
    {
        printf("logPath路径不正确!/n");
    }
    free(logpath);
     //设置debugPath,如果成功就打开log文件
    char *debugpath=ReadConfigfile(confPath,"DebugPath");
    if(debugpath!=NULL)
    {
        strcpy(config->log.DebugPath,debugpath);
        config->log.debug_log = fopen(debugpath, "a");
        setvbuf(config->log.debug_log, NULL, _IONBF, 0);
    }
      else
    {
        printf("debugPath路径不正确!/n");
    }
    free(debugpath);
     //设置accessLogPath,如果成功就打开log文件
    char *accesspath=ReadConfigfile(confPath,"AccessPath");
    if(accesspath!=NULL)
    {
        strcpy(config->log.AccessPath,accesspath);
        config->log.access_log = fopen(accesspath, "a");
        setvbuf(config->log.access_log, NULL, _IONBF, 0);
    }
    else
    {
        printf("accessPath路径不正确!/n");
    }
    free(accesspath);
   // log_debug(__FILE__, __LINE__, "完成了系统日志的初始化!/n");
   printf("/n日志系统初始化完毕,路径如下:/n   L___%s/n   L___%s/n  L___%s/n",config->log.LogPath,config->log.AccessPath,config->log.DebugPath);

    char *debugmodel=ReadConfigfile(confPath,"DebugModel");
    if(debugmodel!=NULL)
    {
        int debugm=atoi(debugmodel);
        config->log.DebugModel=debugm;
        if(debugm)
            printf("   L___调试状态开启/n");
    }
    free(debugmodel);
}
/*
*功能:初始化内存池相关,内部函数
*返回:空
*/
void InitMem(char *confPath)
{
      //设置MaxIndex
    config->memory.MinIndex=GetConfInt(confPath,"MinIndex");
    config->memory.Align=GetConfInt(confPath,"Align");
    config->memory.ExpendMemItem=GetConfInt(confPath,"ExpendMemItem");
    config->memory.InitMemItem=GetConfInt(confPath,"InitMemItem");
    config->memory.MaxMemory=GetConfInt(confPath,"MaxMemory");
    printf("内存池配置:MinIndex =%d,Align =%d/n           InitMemItem=%d,ExpendMemItem =%d,MaxMemory=%d/n",config->memory.MinIndex,config->memory.Align,config->memory.InitMemItem,config->memory.ExpendMemItem,config->memory.MaxMemory);
  
}
/*
     *函数功能:初始化服务器配置文件
     *返回值:void
     */
void InitConf()
{
    config=(struct config_t*)malloc(sizeof(struct config_t));
    //此处的配置字符串以后要改成读取应用程序根目录下面的文件,从而达到直接读取配置文件的目的
    char *confPath="/home/net/c/net/conf.default";
    InitLog(confPath);
    InitMem(confPath);
     //初始化内存池
    InitPool();
}
/*
*销毁系统,为重新加载作准备
*/
void DestroySystem()
{
    //销毁Mempool
    FreePool();
    free(config);
}
/*
     *函数功能:测试config各函数的功能
     *返回值:void
     */
void TestConf()
{
    printf("当前正在测试config文件的ReadConfigfile函数功能/n");
    char * port=ReadConfigfile("/home/net/c/net/conf.default","port");
    if(port!=NULL)
        printf("参数port的值为%s/n",port);
    else
        printf("参数port的值不存在");
    printf("当前正在测试服务器端时间函数:/n");
    printf("当前时间:%s",ServerTime());
}