1 //===-- OptionValueEnumeration.cpp ------------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "lldb/Interpreter/OptionValueEnumeration.h" 11 12 // C Includes 13 // C++ Includes 14 // Other libraries and framework includes 15 // Project includes 16 #include "lldb/Utility/StringList.h" 17 18 using namespace lldb; 19 using namespace lldb_private; 20 21 OptionValueEnumeration::OptionValueEnumeration( 22 const OptionEnumValueElement *enumerators, enum_type value) 23 : OptionValue(), m_current_value(value), m_default_value(value), 24 m_enumerations() { 25 SetEnumerations(enumerators); 26 } 27 28 OptionValueEnumeration::~OptionValueEnumeration() {} 29 30 void OptionValueEnumeration::DumpValue(const ExecutionContext *exe_ctx, 31 Stream &strm, uint32_t dump_mask) { 32 if (dump_mask & eDumpOptionType) 33 strm.Printf("(%s)", GetTypeAsCString()); 34 if (dump_mask & eDumpOptionValue) { 35 if (dump_mask & eDumpOptionType) 36 strm.PutCString(" = "); 37 const size_t count = m_enumerations.GetSize(); 38 for (size_t i = 0; i < count; ++i) { 39 if (m_enumerations.GetValueAtIndexUnchecked(i).value == m_current_value) { 40 strm.PutCString(m_enumerations.GetCStringAtIndex(i).GetStringRef()); 41 return; 42 } 43 } 44 strm.Printf("%" PRIu64, (uint64_t)m_current_value); 45 } 46 } 47 48 Status OptionValueEnumeration::SetValueFromString(llvm::StringRef value, 49 VarSetOperationType op) { 50 Status error; 51 switch (op) { 52 case eVarSetOperationClear: 53 Clear(); 54 NotifyValueChanged(); 55 break; 56 57 case eVarSetOperationReplace: 58 case eVarSetOperationAssign: { 59 ConstString const_enumerator_name(value.trim()); 60 const EnumerationMapEntry *enumerator_entry = 61 m_enumerations.FindFirstValueForName(const_enumerator_name); 62 if (enumerator_entry) { 63 m_current_value = enumerator_entry->value.value; 64 NotifyValueChanged(); 65 } else { 66 StreamString error_strm; 67 error_strm.Printf("invalid enumeration value '%s'", value.str().c_str()); 68 const size_t count = m_enumerations.GetSize(); 69 if (count) { 70 error_strm.Printf(", valid values are: %s", 71 m_enumerations.GetCStringAtIndex(0).GetCString()); 72 for (size_t i = 1; i < count; ++i) { 73 error_strm.Printf(", %s", 74 m_enumerations.GetCStringAtIndex(i).GetCString()); 75 } 76 } 77 error.SetErrorString(error_strm.GetString()); 78 } 79 break; 80 } 81 82 case eVarSetOperationInsertBefore: 83 case eVarSetOperationInsertAfter: 84 case eVarSetOperationRemove: 85 case eVarSetOperationAppend: 86 case eVarSetOperationInvalid: 87 error = OptionValue::SetValueFromString(value, op); 88 break; 89 } 90 return error; 91 } 92 93 void OptionValueEnumeration::SetEnumerations( 94 const OptionEnumValueElement *enumerators) { 95 m_enumerations.Clear(); 96 if (enumerators) { 97 for (size_t i = 0; enumerators[i].string_value != nullptr; ++i) { 98 ConstString const_enumerator_name(enumerators[i].string_value); 99 EnumeratorInfo enumerator_info = {enumerators[i].value, 100 enumerators[i].usage}; 101 m_enumerations.Append(const_enumerator_name, 102 enumerator_info); 103 } 104 m_enumerations.Sort(); 105 } 106 } 107 108 lldb::OptionValueSP OptionValueEnumeration::DeepCopy() const { 109 return OptionValueSP(new OptionValueEnumeration(*this)); 110 } 111 112 size_t OptionValueEnumeration::AutoComplete( 113 CommandInterpreter &interpreter, llvm::StringRef s, int match_start_point, 114 int max_return_elements, bool &word_complete, StringList &matches) { 115 word_complete = false; 116 matches.Clear(); 117 118 const uint32_t num_enumerators = m_enumerations.GetSize(); 119 if (!s.empty()) { 120 for (size_t i = 0; i < num_enumerators; ++i) { 121 llvm::StringRef name = m_enumerations.GetCStringAtIndex(i).GetStringRef(); 122 if (name.startswith(s)) 123 matches.AppendString(name); 124 } 125 } else { 126 // only suggest "true" or "false" by default 127 for (size_t i = 0; i < num_enumerators; ++i) 128 matches.AppendString(m_enumerations.GetCStringAtIndex(i).GetStringRef()); 129 } 130 return matches.GetSize(); 131 } 132