New configuration loader

Mon, 13 Feb 2012 13:49:49 +0100

author
Olaf Wintermann <olaf.wintermann@gmail.com>
date
Mon, 13 Feb 2012 13:49:49 +0100
changeset 21
627b09ee74e4
parent 20
7b235fa88008
child 22
adb0bda54e6b

New configuration loader

src/server/config/conf.c file | annotate | diff | comparison | revisions
src/server/config/conf.h file | annotate | diff | comparison | revisions
src/server/config/initconf.c file | annotate | diff | comparison | revisions
src/server/daemon/config.c file | annotate | diff | comparison | revisions
src/server/daemon/config.h file | annotate | diff | comparison | revisions
src/server/daemon/configmanager.c file | annotate | diff | comparison | revisions
src/server/daemon/configmanager.h file | annotate | diff | comparison | revisions
src/server/daemon/httplistener.c file | annotate | diff | comparison | revisions
src/server/daemon/httprequest.c file | annotate | diff | comparison | revisions
src/server/daemon/protocol.c file | annotate | diff | comparison | revisions
src/server/daemon/request.c file | annotate | diff | comparison | revisions
src/server/public/nsapi.h file | annotate | diff | comparison | revisions
src/server/safs/service.c file | annotate | diff | comparison | revisions
src/server/ucx/map.c file | annotate | diff | comparison | revisions
src/server/ucx/string.c file | annotate | diff | comparison | revisions
--- a/src/server/config/conf.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/config/conf.c	Mon Feb 13 13:49:49 2012 +0100
@@ -259,6 +259,7 @@
  */
 ConfigDirective* cfg_parse_directive(sstr_t line, UcxMempool *mp) {
     if(line.length < 6) {
+        printf("line too short\n");
         return NULL; // line too short
     }
 
@@ -487,3 +488,53 @@
 
     return tag;
 }
+
+
+/* directive functions */
+
+/*
+ * gets a ConfigDirective with a specific name from a List of directives
+ * returns a directive or NULL, if the directive cannot be found
+ */
+ConfigDirective* cfg_directivelist_get(UcxDlist *dirs, sstr_t name) {
+    while(dirs != NULL) {
+        ConfigDirective *d = dirs->data;
+        if(d != NULL) {
+            if(!sstrcmp(d->directive_type, name)) {
+                return d;
+            }
+        }
+        dirs = dirs->next;
+    }
+    return NULL;
+}
+
+sstr_t cfg_directivelist_get_str(UcxDlist *dirs, sstr_t name) {
+    ConfigDirective *d = cfg_directivelist_get(dirs, name);
+    if(d == NULL) {
+        sstr_t n;
+        n.ptr = NULL;
+        n.length = 0;
+        return n;
+    }
+    return cfg_directive_pstr1(d);
+}
+
+/*
+ * returns the name of the first parameter of the directive
+ * useful for 'name value' directives
+ */
+sstr_t cfg_directive_pstr1(ConfigDirective *dir) {
+    if(dir->param == NULL) {
+        fprintf(stderr, "%s", "Error: cfg_directive_pstr1: param is NULL\n");
+        sstr_t n;
+        n.ptr = NULL;
+        n.length = 0;
+        return n;
+    }
+
+    ConfigParam *p = dir->param->data;
+    return p->name;
+}
+
+
--- a/src/server/config/conf.h	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/config/conf.h	Mon Feb 13 13:49:49 2012 +0100
@@ -129,6 +129,12 @@
 
 ConfigTag* cfg_parse_begin_tag(sstr_t line, UcxMempool *mp);
 
+ConfigDirective* cfg_directivelist_get(UcxDlist *dirs, sstr_t name);
+
+sstr_t cfg_directivelist_get_str(UcxDlist *dirs, sstr_t name);
+
+sstr_t cfg_directive_pstr1(ConfigDirective *dir);
+
 #ifdef	__cplusplus
 }
 #endif
--- a/src/server/config/initconf.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/config/initconf.c	Mon Feb 13 13:49:49 2012 +0100
@@ -67,6 +67,10 @@
 
     // parse directive
     ConfigDirective *d = cfg_parse_directive(line, conf->parser.mp);
