]> git.stg.codes - stg.git/blobdiff - projects/stargazer/plugins/other/radius/config.cpp
Fixed crash on stopping mod_radius.
[stg.git] / projects / stargazer / plugins / other / radius / config.cpp
index 64ff3707d93e89f90e92c480b0fb5e4b5188c834..8e9f27a9fab9d99121235efb67627b040b69e5dc 100644 (file)
@@ -64,7 +64,8 @@ size_t checkChar(const std::string& value, size_t start, char ch)
 std::pair<size_t, std::string> readString(const std::string& value, size_t start)
 {
     std::string dest;
-    while (start < value.length() && !std::isspace(value[start]))
+    while (start < value.length() && !std::isspace(value[start]) &&
+           value[start] != ',' && value[start] != '(' && value[start] != ')')
         dest.push_back(value[start++]);
     if (dest.empty()) {
         if (start == value.length())
@@ -85,16 +86,21 @@ Config::Pairs toPairs(const std::vector<std::string>& values)
     while (start < value.size()) {
         Config::Pair pair;
         start = skipSpaces(value, start);
+        if (!res.empty())
+        {
+            start = checkChar(value, start, ',');
+            start = skipSpaces(value, start);
+        }
         size_t pairStart = start;
         start = checkChar(value, start, '(');
-        std::pair<size_t, std::string> key = readString(value, start);
+        const std::pair<size_t, std::string> key = readString(value, start);
         start = key.first;
         pair.first = key.second;
         start = skipSpaces(value, start);
         start = checkChar(value, start, ',');
         start = skipSpaces(value, start);
-        std::pair<size_t, std::string> val = readString(value, start);
-        start = key.first;
+        const std::pair<size_t, std::string> val = readString(value, start);
+        start = val.first;
         pair.second = val.second;
         start = skipSpaces(value, start);
         start = checkChar(value, start, ')');
@@ -131,49 +137,73 @@ T toInt(const std::vector<std::string>& values)
     return 0;
 }
 
-Config::Pairs parseVector(const std::string& paramName, const MODULE_SETTINGS& params)
+Config::Pairs parseVector(const std::string& paramName, const std::vector<PARAM_VALUE>& params)
 {
-    for (size_t i = 0; i < params.moduleParams.size(); ++i)
-        if (params.moduleParams[i].param == paramName)
-            return toPairs(params.moduleParams[i].value);
+    for (size_t i = 0; i < params.size(); ++i)
+        if (params[i].param == paramName)
+            return toPairs(params[i].value);
     return Config::Pairs();
 }
 
-bool parseBool(const std::string& paramName, const MODULE_SETTINGS& params)
+bool parseBool(const std::string& paramName, const std::vector<PARAM_VALUE>& params)
 {
-    for (size_t i = 0; i < params.moduleParams.size(); ++i)
-        if (params.moduleParams[i].param == paramName)
-            return toBool(params.moduleParams[i].value);
+    for (size_t i = 0; i < params.size(); ++i)
+        if (params[i].param == paramName)
+            return toBool(params[i].value);
     return false;
 }
 
-std::string parseString(const std::string& paramName, const MODULE_SETTINGS& params)
+std::string parseString(const std::string& paramName, const std::vector<PARAM_VALUE>& params)
 {
-    for (size_t i = 0; i < params.moduleParams.size(); ++i)
-        if (params.moduleParams[i].param == paramName)
-            return toString(params.moduleParams[i].value);
+    for (size_t i = 0; i < params.size(); ++i)
+        if (params[i].param == paramName)
+            return toString(params[i].value);
     return "";
 }
 
-template <typename T>
-T parseInt(const std::string& paramName, const MODULE_SETTINGS& params)
+std::string parseAddress(const std::string& address)
 {
-    for (size_t i = 0; i < params.moduleParams.size(); ++i)
-        if (params.moduleParams[i].param == paramName)
-            return toInt<T>(params.moduleParams[i].value);
-    return 0;
+    size_t pos = address.find_first_of(':');
+    if (pos == std::string::npos)
+        throw ParserError(0, "Connection type is not specified. Should be either 'unix' or 'tcp'.");
+    return address.substr(pos + 1);
+}
+
+Config::Type parseConnectionType(const std::string& address)
+{
+    size_t pos = address.find_first_of(':');
+    if (pos == std::string::npos)
+        throw ParserError(0, "Connection type is not specified. Should be either 'unix' or 'tcp'.");
+    std::string type = ToLower(address.substr(0, pos));
+    if (type == "unix")
+        return Config::UNIX;
+    else if (type == "tcp")
+        return Config::TCP;
+    throw ParserError(0, "Invalid connection type. Should be either 'unix' or 'tcp', got '" + type + "'");
+}
+
+Config::Section parseSection(const std::string& paramName, const std::vector<PARAM_VALUE>& params)
+{
+    for (size_t i = 0; i < params.size(); ++i)
+        if (params[i].param == paramName)
+            return Config::Section(parseVector("match", params[i].sections),
+                                   parseVector("modify", params[i].sections),
+                                   parseVector("reply", params[i].sections));
+    return Config::Section();
 }
 
 } // namespace anonymous
 
 Config::Config(const MODULE_SETTINGS& settings)
-    : match(parseVector("match", settings)),
-      modify(parseVector("modify", settings)),
-      reply(parseVector("reply", settings)),
-      verbose(parseBool("verbose", settings)),
-      bindAddress(parseString("bind_address", settings)),
-      portStr(parseString("port", settings)),
-      port(parseInt<uint16_t>("port", settings)),
-      key(parseString("key", settings))
+    : autz(parseSection("autz", settings.moduleParams)),
+      auth(parseSection("auth", settings.moduleParams)),
+      postauth(parseSection("postauth", settings.moduleParams)),
+      preacct(parseSection("preacct", settings.moduleParams)),
+      acct(parseSection("acct", settings.moduleParams)),
+      verbose(parseBool("verbose", settings.moduleParams)),
+      address(parseString("bind_address", settings.moduleParams)),
+      bindAddress(parseAddress(address)),
+      connectionType(parseConnectionType(address)),
+      key(parseString("key", settings.moduleParams))
 {
 }