| /*============================================================================ |
| CMake - Cross Platform Makefile Generator |
| Copyright 2000-2009 Kitware, Inc., Insight Software Consortium |
| |
| Distributed under the OSI-approved BSD License (the "License"); |
| see accompanying file Copyright.txt for details. |
| |
| This software is distributed WITHOUT ANY WARRANTY; without even the |
| implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
| See the License for more information. |
| ============================================================================*/ |
| #include "cmIDEOptions.h" |
| |
| #include "cmSystemTools.h" |
| |
| //---------------------------------------------------------------------------- |
| cmIDEOptions::cmIDEOptions() |
| { |
| this->DoingDefine = false; |
| this->AllowDefine = true; |
| this->AllowSlash = false; |
| for(int i=0; i < FlagTableCount; ++i) |
| { |
| this->FlagTable[i] = 0; |
| } |
| } |
| |
| //---------------------------------------------------------------------------- |
| cmIDEOptions::~cmIDEOptions() |
| { |
| } |
| |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::HandleFlag(const char* flag) |
| { |
| // If the last option was -D then this option is the definition. |
| if(this->DoingDefine) |
| { |
| this->DoingDefine = false; |
| this->Defines.push_back(flag); |
| return; |
| } |
| |
| // Look for known arguments. |
| if(flag[0] == '-' || (this->AllowSlash && flag[0] == '/')) |
| { |
| // Look for preprocessor definitions. |
| if(this->AllowDefine && flag[1] == 'D') |
| { |
| if(flag[2] == '\0') |
| { |
| // The next argument will have the definition. |
| this->DoingDefine = true; |
| } |
| else |
| { |
| // Store this definition. |
| this->Defines.push_back(flag+2); |
| } |
| return; |
| } |
| |
| // Look through the available flag tables. |
| bool flag_handled = false; |
| for(int i=0; i < FlagTableCount && this->FlagTable[i]; ++i) |
| { |
| if(this->CheckFlagTable(this->FlagTable[i], flag, flag_handled)) |
| { |
| return; |
| } |
| } |
| |
| // If any map entry handled the flag we are done. |
| if(flag_handled) |
| { |
| return; |
| } |
| } |
| |
| // This option is not known. Store it in the output flags. |
| this->StoreUnknownFlag(flag); |
| } |
| |
| //---------------------------------------------------------------------------- |
| bool cmIDEOptions::CheckFlagTable(cmIDEFlagTable const* table, |
| const char* flag, bool& flag_handled) |
| { |
| // Look for an entry in the flag table matching this flag. |
| for(cmIDEFlagTable const* entry = table; entry->IDEName; ++entry) |
| { |
| bool entry_found = false; |
| if(entry->special & cmIDEFlagTable::UserValue) |
| { |
| // This flag table entry accepts a user-specified value. If |
| // the entry specifies UserRequired we must match only if a |
| // non-empty value is given. |
| int n = static_cast<int>(strlen(entry->commandFlag)); |
| if(strncmp(flag+1, entry->commandFlag, n) == 0 && |
| (!(entry->special & cmIDEFlagTable::UserRequired) || |
| static_cast<int>(strlen(flag+1)) > n)) |
| { |
| if(entry->special & cmIDEFlagTable::UserIgnored) |
| { |
| // Ignore the user-specified value. |
| this->FlagMap[entry->IDEName] = entry->value; |
| } |
| else if(entry->special & cmIDEFlagTable::SemicolonAppendable) |
| { |
| const char *new_value = flag+1+n; |
| |
| std::map<cmStdString,cmStdString>::iterator itr; |
| itr = this->FlagMap.find(entry->IDEName); |
| if(itr != this->FlagMap.end()) |
| { |
| // Append to old value (if present) with semicolons; |
| itr->second += ";"; |
| itr->second += new_value; |
| } |
| else |
| { |
| this->FlagMap[entry->IDEName] = new_value; |
| } |
| } |
| else |
| { |
| // Use the user-specified value. |
| this->FlagMap[entry->IDEName] = flag+1+n; |
| } |
| entry_found = true; |
| } |
| } |
| else if(strcmp(flag+1, entry->commandFlag) == 0) |
| { |
| // This flag table entry provides a fixed value. |
| this->FlagMap[entry->IDEName] = entry->value; |
| entry_found = true; |
| } |
| |
| // If the flag has been handled by an entry not requesting a |
| // search continuation we are done. |
| if(entry_found && !(entry->special & cmIDEFlagTable::Continue)) |
| { |
| return true; |
| } |
| |
| // If the entry was found the flag has been handled. |
| flag_handled = flag_handled || entry_found; |
| } |
| |
| return false; |
| } |
| |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::AddDefine(const std::string& def) |
| { |
| this->Defines.push_back(def); |
| } |
| |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::AddDefines(const char* defines) |
| { |
| if(defines) |
| { |
| // Expand the list of definitions. |
| cmSystemTools::ExpandListArgument(defines, this->Defines); |
| } |
| } |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::AddDefines(const std::vector<std::string> &defines) |
| { |
| this->Defines.insert(this->Defines.end(), defines.begin(), defines.end()); |
| } |
| |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::AddFlag(const char* flag, const char* value) |
| { |
| this->FlagMap[flag] = value; |
| } |
| |
| //---------------------------------------------------------------------------- |
| void cmIDEOptions::RemoveFlag(const char* flag) |
| { |
| this->FlagMap.erase(flag); |
| } |
| |
| //---------------------------------------------------------------------------- |
| const char* cmIDEOptions::GetFlag(const char* flag) |
| { |
| std::map<cmStdString, cmStdString>::iterator i = this->FlagMap.find(flag); |
| if(i != this->FlagMap.end()) |
| { |
| return i->second.c_str(); |
| } |
| return 0; |
| } |