+    if(d == NULL) {
+        fprintf(stderr, "Error: initconf_parse: directive is null\n");
+        return 0;
+    }
     d->begin = begin;
     d->end = end;
     if(d->type_num == 6) {
--- a/src/server/daemon/config.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/config.c	Mon Feb 13 13:49:49 2012 +0100
@@ -42,6 +42,7 @@
 #include "httplistener.h"
 #include "config.h"
 #include "func.h"
+#include "configmanager.h"
 
 #include "vserver.h"
 #include "../util/pblock.h"
@@ -50,10 +51,6 @@
 
 // TODO: Funktion für ConfigDirective -> directive
 // TODO: Funktion für UcxList parameter list -> pblock
-// TODO: ConfigurationManager
-// TODO: server.conf
-
-UcxMap *server_conf_handlers; // type: ServerConfigHandler*
 
 void load_init_conf(char *file) {
     printf("load_init_conf\n");
@@ -102,7 +99,7 @@
     free_init_config(cfg);
 }
 
-ServerConfiguration* load_server_conf(char *file) {
+ServerConfiguration* load_server_conf(ServerConfiguration *old, char *file) {
     printf("load_server_conf\n");
 
     ServerConfig *serverconf = load_server_config(file);
@@ -123,39 +120,22 @@
             while(list != NULL) {
                 ServerConfigObject *scfgobj = list->data;
 
-                /* get handler */
-                ServerConfigHandler *handler = ucx_map_sstr_get(
-                        server_conf_handlers,
-                        scfgobj->type);
-                if(handler != NULL) {
-                    void *object_data = NULL;
-                    if(handler->element_start != NULL) {
-                        object_data = handler->element_start(
-                                handler,
-                                serverconfig);
-                    }
-
-                    /* process the directives */
-                    UcxDlist *dirs = scfgobj->directives;
-                    while(dirs != NULL) {
-                        handler->process_directive(
-                                handler,
-                                serverconfig,
-                                dirs->data,
-                                object_data);
-                        
-                        dirs = dirs->next;
-                    }
-
-                    if(handler->element_end != NULL) {
-                        handler->element_end(
-                                handler,
-                                serverconfig,
-                                NULL,
-                                object_data);
-                    }
+                /* handle config object */
+                int hr = 0;
+                if(!sstrcmp(scfgobj->type, sstr("Runtime"))) {
+                    hr = cfg_handle_runtime(serverconfig, scfgobj);
+                } else if(!sstrcmp(scfgobj->type, sstr("LogFile"))) {
+                    hr = cfg_handle_logfile(serverconfig, scfgobj);
+                } else if(!sstrcmp(scfgobj->type, sstr("AuthDB"))) {
+                    hr = cfg_handle_authdb(serverconfig, scfgobj);
+                } else if(!sstrcmp(scfgobj->type, sstr("Listener"))) {
+                    hr = cfg_handle_listener(serverconfig, scfgobj);
+                } else if(!sstrcmp(scfgobj->type, sstr("VirtualServer"))) {
+                    hr = cfg_handle_vs(serverconfig, scfgobj);
                 }
 
+
+                /* next object */
                 list = list->next;
             }
             
@@ -163,6 +143,8 @@
         }
     }
 
+
+
     /* set VirtualServer for all listeners */
     UcxList *ls = serverconfig->listeners;
     while(ls) {
@@ -198,158 +180,103 @@
 
 
 void init_server_config_parser() {
-    /* create handler map */
-    server_conf_handlers = ucx_map_new(8);
-
-    /* create and add default handlers */
+    
+}
 
-    ServerConfigHandler *runtime = calloc(1, sizeof(ServerConfigHandler));
-    runtime->init = NULL;
-    runtime->process_directive = handle_runtime_directive;
-
-    ucx_map_cstr_put(server_conf_handlers, "Runtime", runtime);
-
+int cfg_handle_runtime(ServerConfiguration *cfg, ServerConfigObject *obj) {
+    cfg->user = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("User")));
+    cfg->tmp = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("Temp")));
 
