/* * kakumei_config.c * * Config management for the kakumei server. * * Author: Dario Rodriguez dario@softhome.net * This program is licensed under the terms of the Affero GPL v1.0+ license. */ #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <string.h> #include <sys/types.h> #include <sys/stat.h> #include "loglib.h" #include "kakumei_config.h" #define MAXLINESIZE 2048 kaconfig * kaconfig_init(char *configfile) { kaconfig *config; FILE *f; char line[MAXLINESIZE]; int len; char *ptr,*sep,*value; int generalsection; int lineno; char **configvalue; if((f=fopen(configfile,"r"))==NULL) return(NULL); if((config=malloc(sizeof(kaconfig)))==NULL) { fclose(f),f=NULL; return(NULL); } memset(config,0,sizeof(kaconfig)); generalsection=0; lineno=0; while(fgets(line,sizeof(line),f)!=NULL) { lineno++; line[sizeof(line)-1]='\0'; /* trim line */ len=strlen(line); while(len>1 && strchr("\n\t ",line[len-1])!=NULL) line[len-1]='\0',len--; for(ptr=line;*ptr!='\0' && strchr("\t ",*ptr)!=NULL;ptr++) ; len=strlen(ptr); /* ignore empty lines and comments */ if(*ptr=='\0' || strchr("#;",*ptr)!=NULL) continue; /* parse line */ if(*ptr=='[' && ptr[len-1]==']') { /* section */ if(strcmp(ptr,"[general]")==0) generalsection=1; else { log_write("CONF","%s:%i: unknown section name \"%s\"\n",configfile,lineno,ptr); generalsection=0; } continue; } else if((sep=strchr(ptr,'='))!=NULL) { *sep='\0'; value=sep+1; /* trim key */ while(sep>ptr && strchr(" \t",sep[-1])!=NULL) { sep--; *sep='\0'; } /* trim value */ while(*value!='\0' && strchr(" \t",*value)!=NULL) value++; /* sanity check */ if(*value=='\0') { log_write("CONF","%s:%i: ignoring key without value; key:\"%s\"\n",configfile,lineno,ptr); continue; } /* assign value */ if(generalsection!=1) { log_write("CONF","%s:%i: ignoring key-value pair in unknown section; key:\"%s\"\n",configfile,lineno,ptr); continue; } /* identify key-value pair */ if(strcmp(ptr,"logfile")==0) { configvalue=&(config->logfile); } else if(strcmp(ptr,"cookiename")==0) { configvalue=&(config->cookiename); } else if(strcmp(ptr,"cookiedomain")==0) { configvalue=&(config->cookiedomain); } else if(strcmp(ptr,"bannerpath")==0) { configvalue=&(config->bannerpath); } else if(strcmp(ptr,"sslproxy")==0) { if(strcmp(value,"true")==0 || strcmp(value,"1")==0 || strcmp(value,"yes")==0) config->sslproxy=1; else config->sslproxy=0; continue; } else { log_write("CONF","%s:%i: unknown key, ignoring key-value pair; key:\"%s\"\n",configfile,lineno,ptr); continue; } /* store value */ if(*configvalue!=NULL) { log_write("CONF","%s:%i: duplicate key, ignoring key-value pair; key:\"%s\"\n",configfile,lineno,ptr); continue; } if((*configvalue=strdup(value))==NULL) { fclose(f),f=NULL; kaconfig_free(config),config=NULL; return(NULL); /* insufficient memory */ } continue; } else { log_write("CONF","%s:%i: malformed line, ignoring; contents:\"%s\"\n",configfile,lineno,ptr); continue; } } fclose(f),f=NULL; return(config); } void kaconfig_free(kaconfig *config) { if(config==NULL) return; if(config->logfile!=NULL) free(config->logfile),config->logfile=NULL; if(config->cookiename!=NULL) free(config->cookiename),config->cookiename=NULL; if(config->cookiedomain!=NULL) free(config->cookiedomain),config->cookiedomain=NULL; if(config->bannerpath!=NULL) free(config->bannerpath),config->bannerpath=NULL; free(config),config=NULL; return; } int kaconfig_exists(char *configfile) { struct stat st; if(stat(configfile,&st)!=0) return(-1); return(0); } int kaconfig_write(char *configfile,char *logfile, char *cookiename,char *cookiedomain, char *bannerpath, int sslproxy) { FILE *f; if((f=fopen(configfile,"w"))==NULL) return(-1); fprintf(f,"; kakumei config file\n"); fprintf(f,"[general]\n"); fprintf(f,"logfile=%s\n",(logfile!=NULL)?logfile:"kakumei.log"); fprintf(f,"cookiename=%s\n",(cookiename!=NULL)?cookiename:"kakumeiauthid"); fprintf(f,"cookiedomain=%s\n",(cookiedomain!=NULL)?cookiedomain:"localhost"); fprintf(f,"bannerpath=%s\n",(bannerpath!=NULL)?bannerpath:"default.png"); fprintf(f,"sslproxy=%s\n",(sslproxy==0)?"no":"yes"); return(0); }