change uid before most of the config is loaded

Sun, 25 Sep 2022 10:36:28 +0200

author
Olaf Wintermann <olaf.wintermann@gmail.com>
date
Sun, 25 Sep 2022 10:36:28 +0200
changeset 388
30d29ef5b79a
parent 387
f5caf41b4db6
child 389
c6c5638e97b8

change uid before most of the config is loaded

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/main.c file | annotate | diff | comparison | revisions
src/server/daemon/webserver.c file | annotate | diff | comparison | revisions
src/server/daemon/websocket.c file | annotate | diff | comparison | revisions
--- a/src/server/daemon/config.c	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/config.c	Sun Sep 25 10:36:28 2022 +0200
@@ -131,7 +131,7 @@
     return 0;
 }
 
-ServerConfiguration* load_server_conf(char *file) {
+ServerConfiguration* load_server_conf(CfgManager *mgr, char *file) {
     log_ereport(LOG_VERBOSE, "load_server_conf");
 
     ServerConfig *serverconf = serverconfig_load(file);
@@ -139,6 +139,7 @@
         log_ereport(LOG_FAILURE, "Cannot load server.conf");
         return NULL;
     }
+    mgr->serverconf = serverconf;
     
     pool_handle_t *pool = pool_create();
     
@@ -152,15 +153,10 @@
     *serverconfig->a = allocator;
     
     serverconfig->listeners = NULL;
-    serverconfig->host_vs = ucx_map_new_a(&allocator, 16);
-    serverconfig->authdbs = ucx_map_new_a(&allocator, 16);
-    serverconfig->resources = ucx_map_new_a(&allocator, 16);
-    serverconfig->dav = ucx_map_new_a(&allocator, 16);
-    
-    
-    
-    // TODO: init serverconfig stuff
-    
+    serverconfig->host_vs = ucx_map_new_a(serverconfig->a, 16);
+    serverconfig->authdbs = ucx_map_new_a(serverconfig->a, 16);
+    serverconfig->resources = ucx_map_new_a(serverconfig->a, 16);
+    serverconfig->dav = ucx_map_new_a(serverconfig->a, 16);
     
     /*
      * convert ServerConfig to ServerConfiguration
@@ -175,12 +171,29 @@
      * VirtualServer (dependencies: Listener)
      */
     
-    /*
-     * free stuff on error
-     */
+    // load Runtime  infos first, because we need that to change the uid
+    // and the server should do that as soon as possible
+    UcxList *list = serverconfig_get_node_list(serverconf->root, CONFIG_NODE_OBJECT, SC("Runtime"));
+    UCX_FOREACH(elm, list) {
+        ConfigNode *runtimeobj = elm->data;
+        if(cfg_handle_runtime(serverconfig, runtimeobj)) {
+            // error
+            return NULL;
+        }
+    }
+    ucx_list_free(list);
+    
+    // we return here, to let the webserver use the runtime info to
+    // change the uid if needed
+    return serverconfig;
+}
+   
+ServerConfiguration* apply_server_conf(CfgManager *mgr) {
+    ServerConfig *serverconf = mgr->serverconf;
+    ServerConfiguration *serverconfig = mgr->cfg;
     
     // init logfile first
-    UcxList *list = NULL;
+    UcxList *list;
     
     list = serverconfig_get_node_list(serverconf->root, CONFIG_NODE_OBJECT, SC("LogFile"));
     if(list) {
@@ -201,15 +214,7 @@
     }
     ucx_list_free(list);
      
-    list = serverconfig_get_node_list(serverconf->root, CONFIG_NODE_OBJECT, SC("Runtime"));
-    UCX_FOREACH(elm, list) {
-        ConfigNode *runtimeobj = elm->data;
-        if(cfg_handle_runtime(serverconfig, runtimeobj)) {
-            // error
-            return NULL;
-        }
-    }
-    ucx_list_free(list);
+    
     
     list = serverconfig_get_node_list(serverconf->root, CONFIG_NODE_OBJECT, SC("Threadpool"));
     UCX_FOREACH(elm, list) {
--- a/src/server/daemon/config.h	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/config.h	Sun Sep 25 10:36:28 2022 +0200
@@ -61,10 +61,15 @@
 typedef struct WebdavRepository      WebdavRepository;
 typedef struct WebdavBackendInitData WebdavBackendInitData;
     
+typedef struct CfgManager {
+    ServerConfig *serverconf;
+    ServerConfiguration *cfg;
+} CfgManager;
+
 struct ServerConfiguration {
     pool_handle_t   *pool;
     UcxAllocator    *a;
-    
+      
     UcxMap          *host_vs;   // map of all vservers. key is the host name
     UcxList         *listeners; // list of all listeners
     UcxList         *logfiles;
@@ -120,7 +125,8 @@
 
 int cfg_handle_dav(ServerConfiguration *cfg, ConfigNode *obj);
 
-ServerConfiguration* load_server_conf(char *file);
+ServerConfiguration* load_server_conf(CfgManager *mgr, char *file);
+ServerConfiguration* apply_server_conf(CfgManager *mgr);
 void cfg_ref(ServerConfiguration *cfg);
 void cfg_unref(ServerConfiguration *cfg);
 
--- a/src/server/daemon/configmanager.c	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/configmanager.c	Sun Sep 25 10:36:28 2022 +0200
@@ -51,16 +51,15 @@
     return &global_vars;
 }
 
-int cfgmgr_load_config(ServerConfiguration **set_cfg) {
-    ServerConfiguration *config = load_server_conf("config/server.conf");
+int cfgmgr_load_config(CfgManager *mgr) {
+    ZERO(mgr, sizeof(CfgManager));
+    ServerConfiguration *config = load_server_conf(mgr, "config/server.conf");
     
     if(!config) {
         return -1;
     }
     
-    if(set_cfg) {
-         *set_cfg = config;
-    }
+    mgr->cfg = config;
     
     if(current_config) {
         cfg_unref(current_config);
@@ -70,6 +69,19 @@
     return 0;
 }
 
+int cfgmgr_apply_config(CfgManager *mgr) {
+    int err = 1;
+    if(apply_server_conf(mgr)) {
+        err = 0;
+        if(current_config) {
+            cfg_unref(current_config);
+        }
+        current_config = mgr->cfg;
+    }
+    
+    return err;
+}
+
 ServerConfiguration *cfgmgr_get_server_config() {
     return current_config;
 }
--- a/src/server/daemon/configmanager.h	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/configmanager.h	Sun Sep 25 10:36:28 2022 +0200
@@ -46,7 +46,8 @@
 
 void init_configuration_manager();
 
-int cfgmgr_load_config(ServerConfiguration **cfg);
+int cfgmgr_load_config(CfgManager *mgr);
+int cfgmgr_apply_config(CfgManager *mgr);
 
 ServerConfiguration* cfgmgr_get_server_config();
 
--- a/src/server/daemon/main.c	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/main.c	Sun Sep 25 10:36:28 2022 +0200
@@ -70,9 +70,15 @@
 void sig_usr1_reload(int sig) {
     log_ereport(LOG_INFORM, "sig reload");
     
-    if(cfgmgr_load_config(NULL) != 0) {
-        log_ereport(LOG_FAILURE, "cannot reload config");
+    CfgManager mgr;
+    if(cfgmgr_load_config(&mgr) != 0) {
+        log_ereport(LOG_FAILURE, "cannot reload server.conf");
+    } else {
+        if(cfgmgr_apply_config(&mgr)) {
+            log_ereport(LOG_FAILURE, "cannot reload config");
+        }
     }
+    
     // start newly created listeners
     start_all_listener();
 
--- a/src/server/daemon/webserver.c	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/webserver.c	Sun Sep 25 10:36:28 2022 +0200
@@ -91,11 +91,15 @@
     }
 
     // load server.conf
+    // Only the runtime infos are stored in the ServerConfiguration at
+    // this stage. The remaining configuration is loaded after the uid
+    // is changed (if needed).
     init_configuration_manager();
-    ServerConfiguration *cfg;
-    if(cfgmgr_load_config(&cfg) != 0) {
+    CfgManager mgr;
+    if(cfgmgr_load_config(&mgr) != 0) {
         return -1;
     }
+    ServerConfiguration *cfg = mgr.cfg;
     
     // init caches
     auth_cache_init();
@@ -163,6 +167,14 @@
                     "server must be started as root to change uid");
     }
     
+    
+    // now that the process is running as the correct user, we can load
+    // the remaining config
+    if(cfgmgr_apply_config(&mgr)) {
+        return -1;
+    }
+    
+    
     // create tmp dir and pid file
     char *mkdir_cmd = NULL;
     asprintf(&mkdir_cmd, "mkdir -p %s", cfg->tmp.ptr);
--- a/src/server/daemon/websocket.c	Sun Sep 25 09:33:39 2022 +0200
+++ b/src/server/daemon/websocket.c	Sun Sep 25 10:36:28 2022 +0200
@@ -304,7 +304,7 @@
 
 NSAPI_PUBLIC int websocket_send_text(SYS_NETFD csd, char *msg, size_t len) {
     char frame[WS_FRAMEHEADER_BUFLEN];
-    frame[0] = 129; // 0b10000001
+    frame[0] = (char)129; // 0b10000001
     size_t hlen;
     if(len < 126) {
         frame[1] = (char)len;

mercurial