-    ServerConfigHandler *listener = calloc(1, sizeof(ServerConfigHandler));
-    listener->init = NULL;
-    listener->element_start = handle_listener_start;
-    listener->element_end = handle_listener_end;
-    listener->process_directive = handle_listener_directive;
+    return 0;
+}
 
-    ucx_map_cstr_put(server_conf_handlers, "Listener", listener);
-
+int cfg_handle_logfile(ServerConfiguration *cfg, ServerConfigObject *obj) {
+    /* TODO: log files */
 
-    ServerConfigHandler *vserver = calloc(1, sizeof(ServerConfigHandler));
-    vserver->init = NULL;
-    vserver->element_start = handle_vserver_start;
-    vserver->element_end = handle_vserver_end;
-    vserver->process_directive = handle_vserver_directive;
+    return 0;
+}
 
-    ucx_map_cstr_put(server_conf_handlers, "VirtualServer", vserver);
+int cfg_handle_authdb(ServerConfiguration *cfg, ServerConfigObject *obj) {
+    /* TODO: authdb*/
 
-
+    return 0;
 }
 
-/*
- *  server.conf handlers
- */
-int handle_runtime_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data)
-{
+int cfg_handle_listener(ServerConfiguration *cfg, ServerConfigObject *obj) {
+    ListenerConfig lc;
+    lc.port = 8080;
+    lc.nacceptors = 1;
+
+    lc.name = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("Name")));
+    lc.port = atoi(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("Port")).ptr);
+    lc.vs = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("DefaultVS")));
     
 
+    HttpListener *listener = http_listener_new(&lc);
+    listener->default_vs.vs_name = lc.vs.ptr;
+    cfg->listeners = ucx_list_append(cfg->listeners, listener); 
+
+    return 0;
+}
+
+int cfg_handle_vs(ServerConfiguration *cfg, ServerConfigObject *obj) {
+    VirtualServer *vs = vs_new();
+
+    vs->name = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("Name")));
+    vs->host = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("Host")));
+    vs->document_root = sstrdub(cfg_directivelist_get_str(
+            obj->directives,
+            sstr("DocRoot")));
+    sstr_t objfile = cfg_directivelist_get_str(
+            obj->directives,
+            sstr("ObjectFile"));
+    sstr_t base = sstr("conf/");
+    sstr_t file;
+    file.length = base.length + objfile.length + 1;
+    file.ptr = alloca(file.length);
+    file.ptr[file.length] = 0;
+    file = sstrncat(2, file, base, objfile);
+
+    ConfigFile *f = cfgmgr_get_file(file);
+    if(f == NULL) {
+        f = malloc(sizeof(ConfigFile));
+        f->file = sstrdub(file);
+        f->reload = object_conf_reload;
+        f->reload(f, cfg);
+        cfgmgr_attach_file(f);
+    }
+    vs->objects = (HTTPObjectConfig*)f->data;
+
+    ucx_map_sstr_put(cfg->host_vs, vs->host, vs);
+    
     return 0;
 }
 
 
