From 0fc6fd13c5bd44e6d595b56337a95156fd42ceea Mon Sep 17 00:00:00 2001 From: Fredrik Tolf Date: Wed, 25 Aug 2010 02:05:05 +0200 Subject: [PATCH] Added global config files to dirplex and patplex. --- lib/cf.c | 20 ++++++++++++++++++++ lib/cf.h | 1 + src/dirplex.c | 54 +++++++++++++++++++++++++++++++++++++++++++++++------ src/patplex.c | 60 ++++++++++++++++++++++++++++++++++++++++++++++++++++------- 4 files changed, 122 insertions(+), 13 deletions(-) diff --git a/lib/cf.c b/lib/cf.c index 3314e4a..f55a620 100644 --- a/lib/cf.c +++ b/lib/cf.c @@ -221,6 +221,26 @@ void freecfparser(struct cfstate *s) free(s); } +char *findstdconf(char *name) +{ + char *path, *p, *p2, *t; + + if((path = getenv("PATH")) == NULL) + return(NULL); + path = sstrdup(path); + for(p = strtok(path, ":"); p != NULL; p = strtok(NULL, ":")) { + if((p2 = strrchr(p, '/')) == NULL) + continue; + *p2 = 0; + if(!access(t = sprintf3("%s/etc/%s", p, name), R_OK)) { + free(path); + return(sstrdup(t)); + } + } + free(path); + return(NULL); +} + static struct child *newchild(char *name, int type) { struct child *ch; diff --git a/lib/cf.h b/lib/cf.h index 09dad29..45e7698 100644 --- a/lib/cf.h +++ b/lib/cf.h @@ -24,6 +24,7 @@ void skipcfblock(struct cfstate *s); struct cfstate *mkcfparser(FILE *in, char *name); void freecfparser(struct cfstate *s); char **getcfline(struct cfstate *s); +char *findstdconf(char *name); void freechild(struct child *ch); struct child *parsechild(struct cfstate *s); diff --git a/src/dirplex.c b/src/dirplex.c index fa4bae5..6595201 100644 --- a/src/dirplex.c +++ b/src/dirplex.c @@ -62,7 +62,8 @@ struct pattern { struct rule **rules; }; -struct config *cflist; +static struct config *cflist; +static struct config *gconfig, *lconfig; static time_t now; static void freepattern(struct pattern *pat) @@ -90,7 +91,8 @@ static void freeconfig(struct config *cf) cf->next->prev = cf->prev; if(cf == cflist) cflist = cf->next; - free(cf->path); + if(cf->path != NULL) + free(cf->path); for(ch = cf->children; ch != NULL; ch = nch) { nch = ch->next; freechild(ch); @@ -301,6 +303,10 @@ static struct config **getconfigs(char *file) free(tmp); if((cf = getconfig(".")) != NULL) bufadd(buf, cf); + if(lconfig != NULL) + bufadd(buf, lconfig); + if(gconfig != NULL) + bufadd(buf, gconfig); bufadd(buf, NULL); return(ret = buf.b); } @@ -506,17 +512,53 @@ out: free(path); } +static void usage(FILE *out) +{ + fprintf(out, "usage: dirplex [-hN] [-c CONFIG] DIR\n"); +} + int main(int argc, char **argv) { + int c; + int nodef; + char *gcf, *lcf; struct hthead *req; int fd; - if(argc < 2) { - flog(LOG_ERR, "usage: dirplex DIR"); + nodef = 0; + lcf = NULL; + while((c = getopt(argc, argv, "hNc:")) >= 0) { + switch(c) { + case 'h': + usage(stdout); + exit(0); + case 'N': + nodef = 1; + break; + case 'c': + lcf = optarg; + break; + default: + usage(stderr); + exit(1); + } + } + if(argc - optind < 1) { + usage(stderr); exit(1); } - if(chdir(argv[1])) { - flog(LOG_ERR, "could not change directory to %s: %s", argv[1], strerror(errno)); + if(!nodef) { + if((gcf = findstdconf("ashd/dirplex.rc")) != NULL) { + gconfig = readconfig(gcf); + free(gcf); + } + } + if(lcf != NULL) { + if((lconfig = readconfig(lcf)) == NULL) + exit(1); + } + if(chdir(argv[optind])) { + flog(LOG_ERR, "could not change directory to %s: %s", argv[optind], strerror(errno)); exit(1); } signal(SIGCHLD, SIG_IGN); diff --git a/src/patplex.c b/src/patplex.c index 26c6bd3..2ea28d5 100644 --- a/src/patplex.c +++ b/src/patplex.c @@ -63,7 +63,7 @@ struct pattern { char *restpat; }; -static struct config *config; +static struct config *gconfig, *lconfig; static void freepattern(struct pattern *pat) { @@ -393,11 +393,29 @@ static void serve(struct hthead *req, int fd) char *chnm; struct child *ch; - if(((chnm = findmatch(config, req, 0)) == NULL) && ((chnm = findmatch(config, req, 1)) == NULL)) { + chnm = NULL; + if(chnm == NULL) + chnm = findmatch(lconfig, req, 0); + if(chnm == NULL) + chnm = findmatch(lconfig, req, 1); + if(gconfig != NULL) { + if(chnm == NULL) + chnm = findmatch(gconfig, req, 0); + if(chnm == NULL) + chnm = findmatch(gconfig, req, 1); + } + if(chnm == NULL) { simpleerror(fd, 404, "Not Found", "The requested resource could not be found on this server."); return; } - if((ch = getchild(config, chnm)) == NULL) { + ch = NULL; + if(ch == NULL) + ch = getchild(lconfig, chnm); + if(gconfig != NULL) { + if(ch == NULL) + ch = getchild(gconfig, chnm); + } + if(ch == NULL) { flog(LOG_ERR, "child %s requested, but was not declared", chnm); simpleerror(fd, 500, "Configuration Error", "The server is erroneously configured. Handler %s was requested, but not declared.", chnm); return; @@ -407,16 +425,44 @@ static void serve(struct hthead *req, int fd) simpleerror(fd, 500, "Server Error", "The request handler crashed."); } +static void usage(FILE *out) +{ + fprintf(out, "usage: patplex [-hN] CONFIGFILE\n"); +} + int main(int argc, char **argv) { + int c; + int nodef; + char *gcf; struct hthead *req; int fd; - - if(argc < 2) { - flog(LOG_ERR, "usage: patplex CONFIGFILE"); + + nodef = 0; + while((c = getopt(argc, argv, "hN")) >= 0) { + switch(c) { + case 'h': + usage(stdout); + exit(0); + case 'N': + nodef = 1; + break; + default: + usage(stderr); + exit(1); + } + } + if(argc - optind < 1) { + usage(stderr); exit(1); } - config = readconfig(argv[1]); + if(!nodef) { + if((gcf = findstdconf("ashd/patplex.rc")) != NULL) { + gconfig = readconfig(gcf); + free(gcf); + } + } + lconfig = readconfig(argv[optind]); signal(SIGCHLD, SIG_IGN); while(1) { if((fd = recvreq(0, &req)) < 0) { -- 2.11.0