More incremental config changes
This commit is contained in:
parent
49e9b3be32
commit
3d27be7405
|
@ -32,18 +32,75 @@
|
|||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "conf.h"
|
||||
#include "err.h"
|
||||
#include "ll.h"
|
||||
#include "daapd.h"
|
||||
|
||||
/** Globals */
|
||||
int ecode;
|
||||
LL_HANDLE config_main=NULL;
|
||||
static int ecode;
|
||||
static LL_HANDLE config_main=NULL;
|
||||
|
||||
#define CONFIG_LINEBUFFER 128
|
||||
|
||||
#define CONF_T_INT 0
|
||||
#define CONF_T_STRING 1
|
||||
|
||||
/** Forwards */
|
||||
static int _ll_verify(LL_HANDLE pll);
|
||||
|
||||
|
||||
|
||||
typedef struct _CONF_ELEMENTS {
|
||||
int required;
|
||||
int deprecated;
|
||||
int type;
|
||||
char *section;
|
||||
char *term;
|
||||
} CONF_ELEMENTS;
|
||||
|
||||
static CONF_ELEMENTS conf_elements[] = {
|
||||
{ 1, 0, CONF_T_STRING,"general","runas" },
|
||||
{ 1, 0, CONF_T_STRING,"general","web_root" },
|
||||
{ 1, 0, CONF_T_INT,"general","port" },
|
||||
{ 1, 0, CONF_T_STRING,"general","admin_pw" },
|
||||
{ 1, 0, CONF_T_STRING,"general","mp3_dir" },
|
||||
{ 0, 1, CONF_T_STRING,"general","db_dir" },
|
||||
{ 0, 0, CONF_T_STRING,"general","db_type" },
|
||||
{ 0, 0, CONF_T_STRING,"general","db_parms" },
|
||||
{ 0, 0, CONF_T_INT,"general","debuglevel" },
|
||||
{ 1, 0, CONF_T_STRING,"general","servername" },
|
||||
{ 0, 0, CONF_T_INT,"general","rescan_interval" },
|
||||
{ 0, 0, CONF_T_INT,"general","always_scan" },
|
||||
{ 0, 1, CONF_T_INT,"general","latin1_tags" },
|
||||
{ 0, 0, CONF_T_INT,"general","process_m3u" },
|
||||
{ 0, 0, CONF_T_INT,"general","scan_type" },
|
||||
{ 0, 1, CONF_T_INT,"general","compress" },
|
||||
{ 0, 0, CONF_T_STRING,"general","playlist" },
|
||||
{ 0, 0, CONF_T_STRING,"general","extensions" },
|
||||
{ 0, 0, CONF_T_STRING,"general","interface" },
|
||||
{ 0, 0, CONF_T_STRING,"general","ssc_codectypes" },
|
||||
{ 0, 0, CONF_T_STRING,"general","ssc_prog" },
|
||||
{ 0, 0, CONF_T_STRING,"general","password" },
|
||||
{ 0, 0, CONF_T_STRING,"general","compdirs" },
|
||||
{ 0, 0, CONF_T_STRING,"general","logfile" }
|
||||
};
|
||||
|
||||
/**
|
||||
* read a configfile into a bag
|
||||
* check a tree and make sure it doesn't have any obviously bad
|
||||
* configuration information
|
||||
*
|
||||
* @param pll tree to check
|
||||
*/
|
||||
int _ll_verify(LL_HANDLE pll) {
|
||||
|
||||
|
||||
return LL_E_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* read a configfile into a tree
|
||||
*
|
||||
* @param file file to read
|
||||
* @returns TRUE if successful, FALSE otherwise
|
||||
|
@ -51,26 +108,30 @@ LL_HANDLE config_main=NULL;
|
|||
int config_read(char *file) {
|
||||
FILE *fin;
|
||||
int err;
|
||||
LL_HANDLE pllnew, plltemp;
|
||||
LL_HANDLE pllnew, plltemp, pllcurrent;
|
||||
char linebuffer[CONFIG_LINEBUFFER+1];
|
||||
char *comment, *term, *value, *delim;
|
||||
int compat_mode=1;
|
||||
int line=0;
|
||||
|
||||
fin=fopen(file,"r");
|
||||
if(!fin) {
|
||||
return CONFIG_E_FOPEN;
|
||||
return CONF_E_FOPEN;
|
||||
}
|
||||
|
||||
if((err=ll_create(&pllnew)) != LL_E_SUCCESS) {
|
||||
DPRINTF(E_LOG,L_CONF,"Error creating linked list: %d\n",err);
|
||||
fclose(fin);
|
||||
return CONFIG_E_UNKNOWN;
|
||||
return CONF_E_UNKNOWN;
|
||||
}
|
||||
|
||||
pllcurrent=NULL;
|
||||
|
||||
/* got what will be the root of the config tree, now start walking through
|
||||
* the input file, populating the tree
|
||||
*/
|
||||
while(fgets(linebuffer,CONFIG_LINEBUFFER,fin)) {
|
||||
line++;
|
||||
linebuffer[CONFIG_LINEBUFFER] = '\0';
|
||||
|
||||
comment=strchr(linebuffer,'#');
|
||||
|
@ -90,17 +151,18 @@ int config_read(char *file) {
|
|||
if(!value) {
|
||||
ll_destroy(pllnew);
|
||||
fclose(fin);
|
||||
return CONFIG_E_BADHEADER;
|
||||
return CONF_E_BADHEADER;
|
||||
}
|
||||
*value = '\0';
|
||||
|
||||
if((err = ll_create(&plltemp)) != LL_E_SUCCESS) {
|
||||
ll_destroy(pllnew);
|
||||
fclose(fin);
|
||||
return CONFIG_E_UNKNOWN;
|
||||
return CONF_E_UNKNOWN;
|
||||
}
|
||||
|
||||
ll_add_ll(pllnew,term,plltemp);
|
||||
pllcurrent = plltemp;
|
||||
} else {
|
||||
/* k/v pair */
|
||||
term=&linebuffer[0];
|
||||
|
@ -121,7 +183,23 @@ int config_read(char *file) {
|
|||
while(strlen(value) && (strchr("\t ",*value)))
|
||||
value++;
|
||||
|
||||
ll_add_string(pllnew,term,value);
|
||||
if(!pllcurrent) {
|
||||
/* we are definately in compat mode -- add a general section */
|
||||
if((err=ll_create(&plltemp)) != LL_E_SUCCESS) {
|
||||
DPRINTF(E_LOG,L_CONF,"Error creating linked list: %d\n",err);
|
||||
ll_destroy(pllnew);
|
||||
fclose(fin);
|
||||
return CONF_E_UNKNOWN;
|
||||
}
|
||||
ll_add_ll(pllnew,"general",plltemp);
|
||||
pllcurrent = plltemp;
|
||||
}
|
||||
ll_add_string(pllcurrent,term,value);
|
||||
}
|
||||
if(((term) && (strlen(term))) && (!value)) {
|
||||
DPRINTF(E_LOG,L_CONF,"Error in config file on line %d\n",line);
|
||||
ll_destroy(pllnew);
|
||||
return CONF_E_PARSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -129,16 +207,18 @@ int config_read(char *file) {
|
|||
fclose(fin);
|
||||
|
||||
/* Sanity check */
|
||||
_ll_verify(pllnew);
|
||||
|
||||
ll_dump(pllnew);
|
||||
ll_destroy(pllnew);
|
||||
|
||||
return CONFIG_E_SUCCESS;
|
||||
return CONF_E_SUCCESS;
|
||||
}
|
||||
|
||||
int config_close(void) {
|
||||
if(config_main)
|
||||
ll_destroy(config_main);
|
||||
|
||||
return CONFIG_E_SUCCESS;
|
||||
return CONF_E_SUCCESS;
|
||||
}
|
||||
|
|
@ -22,10 +22,11 @@
|
|||
#ifndef _CONFIG_H_
|
||||
#define _CONFIG_H_
|
||||
|
||||
#define CONFIG_E_SUCCESS 0
|
||||
#define CONFIG_E_FOPEN 1
|
||||
#define CONFIG_E_UNKNOWN 2
|
||||
#define CONFIG_E_BADHEADER 3
|
||||
#define CONF_E_SUCCESS 0
|
||||
#define CONF_E_FOPEN 1
|
||||
#define CONF_E_UNKNOWN 2
|
||||
#define CONF_E_BADHEADER 3
|
||||
#define CONF_E_PARSE 4
|
||||
|
||||
|
||||
extern int config_read(char *file);
|
|
@ -4,13 +4,20 @@
|
|||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "config.h"
|
||||
#include "conf.h"
|
||||
#include "err.h"
|
||||
|
||||
int main(int argc, char *argv[]) {
|
||||
if(config_read(argv[1]) != CONFIG_E_SUCCESS) {
|
||||
printf("Read config!\n");
|
||||
int err;
|
||||
|
||||
err_debuglevel = 9;
|
||||
|
||||
printf("Reading %s\n",argv[1]);
|
||||
|
||||
if((err=config_read(argv[1])) != CONF_E_SUCCESS) {
|
||||
printf("Error reading config: %d\n",err);
|
||||
} else {
|
||||
printf("Error reading config\n");
|
||||
printf("Read config!\n");
|
||||
}
|
||||
config_close();
|
||||
}
|
||||
|
|
|
@ -2,8 +2,8 @@
|
|||
CC=gcc
|
||||
CFLAGS := $(CFLAGS) -g -DHAVE_CONFIG_H -I. -I..
|
||||
LDFLAGS := $(LDFLAGS)
|
||||
TARGET = config
|
||||
OBJECTS=config-driver.o config.o ll.o
|
||||
TARGET = conf
|
||||
OBJECTS=config-driver.o conf.o ll.o err.o
|
||||
|
||||
$(TARGET): $(OBJECTS)
|
||||
$(CC) -o $(TARGET) $(LDFLAGS) $(OBJECTS)
|
||||
|
|
64
src/ll.c
64
src/ll.c
|
@ -34,6 +34,7 @@
|
|||
/** Internal functions */
|
||||
|
||||
int _ll_add_item(LL *pl, char *key, void *vpval, int ival, int type);
|
||||
void _ll_dump(LL *pl, int depth);
|
||||
|
||||
/**
|
||||
* create a ll
|
||||
|
@ -47,6 +48,9 @@ int ll_create(LL **ppl) {
|
|||
return LL_E_MALLOC;
|
||||
|
||||
memset(*ppl,0x0,sizeof(struct _LL));
|
||||
|
||||
/* set default flags */
|
||||
(*ppl)->flags = LL_FLAG_NODUPS | LL_FLAG_INHERIT;
|
||||
return LL_E_SUCCESS;
|
||||
}
|
||||
|
||||
|
@ -88,7 +92,7 @@ int ll_destroy(LL *pl) {
|
|||
* thin wrapper for _ll_add_item
|
||||
*/
|
||||
int ll_add_string(LL *pl, char *key, char *cval) {
|
||||
return _ll_add_item(pl,cval,key,0,LL_TYPE_STRING);
|
||||
return _ll_add_item(pl,key,cval,0,LL_TYPE_STRING);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -102,7 +106,15 @@ int ll_add_int(LL *pl, char *key, int ival) {
|
|||
* thin wrapper for _ll_add_item
|
||||
*/
|
||||
int ll_add_ll(LL *pl, char *key, LL *pnew) {
|
||||
return _ll_add_item(pl,key,(void*)pnew,0,LL_TYPE_LL);
|
||||
int result;
|
||||
|
||||
result = _ll_add_item(pl,key,(void*)pnew,0,LL_TYPE_LL);
|
||||
if(result == LL_E_SUCCESS) {
|
||||
if(pl->flags & LL_FLAG_INHERIT) {
|
||||
pnew->flags = pl->flags;
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -111,6 +123,11 @@ int ll_add_ll(LL *pl, char *key, LL *pnew) {
|
|||
int _ll_add_item(LL *pl, char *key, void* vpval, int ival, int type) {
|
||||
LL_ITEM *pli;
|
||||
|
||||
if(pl->flags & LL_FLAG_NODUPS) {
|
||||
if(ll_fetch_item(pl,key))
|
||||
return LL_E_DUP;
|
||||
}
|
||||
|
||||
pli=(LL_ITEM *)malloc(sizeof(LL_ITEM));
|
||||
if(!pli) {
|
||||
return LL_E_MALLOC;
|
||||
|
@ -138,7 +155,11 @@ int _ll_add_item(LL *pl, char *key, void* vpval, int ival, int type) {
|
|||
pl->itemlist.next = pli;
|
||||
} else {
|
||||
pli->next = NULL;
|
||||
pl->tailptr->next = pli;
|
||||
if(pl->tailptr) {
|
||||
pl->tailptr->next = pli;
|
||||
} else {
|
||||
pl->itemlist.next = pli;
|
||||
}
|
||||
pl->tailptr = pli;
|
||||
}
|
||||
|
||||
|
@ -160,10 +181,11 @@ LL_ITEM *ll_fetch_item(LL *pl, char *key) {
|
|||
current = pl->itemlist.next;
|
||||
while(current) {
|
||||
if(pl->flags & LL_FLAG_HONORCASE) {
|
||||
if(!strcasecmp(current->key,key))
|
||||
break;
|
||||
if(!strcmp(current->key,key))
|
||||
break;
|
||||
return current;
|
||||
} else {
|
||||
if(!strcasecmp(current->key,key))
|
||||
return current;
|
||||
}
|
||||
current = current->next;
|
||||
}
|
||||
|
@ -198,7 +220,35 @@ int ll_get_flags(LL *pl, unsigned int *flags) {
|
|||
*
|
||||
* @parm pl linked list to dump
|
||||
*/
|
||||
extern void ll_dump(LL *pl) {
|
||||
void ll_dump(LL *pl) {
|
||||
_ll_dump(pl,0);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Internal support function for dumping linked list that
|
||||
* carries depth.
|
||||
*
|
||||
* @param pl linked list to dump
|
||||
* @param depth depth of list
|
||||
*/
|
||||
|
||||
void _ll_dump(LL *pl, int depth) {
|
||||
LL_ITEM *pli;
|
||||
pli = pl->itemlist.next;
|
||||
while(pli) {
|
||||
switch(pli->type) {
|
||||
case LL_TYPE_INT:
|
||||
printf("%*s%s (int): %d\n",depth*2,"",pli->key,pli->value.as_int);
|
||||
break;
|
||||
case LL_TYPE_STRING:
|
||||
printf("%*s%s (string): %s\n",depth*2,"",pli->key,pli->value.as_string);
|
||||
break;
|
||||
case LL_TYPE_LL:
|
||||
printf("%*s%s (list)\n",depth*2,"",pli->key);
|
||||
_ll_dump(pli->value.as_ll,depth+1);
|
||||
break;
|
||||
}
|
||||
pli = pli->next;
|
||||
}
|
||||
}
|
||||
|
|
4
src/ll.h
4
src/ll.h
|
@ -30,10 +30,12 @@
|
|||
#define LL_E_SUCCESS 0
|
||||
#define LL_E_MALLOC 1
|
||||
#define LL_E_NOKEY 2
|
||||
#define LL_E_DUP 3
|
||||
|
||||
#define LL_FLAG_HONORCASE 1 /** Make keys case sensitive */
|
||||
#define LL_FLAG_HEADINSERT 2 /** Insert at head, rather than tail */
|
||||
|
||||
#define LL_FLAG_NODUPS 4 /** Do not allow duplicates */
|
||||
#define LL_FLAG_INHERIT 8 /** Set child flags based on parent flags */
|
||||
|
||||
typedef struct _LLITEM {
|
||||
int type;
|
||||
|
|
Loading…
Reference in New Issue