X-Git-Url: https://git.netwichtig.de/gitweb/?a=blobdiff_plain;f=src%2Fconfigparser.cpp;h=b6e3f7187e2814e7276056de0d5898eec8633469;hb=074a96c9ffc85763da833bccadefc9978152482c;hp=495d38fff4659336e23d68fa10c32914646d8030;hpb=5d73e8928826340aaca9e78205ffb093a6b4f95c;p=user%2Fhenk%2Fcode%2Finspircd.git diff --git a/src/configparser.cpp b/src/configparser.cpp index 495d38fff..b6e3f7187 100644 --- a/src/configparser.cpp +++ b/src/configparser.cpp @@ -1,16 +1,22 @@ -/* +------------------------------------+ - * | Inspire Internet Relay Chat Daemon | - * +------------------------------------+ +/* + * InspIRCd -- Internet Relay Chat Daemon * - * InspIRCd: (C) 2002-2009 InspIRCd Development Team - * See: http://wiki.inspircd.org/Credits + * Copyright (C) 2009-2010 Daniel De Graaf * - * This program is free but copyrighted software; see - * the file COPYING for details. + * This file is part of InspIRCd. InspIRCd is free software: you can + * redistribute it and/or modify it under the terms of the GNU General Public + * License as published by the Free Software Foundation, version 2. * - * --------------------------------------------------- + * This program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . */ + #include "inspircd.h" #include #include "configparser.h" @@ -76,7 +82,7 @@ struct Parser int ch = next(); while (isspace(ch)) ch = next(); - while (isalnum(ch) || ch == '_') + while (isalnum(ch) || ch == '_'|| ch == '-') { rv.push_back(ch); ch = next(); @@ -84,7 +90,7 @@ struct Parser unget(ch); } - bool kv(std::vector* items) + bool kv(std::vector* items, std::set& seen) { std::string key; nextword(key); @@ -149,6 +155,10 @@ struct Parser else value.push_back(ch); } + + if (!seen.insert(key).second) + throw CoreException("Duplicate key '" + key + "' found"); + items->push_back(KeyVal(key, value)); return true; } @@ -169,14 +179,29 @@ struct Parser throw CoreException("Empty tag name"); std::vector* items; + std::set seen; tag = ConfigTag::create(name, current.filename, current.line, items); - while (kv(items)); + while (kv(items, seen)); if (name == "include") { stack.DoInclude(tag, flags); } + else if (name == "files") + { + for(std::vector::iterator i = items->begin(); i != items->end(); i++) + { + stack.DoReadFile(i->first, i->second, flags, false); + } + } + else if (name == "execfiles") + { + for(std::vector::iterator i = items->begin(); i != items->end(); i++) + { + stack.DoReadFile(i->first, i->second, flags, true); + } + } else if (name == "define") { if (!(flags & FLAG_USE_XML)) @@ -275,6 +300,33 @@ void ParseStack::DoInclude(ConfigTag* tag, int flags) } } +void ParseStack::DoReadFile(const std::string& key, const std::string& name, int flags, bool exec) +{ + if (flags & FLAG_NO_INC) + throw CoreException("Invalid tag in file included with noinclude=\"yes\""); + if (exec && (flags & FLAG_NO_EXEC)) + throw CoreException("Invalid tag in file included with noexec=\"yes\""); + + FileWrapper file(exec ? popen(name.c_str(), "r") : fopen(name.c_str(), "r"), exec); + if (!file) + throw CoreException("Could not read \"" + name + "\" for \"" + key + "\" file"); + + file_cache& cache = FilesOutput[key]; + cache.clear(); + + char linebuf[MAXBUF*10]; + while (fgets(linebuf, sizeof(linebuf), file)) + { + size_t len = strlen(linebuf); + if (len) + { + if (linebuf[len-1] == '\n') + len--; + cache.push_back(std::string(linebuf, len)); + } + } +} + bool ParseStack::ParseFile(const std::string& name, int flags) { ServerInstance->Logs->Log("CONFIG", DEBUG, "Reading file %s", name.c_str()); @@ -312,7 +364,7 @@ bool ParseStack::ParseExec(const std::string& name, int flags) /* It's not already included, add it to the list of files we've loaded */ - FileWrapper file(popen(name.c_str(), "r")); + FileWrapper file(popen(name.c_str(), "r"), true); if (!file) throw CoreException("Could not open executable \"" + name + "\" for include"); @@ -392,7 +444,14 @@ bool ConfigTag::getBool(const std::string &key, bool def) if(!readString(key, result)) return def; - return (result == "yes" || result == "true" || result == "1" || result == "on"); + if (result == "yes" || result == "true" || result == "1" || result == "on") + return true; + if (result == "no" || result == "false" || result == "0" || result == "off") + return false; + + ServerInstance->Logs->Log("CONFIG",DEFAULT, "Value of <" + tag + ":" + key + "> at " + getTagLocation() + + " is not valid, ignoring"); + return def; } std::string ConfigTag::getTagLocation()