X-Git-Url: http://www.dolda2000.com/gitweb/?a=blobdiff_plain;f=src%2Fdirplex.c;h=8e4ae11629a61bc695c03f53e8d3ba377a842add;hb=9bebca54879412ae5879695800ceac77eb2c805c;hp=52313cc594dd5c6a8b3825742d9368b3eac3155d;hpb=1604c0967129b4b348f3c6150f5a2c87f780e404;p=ashd.git diff --git a/src/dirplex.c b/src/dirplex.c index 52313cc..8e4ae11 100644 --- a/src/dirplex.c +++ b/src/dirplex.c @@ -43,6 +43,9 @@ #define PAT_ALL 2 #define PAT_DEFAULT 3 +#define PT_FILE 0 +#define PT_DIR 1 + struct config { struct config *next, *prev; char *path; @@ -59,6 +62,7 @@ struct rule { struct pattern { struct pattern *next; + int type; char *childnm; char **fchild; struct rule **rules; @@ -169,6 +173,8 @@ static struct pattern *parsepattern(struct cfstate *s) return(NULL); } + if((s->argc > 1) && !strcmp(s->argv[1], "directory")) + pat->type = PT_DIR; sl = s->lno; while(1) { getcfline(s); @@ -355,7 +361,7 @@ static struct child *findchild(char *file, char *name) return(ch); } -static struct pattern *findmatch(char *file, int trydefault) +static struct pattern *findmatch(char *file, int trydefault, int dir) { int i, o, c; char *bn; @@ -370,6 +376,10 @@ static struct pattern *findmatch(char *file, int trydefault) cfs = getconfigs(file); for(c = 0; cfs[c] != NULL; c++) { for(pat = cfs[c]->patterns; pat != NULL; pat = pat->next) { + if(!dir && (pat->type == PT_DIR)) + continue; + if(dir && (pat->type != PT_DIR)) + continue; for(i = 0; (rule = pat->rules[i]) != NULL; i++) { if(rule->type == PAT_BASENAME) { for(o = 0; rule->patterns[o] != NULL; o++) { @@ -395,19 +405,16 @@ static struct pattern *findmatch(char *file, int trydefault) return(pat); } } + if(!trydefault) + return(findmatch(file, 1, dir)); return(NULL); } -static void handlefile(struct hthead *req, int fd, char *path) +static void handle(struct hthead *req, int fd, char *path, struct pattern *pat) { - struct pattern *pat; struct child *ch; headappheader(req, "X-Ash-File", path); - if(((pat = findmatch(path, 0)) == NULL) && ((pat = findmatch(path, 1)) == NULL)) { - simpleerror(fd, 404, "Not Found", "The requested URL has no corresponding resource."); - return; - } if(pat->fchild) { stdforkserve(pat->fchild, req, fd); } else { @@ -421,16 +428,29 @@ static void handlefile(struct hthead *req, int fd, char *path) } } +static void handlefile(struct hthead *req, int fd, char *path) +{ + struct pattern *pat; + + if((pat = findmatch(path, 0, 0)) == NULL) { + simpleerror(fd, 404, "Not Found", "The requested URL has no corresponding resource."); + return; + } + handle(req, fd, path, pat); +} + static void handledir(struct hthead *req, int fd, char *path) { struct config **cfs; int i, o; struct stat sb; - char *inm, *ipath, *p; + char *inm, *ipath, *p, *cpath; DIR *dir; struct dirent *dent; + struct pattern *pat; - cfs = getconfigs(sprintf3("%s/", path)); + cpath = sprintf2("%s/", path); + cfs = getconfigs(cpath); for(i = 0; cfs[i] != NULL; i++) { if(cfs[i]->index != NULL) { for(o = 0; cfs[i]->index[o] != NULL; o++) { @@ -439,7 +459,7 @@ static void handledir(struct hthead *req, int fd, char *path) if(!stat(ipath, &sb) && S_ISREG(sb.st_mode)) { handlefile(req, fd, ipath); free(ipath); - return; + goto out; } free(ipath); @@ -463,14 +483,20 @@ static void handledir(struct hthead *req, int fd, char *path) if(ipath != NULL) { handlefile(req, fd, ipath); free(ipath); - return; + goto out; } } break; } } - /* XXX: Directory listings */ + if((pat = findmatch(cpath, 0, 1)) != NULL) { + handle(req, fd, cpath, pat); + goto out; + } simpleerror(fd, 403, "Not Authorized", "Will not send listings for this directory."); + +out: + free(cpath); } static int checkdir(struct hthead *req, int fd, char *path) @@ -614,7 +640,7 @@ int main(int argc, char **argv) { int c; int nodef; - char *gcf, *lcf; + char *gcf, *lcf, *clcf; struct hthead *req; int fd; @@ -647,8 +673,18 @@ int main(int argc, char **argv) } } if(lcf != NULL) { - if((lconfig = readconfig(lcf)) == NULL) - exit(1); + if(strchr(lcf, '/') == NULL) { + if((clcf = findstdconf(sprintf3("ashd/%s", lcf))) == NULL) { + flog(LOG_ERR, "could not find requested configuration `%s'", lcf); + exit(1); + } + if((lconfig = readconfig(clcf)) == NULL) + exit(1); + free(clcf); + } else { + 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));