diff options
author | Dwayne Boone <dwayne@zeroc.com> | 2008-03-20 11:20:11 -0230 |
---|---|---|
committer | Dwayne Boone <dwayne@zeroc.com> | 2008-03-20 11:20:11 -0230 |
commit | 82ef8e6f9d564358aeb1685fc82227d77a7beae2 (patch) | |
tree | 6d231fa27405cc0290ed456451c872439ef71fd3 /cpp/src/Ice/PropertiesI.cpp | |
parent | Merge branch 'master' of ssh://git/home/git/ice (diff) | |
download | ice-82ef8e6f9d564358aeb1685fc82227d77a7beae2.tar.bz2 ice-82ef8e6f9d564358aeb1685fc82227d77a7beae2.tar.xz ice-82ef8e6f9d564358aeb1685fc82227d77a7beae2.zip |
Handle \\ in config file parsing
Diffstat (limited to 'cpp/src/Ice/PropertiesI.cpp')
-rw-r--r-- | cpp/src/Ice/PropertiesI.cpp | 245 |
1 files changed, 146 insertions, 99 deletions
diff --git a/cpp/src/Ice/PropertiesI.cpp b/cpp/src/Ice/PropertiesI.cpp index faf997b0c93..94f8c64914b 100644 --- a/cpp/src/Ice/PropertiesI.cpp +++ b/cpp/src/Ice/PropertiesI.cpp @@ -147,7 +147,7 @@ Ice::PropertiesI::setProperty(const string& key, const string& value) string currentKey = IceUtilInternal::trim(key); if(currentKey.empty()) { - return; + throw InitializationException(__FILE__, __LINE__, "Attempt to set property with empty key"); } // @@ -409,121 +409,168 @@ Ice::PropertiesI::PropertiesI(StringSeq& args, const PropertiesPtr& defaults, co void Ice::PropertiesI::parseLine(const string& line, const StringConverterPtr& converter) { - string s = line; + string key; + string value; - // - // Remove comments and unescape #'s - // - string::size_type idx = 0; - while((idx = s.find("#", idx)) != string::npos) - { - if(idx != 0 && s[idx - 1] == '\\') - { - s.erase(idx - 1, 1); - ++idx; - } - else - { - s.erase(idx); - break; - } - } - - // - // Split key/value and unescape ='s - // - string::size_type split = string::npos; - idx = 0; - while((idx = s.find("=", idx)) != string::npos) - { - if(idx != 0 && s[idx - 1] == '\\') - { - s.erase(idx - 1, 1); - } - else if(split == string::npos) - { - split = idx; - } - ++idx; - } - - if(split == 0 || split == string::npos) - { - s = IceUtilInternal::trim(s); - if(s.length() != 0) - { - getProcessLogger()->warning("invalid config file entry: \"" + line + "\""); - } - return; - } - - // - // Deal with espaced spaces. For key we just unescape and trim but - // for values any esaped spaces must be kept. - // - string key = s.substr(0, split); - while((idx = key.find("\\ ")) != string::npos) - { - key.replace(idx, 2, " "); - } - key = IceUtilInternal::trim(key); + enum ParseState { Key , Value }; + ParseState state = Key; - string value = s.substr(split + 1, s.length() - split - 1); - idx = 0; - string whitespace = ""; - while(idx < value.length()) + string whitespace; + string escapedspace; + bool finished = false; + for(string::size_type i = 0; i < line.size(); ++i) { - if(value[idx] == '\\') + char c = line[i]; + switch(state) { - if(idx + 1 != value.length() && - (value[idx + 1] == ' ' || value[idx + 1] == '\t' || value[idx + 1] == '\r' || value[idx + 1] == '\n')) + case Key: + { + switch(c) { - whitespace += value[idx + 1]; - idx += 2; + case '\\': + if(i < line.length() - 1) + { + c = line[++i]; + switch(c) + { + case '\\': + case '#': + case '=': + key += whitespace; + whitespace.clear(); + key += c; + break; + + case ' ': + if(key.length() != 0) + { + whitespace += c; + } + break; + + default: + key += whitespace; + whitespace.clear(); + key += '\\'; + key += c; + break; + } + } + else + { + key += whitespace; + key += c; + } + break; + + case ' ': + case '\t': + case '\r': + case '\n': + if(key.length() != 0) + { + whitespace += c; + } + break; + + case '=': + whitespace.clear(); + state = Value; + break; + + case '#': + finished = true; + break; + + default: + key += whitespace; + whitespace.clear(); + key += c; + break; } - else + break; + } + + case Value: + { + switch(c) { + case '\\': + if(i < line.length() - 1) + { + c = line[++i]; + switch(c) + { + case '\\': + case '#': + case '=': + value += value.length() == 0 ? escapedspace : whitespace; + whitespace.clear(); + escapedspace.clear(); + value += c; + break; + + case ' ': + whitespace += c; + escapedspace += c; + break; + + default: + value += value.length() == 0 ? escapedspace : whitespace; + whitespace.clear(); + escapedspace.clear(); + value += '\\'; + value += c; + break; + } + } + else + { + value += value.length() == 0 ? escapedspace : whitespace; + value += c; + } break; + + case ' ': + case '\t': + case '\r': + case '\n': + if(value.length() != 0) + { + whitespace += c; + } + break; + + case '#': + value += escapedspace; + finished = true; + break; + + default: + value += value.length() == 0 ? escapedspace : whitespace; + whitespace.clear(); + escapedspace.clear(); + value += c; + break; } + break; + } } - else if(value[idx] == ' ' || value[idx] == '\t' || value[idx] == '\r' || value[idx] == '\n') - { - ++idx; - } - else + if(finished) { break; } } - value = whitespace + value.substr(idx, value.length() - idx); - if(idx != value.length()) + value += escapedspace; + + if((state == Key && key.length() != 0) || (state == Value && key.length() == 0)) { - idx = value.length() - 1; - whitespace = ""; - while(idx > 0) - { - if(value[idx] == ' ' || value[idx] == '\t' || value[idx] == '\r' || value[idx] == '\n') - { - if(value[idx - 1] == '\\') - { - whitespace += value[idx]; - idx -= 2; - } - else - { - --idx; - } - } - else - { - break; - } - } - value = value.substr(0, idx + 1) + whitespace; + getProcessLogger()->warning("invalid config file entry: \"" + line + "\""); + return; } - while((idx = value.find("\\ ")) != string::npos) + else if(key.length() == 0) { - value.replace(idx, 2, " "); + return; } if(converter) |