-void* handle_listener_start(ServerConfigHandler *h, ServerConfiguration *cfg) {
-    /* free this in handle_listener_end */
-    ListenerConfig *listener = calloc(1, sizeof(ListenerConfig));
-    listener->nacceptors = 1;
-    listener->port = 0;
-    //printf("<Listener>\n");
-    return listener;
-}
-
-int handle_listener_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data)
-{
-    ListenerConfig *listener = data;
-    ConfigParam *param = dir->param->data;
-
-    if(!sstrcmp(dir->directive_type, sstr("Name"))) {
-        listener->name = sstrdub(param->name);
-        //printf("Name        %s\n", listener->name.ptr);
-    } else if(!sstrcmp(dir->directive_type, sstr("Port"))) {
-        listener->port = atoi(param->name.ptr);
-        //printf("Port        %d\n", listener->port);
-    } else if(!sstrcmp(dir->directive_type, sstr("DefaultVS"))) {
-        listener->vs = sstrdub(param->name);
-        //printf("DefaultVS   %s\n", param->name.ptr);
+int object_conf_reload(ConfigFile *file, ServerConfiguration *cfg) {
+    file->data = load_obj_conf(file->file.ptr);
+    struct stat s;
+    if(stat(file->file.ptr, &s) != 0) {
+        perror("object_conf_reload: stat");
+        return -1;
     }
-
-    return 0;
-}
-
-int handle_listener_end(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data)
-{
-    //printf("</Listener>\n\n");
-    /* add listener to server configuration */
-    ListenerConfig *lc = data;
-    HttpListener *listener = http_listener_new(lc);
-    listener->default_vs.vs_name = lc->vs.ptr;
-    //free(lc);
-    conf->listeners = ucx_list_append(conf->listeners, listener);
-
-    return 0;
+    file->last_modified = s.st_mtim.tv_sec;
 }
 
-
-void* handle_vserver_start(ServerConfigHandler *h, ServerConfiguration *cfg) {
-    //printf("<VirtualServer>\n");
-    VirtualServer *vs = vs_new();
-    return vs;
-}
-
-int handle_vserver_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data)
-{
-    VirtualServer *vs = data;
-    ConfigParam *param = dir->param->data;
-
-    if(!sstrcmp(dir->directive_type, sstr("Name"))) {
-        vs->name = sstrdub(param->name);
-        //printf("Name        %s\n", vs->name.ptr);
-    } else if(!sstrcmp(dir->directive_type, sstr("Host"))) {
-        vs->host = sstrdub(param->name);
-        //printf("Host        %s\n", vs->host.ptr);
-    } else if(!sstrcmp(dir->directive_type, sstr("ObjectFile"))) {
-        sstr_t base = sstr("conf/");
-        sstr_t file;
-        file.length = base.length + param->name.length + 1;
-        file.ptr = alloca(file.length);
-        file.ptr[file.length] = 0;
-        file = sstrncat(2, file, base, param->name);
-        //printf("ObjectFile  %s\n", file.ptr);
-
-        vs->objects = load_obj_conf(file.ptr);
-        
-    } else if(!sstrcmp(dir->directive_type, sstr("DocRoot"))) {
-        vs->document_root = sstrdub(param->name);
-    }
-    // TODO: Listener, ACLFile, DAVFile, DocRoot, ...
-
-    return 0;
-}
-
-int handle_vserver_end(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data)
-{
-    //printf("</VirtualServer>\n\n");
-    VirtualServer *vs = data;
-
-    ucx_map_sstr_put(conf->host_vs, vs->host, vs);
-
-    return 0;
-}
-
-
 HTTPObjectConfig* load_obj_conf(char *file) {
     printf("load_obj_conf\n");
 
--- a/src/server/daemon/config.h	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/config.h	Mon Feb 13 13:49:49 2012 +0100
@@ -45,6 +45,7 @@
 extern "C" {
 #endif
 
+
 typedef struct _server_configuration {
     pool_handle_t   *pool;
     UcxMap          *host_vs;   // map of all vservers. key is the host name
@@ -55,66 +56,36 @@
     sstr_t          user;
 } ServerConfiguration;
 
-/*
- * Handles an object in the server.conf
- * An object looks like <ObjectName> ... directives ... </ObjectName>
- * The parser executes the handlers process_directive function for each
- * directive in the object
- */
-typedef struct _server_conf_handler ServerConfigHandler;
+
+typedef struct ConfigFile ConfigFile;
+
+typedef int(*cfg_reload_f)(ConfigFile*,ServerConfiguration*);
 
-typedef void(*cfg_handler_init_f)(ServerConfigHandler*, ServerConfiguration*);
-typedef void*(*cfg_element_start_f)(
-        ServerConfigHandler*,
-        ServerConfiguration*);
-typedef int(*cfg_process_directive_f)(
-        ServerConfigHandler*,
-        ServerConfiguration*,
-        ConfigDirective*,
-        void*); /* element object created in element_start */
+struct ConfigFile {
+    sstr_t         file;
+    time_t         last_modified;
+    cfg_reload_f   reload;
+    void           *data;
+};
 
-struct _server_conf_handler {
-    cfg_handler_init_f      init;
-    cfg_element_start_f     element_start;
-    cfg_process_directive_f process_directive;
-    cfg_process_directive_f element_end;
-};
 
 void load_init_conf(char *file);
 
 void init_server_config_parser();
 
-ServerConfiguration* load_server_conf(char *file);
+int cfg_handle_runtime(ServerConfiguration *cfg, ServerConfigObject *obj);
 
-int handle_runtime_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data);
+int cfg_handle_logfile(ServerConfiguration *cfg, ServerConfigObject *obj);
+
+int cfg_handle_authdb(ServerConfiguration *cfg, ServerConfigObject *obj);
 
-void* handle_listener_start(ServerConfigHandler *h, ServerConfiguration *cfg);
-int handle_listener_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data);
-int handle_listener_end(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data);
+int cfg_handle_listener(ServerConfiguration *cfg, ServerConfigObject *obj);
+
+int cfg_handle_vs(ServerConfiguration *cfg, ServerConfigObject *obj);
 
-void* handle_vserver_start(ServerConfigHandler *h, ServerConfiguration *cfg);
-int handle_vserver_directive(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data);
-int handle_vserver_end(
-        ServerConfigHandler *h,
-        ServerConfiguration *conf,
-        ConfigDirective *dir,
-        void *data);
+ServerConfiguration* load_server_conf(ServerConfiguration *old, char *file);
+
+int object_conf_reload(ConfigFile *file, ServerConfiguration *cfg);
 
 HTTPObjectConfig* load_obj_conf(char *file);
 
--- a/src/server/daemon/configmanager.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/configmanager.c	Mon Feb 13 13:49:49 2012 +0100
@@ -34,19 +34,89 @@
 #include "configmanager.h"
 
 ServerConfiguration *current_config = NULL;
+time_t sc_last_modified = 0;
+
+UcxMap *config_files;
 
 void init_configuration_manager() {
     /* init parser */
     init_server_config_parser();
+
+    config_files = ucx_map_new(16);
+}
+
+void cfgmgr_attach_file(ConfigFile *cf) {
+    ucx_map_sstr_put(config_files, cf->file, cf);
+}
+
+ConfigFile* cfgmgr_get_file(sstr_t name) {
+    ucx_map_sstr_get(config_files, name);
 }
 
 int cfgmgr_load_config() {
-    ServerConfiguration *config = load_server_conf("conf/server.conf");
-    if(config == NULL) {
-        fprintf(stderr, "Cannot load server.conf\n");
+    int cfgreload = 0;
+    /* check config files */
+    for(int i=0;i<config_files->size;i++) {
+        UcxMapElement *elm = &config_files->map[i];
+        while(elm != NULL) {
+            /*check file */
+            ConfigFile *f = elm->data;
+
+            if(f != NULL) {
+                struct stat s;
+                if(stat(f->file.ptr, &s) != 0) {
+                    fprintf(
+                            stderr,
+                            "Error: Cannot get stat of file %s\n", f->file.ptr);
+                    perror("cfgmgr_load_config: stat");
+                    return -1;
+                }
+
+                if(f->last_modified != s.st_mtim.tv_sec) {
+                    /* reload the file */
+                    f->reload(f, current_config);
+                    cfgreload = 1;
+                }
+            }
+
+            elm = elm->next;
+        }
+    }
+
+    struct stat s;
+    if(stat("conf/server.conf", &s) != 0) {
+        perror("stat(\"conf/server.conf\")");
         return -1;
     }
 
+    ServerConfiguration *config;
+    if(sc_last_modified != s.st_mtim.tv_sec) {
+        config = load_server_conf(
+            current_config,
+            "conf/server.conf");
+
+        if(config == NULL) {
+            fprintf(stderr, "Cannot load server.conf\n");
+            return -1;
+        }
+    } else if(cfgreload) {
+        /* copy configuration */
+
+        /* TODO: copy */
+        config = load_server_conf(
+            current_config,
+            "conf/server.conf");
+
+        if(config == NULL) {
+            fprintf(stderr, "Cannot load server.conf\n");
+            return -1;
+        }
+
+    } else {
+        config = current_config;
+    }
+
+
     current_config = config;
     return 0;
 }
--- a/src/server/daemon/configmanager.h	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/configmanager.h	Mon Feb 13 13:49:49 2012 +0100
@@ -39,13 +39,19 @@
 #include "../ucx/mempool.h"
 #include "../ucx/string.h"
 
+#include <sys/types.h>
+
 #ifdef	__cplusplus
 extern "C" {
 #endif
 
+void init_configuration_manager();
 
-void init_configuration_manager();
+void cfgmgr_attach_file(ConfigFile *cf);
+ConfigFile* cfgmgr_get_file(sstr_t name);
+
 int cfgmgr_load_config();
+
 ServerConfiguration* cfgmgr_get_server_config();
 
 
--- a/src/server/daemon/httplistener.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/httplistener.c	Mon Feb 13 13:49:49 2012 +0100
@@ -112,7 +112,7 @@
 int http_listener_start(HttpListener *listener) {
     printf("INFO: start listener\n");
 
-    if (listen(listener->server_socket, 16) == -1) {
+    if (listen(listener->server_socket, 256) == -1) {
         perror("Error: http_listener_start: listen");
         return -1;
     }
--- a/src/server/daemon/httprequest.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/httprequest.c	Mon Feb 13 13:49:49 2012 +0100
@@ -162,8 +162,6 @@
     // TODO: decode abs_path
 
     /* Pass the abs_path as 'uri' in reqpb */
-    // TODO: pass abs_path to reqpb
-    // TODO: replace this code
     pblock_kvinsert(
             pb_key_uri,
             absPath.ptr,
@@ -289,7 +287,7 @@
                 nsapi_context_next_stage(&rq->context);
             }
             case NSAPINameTrans: {
-                printf(">>> NameTrans\n");
+                //printf(">>> NameTrans\n");
                 r = nsapi_nametrans(sn, rq);
                 if(r != REQ_PROCEED) {
                     break;
@@ -298,12 +296,12 @@
                 nsapi_context_next_stage(&rq->context);
             }
             case NSAPIPathCheck: {
-                printf(">>> PathCheck\n");
+                //printf(">>> PathCheck\n");
                 rq->phase++;
                 nsapi_context_next_stage(&rq->context);
             }
             case NSAPIObjectType: {
-                printf(">>> ObjectType\n");
+                //printf(">>> ObjectType\n");
                 r = nsapi_objecttype(sn, rq);
                 if(r != REQ_PROCEED) {
                     break;
@@ -312,7 +310,7 @@
                 nsapi_context_next_stage(&rq->context);
             }
             case NSAPIService: {
-                printf(">>> Service\n");
+                //printf(">>> Service\n");
                 r = nsapi_service(sn, rq);
                 if(r != REQ_PROCEED) {
                     break;
@@ -321,12 +319,12 @@
                 nsapi_context_next_stage(&rq->context);
             }
             case NSAPIAddLog: {
-                printf(">>> AddLog\n");
+                //printf(">>> AddLog\n");
                 rq->phase++;
                 nsapi_context_next_stage(&rq->context);
             }
             case REQ_FINISH: {
-                printf(">>> Finish\n");
+                //printf(">>> Finish\n");
                 r = nsapi_finish_request(sn, rq);
             }
         }
@@ -345,7 +343,7 @@
 
 int nsapi_nametrans(NSAPISession *sn, NSAPIRequest *rq) {
     HTTPObjectConfig *objconf = rq->vs->objects;
-    printf("nsapi_nametrans\n");
+    //printf("nsapi_nametrans\n");
     httpd_objset *objset = objset_create(sn->sn.pool);
     rq->rq.os = objset;
     /* first object in objconf is the default object  TODO: make sure it is */
@@ -419,7 +417,7 @@
 }
 
 int nsapi_objecttype(NSAPISession *sn, NSAPIRequest *rq) {
-    printf("nsapi_objecttype\n");
+    //printf("nsapi_objecttype\n");
     httpd_objset *objset = rq->rq.os;
 
     if(NCX_OI(rq) == -1) {
@@ -486,7 +484,7 @@
 }
 
 int nsapi_service(NSAPISession *sn, NSAPIRequest *rq) {
-    printf("nsapi_service\n");
+    //printf("nsapi_service\n");
     httpd_objset *objset = rq->rq.os;
 
     if(NCX_OI(rq) == -1) {
@@ -531,6 +529,7 @@
                 }
             }
 
+            /* execute the saf */
             ret = d->func->func(d->param, (Session*)sn, (Request*)rq);
             if(ret != REQ_PROCEED) {
                 fprintf(stderr, "saf not proceed\n");
--- a/src/server/daemon/protocol.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/protocol.c	Mon Feb 13 13:49:49 2012 +0100
@@ -307,7 +307,7 @@
     const pb_key *key = pblock_key(name);
     pb_param *pp = pblock_findkey(key, rq->headers);
     if(pp != NULL) {
-        value = &pp->value;
+        *value = pp->value;
         return REQ_PROCEED;
     } else {
         return REQ_ABORTED;
--- a/src/server/daemon/request.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/daemon/request.c	Mon Feb 13 13:49:49 2012 +0100
@@ -33,7 +33,7 @@
 
 
 /* Code from req.cpp */
-/* fremden Code durch eigenen ersetzen */
+/* TODO: fremden Code durch eigenen ersetzen */
 
 /* -------------------------- request_initialize -------------------------- */
 
--- a/src/server/public/nsapi.h	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/public/nsapi.h	Mon Feb 13 13:49:49 2012 +0100
@@ -751,13 +751,17 @@
 /*
  * Function prototypes for filter methods
  */
-typedef int (FilterInsertFunc)(FilterLayer *layer, pblock *pb);
-typedef void (FilterRemoveFunc)(FilterLayer *layer);
-typedef int (FilterFlushFunc)(FilterLayer *layer);
-typedef int (FilterReadFunc)(FilterLayer *layer, void *buf, int amount, int timeout);
-typedef int (FilterWriteFunc)(FilterLayer *layer, const void *buf, int amount);
-typedef int (FilterWritevFunc)(FilterLayer *layer, const NSAPIIOVec *iov, int iov_size);
-typedef int (FilterSendfileFunc)(FilterLayer *layer, sendfiledata *sfd);
+
+/*
+ * TODO: modified: added * bevor Filter...Func
+ */
+typedef int (*FilterInsertFunc)(FilterLayer *layer, pblock *pb);
+typedef void (*FilterRemoveFunc)(FilterLayer *layer);
+typedef int (*FilterFlushFunc)(FilterLayer *layer);
+typedef int (*FilterReadFunc)(FilterLayer *layer, void *buf, int amount, int timeout);
+typedef int (*FilterWriteFunc)(FilterLayer *layer, const void *buf, int amount);
+typedef int (*FilterWritevFunc)(FilterLayer *layer, const NSAPIIOVec *iov, int iov_size);
+typedef int (*FilterSendfileFunc)(FilterLayer *layer, sendfiledata *sfd);
 
 /*
  * FilterMethods is passed to filter_create() to declare the filter methods for
@@ -1266,12 +1270,6 @@
 NSAPI_PUBLIC char *session_dns_lookup(Session *s, int verify);
 
 
-/* --- OBSOLETE ----------------------------------------------------------
- * The following macros/functions are obsolete and are only maintained for
- * compatibility.  Do not use them.
- * -----------------------------------------------------------------------
- */
-
 
 /* new macro and function definitions begin */
 
@@ -1289,6 +1287,15 @@
 
 NSAPI_PUBLIC int netbuf_grab(netbuf *buf, int sz);
 
+#define netbuf_open        netbuf_open
+#define netbuf_close       netbuf_close
+#define netbuf_replace     netbuf_replace
+#define netbuf_next        netbuf_next
+#define netbuf_getbytes    netbuf_getbytes
+#define netbuf_grab        netbuf_grab
+
+
+
 /* end new macro and function definitions */
 
 #define SYS_STDERR STDERR_FILENO
--- a/src/server/safs/service.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/safs/service.c	Mon Feb 13 13:49:49 2012 +0100
@@ -101,25 +101,6 @@
 }
 
 int send_file(pblock *pb, Session *sn, Request *rq) {
-    printf("test_service\n");
-
-    // request body test begin
-    char *ctval = pblock_findkeyval(pb_key_content_length, rq->headers);
-    if(ctval != NULL) {
-        printf("read request body\n");
-
-        printf("netbuf{%d}\n", sn->inbuf);
-
-        int c;
-        while((c = netbuf_getc(sn->inbuf)) != IO_EOF) {
-            putchar(c);
-        }
-        printf("\n");
-    }
-
-
-    // end test
-
     int fd = prepare_service_file(sn, rq);
     if(fd < 0) {
         /* TODO: service error */
@@ -132,7 +113,6 @@
 
     off_t fileoffset = 0;
     int len = atoi(pblock_findkeyval(pb_key_content_length, rq->srvhdrs));
-    printf("content-length: %d\n", len);
     sendfile(io->fd, fd, &fileoffset, len);
 
     close(fd);
--- a/src/server/ucx/map.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/ucx/map.c	Mon Feb 13 13:49:49 2012 +0100
@@ -2,6 +2,7 @@
  *
  */
 
+#include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 
@@ -27,21 +28,38 @@
     if(key.hash == 0) {
         key.hash = ucx_hash((char*)key.data, key.len);
     }
-    void *kd = malloc(key.len);
+    void *kd = calloc(1, key.len);
     memcpy(kd, key.data, key.len);
     key.data = kd;
 
     UcxMapElement *elm = &map->map[key.hash%map->size];
-    if(elm->next != NULL) {
-        while(elm->next != NULL) {
-            elm = elm->next;
+    if(elm->key.hash != 0) {
+        UcxMapElement *e = elm;
+        for(;;) {
+            /* check if the key is already in use */
+            if(key.hash == e->key.hash) {
+                int n = (key.len > elm->key.len) ? elm->key.len : key.len;
+                if(memcmp(elm->key.data, key.data, n) == 0) {
+                    /* use elm as storage place */
+                    elm = e;
+                    break;
+                }
+            }
+
+            /* check if this is the last element */
+            if(e->next == NULL) {
+                /* create new element */
+                UcxMapElement *en = (UcxMapElement*)malloc(sizeof(UcxMapElement));
+                if(en == NULL) {
+                    return -1;
+                }
+                e->next = en;
+                elm = en;
+                break;
+            }
+
+            e = e->next;
         }
-        UcxMapElement *e = (UcxMapElement*)malloc(sizeof(UcxMapElement));
-        if(e == NULL) {
-            return -1;
-        }
-        elm->next = e;
-        elm = e;
     }
 
     elm->key = key;
@@ -54,7 +72,7 @@
     if(key.hash == 0) {
         key.hash = ucx_hash((char*)key.data, key.len);
     }
-    
+
     UcxMapElement *elm = &map->map[key.hash%map->size];
     while(elm != NULL) {
         if(elm->key.hash == key.hash) {
--- a/src/server/ucx/string.c	Sat Jan 28 16:01:07 2012 +0100
+++ b/src/server/ucx/string.c	Mon Feb 13 13:49:49 2012 +0100
@@ -131,7 +131,11 @@
     newstring.length = s.length;
     newstring.ptr[newstring.length] = 0;
 
-    memcpy(newstring.ptr, s.ptr, s.length);
+    /* TODO: sometimes memcpy and/or memmove destroy the source */
+    //memcpy(newstring.ptr, s.ptr, s.length);
+    for(int i=0;i<s.length;i++) {
+        newstring.ptr[i] = s.ptr[i];
+    }
 
     return newstring;
 }

mercurial