1//===-- TypeCategory.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/lldb-python.h" 11 12#include "lldb/DataFormatters/TypeCategory.h" 13 14// C Includes 15// C++ Includes 16// Other libraries and framework includes 17// Project includes 18 19using namespace lldb; 20using namespace lldb_private; 21 22TypeCategoryImpl::TypeCategoryImpl(IFormatChangeListener* clist, 23 ConstString name) : 24m_summary_nav(new SummaryNavigator("summary",clist)), 25m_regex_summary_nav(new RegexSummaryNavigator("regex-summary",clist)), 26m_filter_nav(new FilterNavigator("filter",clist)), 27m_regex_filter_nav(new RegexFilterNavigator("regex-filter",clist)), 28#ifndef LLDB_DISABLE_PYTHON 29m_synth_nav(new SynthNavigator("synth",clist)), 30m_regex_synth_nav(new RegexSynthNavigator("regex-synth",clist)), 31#endif 32m_enabled(false), 33m_change_listener(clist), 34m_mutex(Mutex::eMutexTypeRecursive), 35m_name(name) 36{} 37 38bool 39TypeCategoryImpl::Get (ValueObject& valobj, 40 lldb::TypeSummaryImplSP& entry, 41 lldb::DynamicValueType use_dynamic, 42 uint32_t* reason) 43{ 44 if (!IsEnabled()) 45 return false; 46 if (GetSummaryNavigator()->Get(valobj, entry, use_dynamic, reason)) 47 return true; 48 bool regex = GetRegexSummaryNavigator()->Get(valobj, entry, use_dynamic, reason); 49 if (regex && reason) 50 *reason |= lldb_private::eFormatterChoiceCriterionRegularExpressionSummary; 51 return regex; 52} 53 54bool 55TypeCategoryImpl::Get(ValueObject& valobj, 56 lldb::SyntheticChildrenSP& entry_sp, 57 lldb::DynamicValueType use_dynamic, 58 uint32_t* reason) 59{ 60 if (!IsEnabled()) 61 return false; 62 TypeFilterImpl::SharedPointer filter_sp; 63 uint32_t reason_filter = 0; 64 bool regex_filter = false; 65 // first find both Filter and Synth, and then check which is most recent 66 67 if (!GetFilterNavigator()->Get(valobj, filter_sp, use_dynamic, &reason_filter)) 68 regex_filter = GetRegexFilterNavigator()->Get (valobj, filter_sp, use_dynamic, &reason_filter); 69 70#ifndef LLDB_DISABLE_PYTHON 71 bool regex_synth = false; 72 uint32_t reason_synth = 0; 73 bool pick_synth = false; 74 ScriptedSyntheticChildren::SharedPointer synth; 75 if (!GetSyntheticNavigator()->Get(valobj, synth, use_dynamic, &reason_synth)) 76 regex_synth = GetRegexSyntheticNavigator()->Get (valobj, synth, use_dynamic, &reason_synth); 77 if (!filter_sp.get() && !synth.get()) 78 return false; 79 else if (!filter_sp.get() && synth.get()) 80 pick_synth = true; 81 82 else if (filter_sp.get() && !synth.get()) 83 pick_synth = false; 84 85 else /*if (filter_sp.get() && synth.get())*/ 86 { 87 if (filter_sp->GetRevision() > synth->GetRevision()) 88 pick_synth = false; 89 else 90 pick_synth = true; 91 } 92 if (pick_synth) 93 { 94 if (regex_synth && reason) 95 *reason |= lldb_private::eFormatterChoiceCriterionRegularExpressionFilter; 96 entry_sp = synth; 97 return true; 98 } 99 else 100 { 101 if (regex_filter && reason) 102 *reason |= lldb_private::eFormatterChoiceCriterionRegularExpressionFilter; 103 entry_sp = filter_sp; 104 return true; 105 } 106 107#else 108 if (filter_sp) 109 { 110 entry_sp = filter_sp; 111 return true; 112 } 113#endif 114 115 return false; 116 117} 118 119void 120TypeCategoryImpl::Clear (FormatCategoryItems items) 121{ 122 if ( (items & eFormatCategoryItemSummary) == eFormatCategoryItemSummary ) 123 m_summary_nav->Clear(); 124 if ( (items & eFormatCategoryItemRegexSummary) == eFormatCategoryItemRegexSummary ) 125 m_regex_summary_nav->Clear(); 126 if ( (items & eFormatCategoryItemFilter) == eFormatCategoryItemFilter ) 127 m_filter_nav->Clear(); 128 if ( (items & eFormatCategoryItemRegexFilter) == eFormatCategoryItemRegexFilter ) 129 m_regex_filter_nav->Clear(); 130#ifndef LLDB_DISABLE_PYTHON 131 if ( (items & eFormatCategoryItemSynth) == eFormatCategoryItemSynth ) 132 m_synth_nav->Clear(); 133 if ( (items & eFormatCategoryItemRegexSynth) == eFormatCategoryItemRegexSynth ) 134 m_regex_synth_nav->Clear(); 135#endif 136} 137 138bool 139TypeCategoryImpl::Delete (ConstString name, 140 FormatCategoryItems items) 141{ 142 bool success = false; 143 if ( (items & eFormatCategoryItemSummary) == eFormatCategoryItemSummary ) 144 success = m_summary_nav->Delete(name) || success; 145 if ( (items & eFormatCategoryItemRegexSummary) == eFormatCategoryItemRegexSummary ) 146 success = m_regex_summary_nav->Delete(name) || success; 147 if ( (items & eFormatCategoryItemFilter) == eFormatCategoryItemFilter ) 148 success = m_filter_nav->Delete(name) || success; 149 if ( (items & eFormatCategoryItemRegexFilter) == eFormatCategoryItemRegexFilter ) 150 success = m_regex_filter_nav->Delete(name) || success; 151#ifndef LLDB_DISABLE_PYTHON 152 if ( (items & eFormatCategoryItemSynth) == eFormatCategoryItemSynth ) 153 success = m_synth_nav->Delete(name) || success; 154 if ( (items & eFormatCategoryItemRegexSynth) == eFormatCategoryItemRegexSynth ) 155 success = m_regex_synth_nav->Delete(name) || success; 156#endif 157 return success; 158} 159 160uint32_t 161TypeCategoryImpl::GetCount (FormatCategoryItems items) 162{ 163 uint32_t count = 0; 164 if ( (items & eFormatCategoryItemSummary) == eFormatCategoryItemSummary ) 165 count += m_summary_nav->GetCount(); 166 if ( (items & eFormatCategoryItemRegexSummary) == eFormatCategoryItemRegexSummary ) 167 count += m_regex_summary_nav->GetCount(); 168 if ( (items & eFormatCategoryItemFilter) == eFormatCategoryItemFilter ) 169 count += m_filter_nav->GetCount(); 170 if ( (items & eFormatCategoryItemRegexFilter) == eFormatCategoryItemRegexFilter ) 171 count += m_regex_filter_nav->GetCount(); 172#ifndef LLDB_DISABLE_PYTHON 173 if ( (items & eFormatCategoryItemSynth) == eFormatCategoryItemSynth ) 174 count += m_synth_nav->GetCount(); 175 if ( (items & eFormatCategoryItemRegexSynth) == eFormatCategoryItemRegexSynth ) 176 count += m_regex_synth_nav->GetCount(); 177#endif 178 return count; 179} 180 181bool 182TypeCategoryImpl::AnyMatches(ConstString type_name, 183 FormatCategoryItems items, 184 bool only_enabled, 185 const char** matching_category, 186 FormatCategoryItems* matching_type) 187{ 188 if (!IsEnabled() && only_enabled) 189 return false; 190 191 lldb::TypeSummaryImplSP summary; 192 TypeFilterImpl::SharedPointer filter; 193#ifndef LLDB_DISABLE_PYTHON 194 ScriptedSyntheticChildren::SharedPointer synth; 195#endif 196 197 if ( (items & eFormatCategoryItemSummary) == eFormatCategoryItemSummary ) 198 { 199 if (m_summary_nav->Get(type_name, summary)) 200 { 201 if (matching_category) 202 *matching_category = m_name.GetCString(); 203 if (matching_type) 204 *matching_type = eFormatCategoryItemSummary; 205 return true; 206 } 207 } 208 if ( (items & eFormatCategoryItemRegexSummary) == eFormatCategoryItemRegexSummary ) 209 { 210 if (m_regex_summary_nav->Get(type_name, summary)) 211 { 212 if (matching_category) 213 *matching_category = m_name.GetCString(); 214 if (matching_type) 215 *matching_type = eFormatCategoryItemRegexSummary; 216 return true; 217 } 218 } 219 if ( (items & eFormatCategoryItemFilter) == eFormatCategoryItemFilter ) 220 { 221 if (m_filter_nav->Get(type_name, filter)) 222 { 223 if (matching_category) 224 *matching_category = m_name.GetCString(); 225 if (matching_type) 226 *matching_type = eFormatCategoryItemFilter; 227 return true; 228 } 229 } 230 if ( (items & eFormatCategoryItemRegexFilter) == eFormatCategoryItemRegexFilter ) 231 { 232 if (m_regex_filter_nav->Get(type_name, filter)) 233 { 234 if (matching_category) 235 *matching_category = m_name.GetCString(); 236 if (matching_type) 237 *matching_type = eFormatCategoryItemRegexFilter; 238 return true; 239 } 240 } 241#ifndef LLDB_DISABLE_PYTHON 242 if ( (items & eFormatCategoryItemSynth) == eFormatCategoryItemSynth ) 243 { 244 if (m_synth_nav->Get(type_name, synth)) 245 { 246 if (matching_category) 247 *matching_category = m_name.GetCString(); 248 if (matching_type) 249 *matching_type = eFormatCategoryItemSynth; 250 return true; 251 } 252 } 253 if ( (items & eFormatCategoryItemRegexSynth) == eFormatCategoryItemRegexSynth ) 254 { 255 if (m_regex_synth_nav->Get(type_name, synth)) 256 { 257 if (matching_category) 258 *matching_category = m_name.GetCString(); 259 if (matching_type) 260 *matching_type = eFormatCategoryItemRegexSynth; 261 return true; 262 } 263 } 264#endif 265 return false; 266} 267 268TypeCategoryImpl::SummaryNavigator::MapValueType 269TypeCategoryImpl::GetSummaryForType (lldb::TypeNameSpecifierImplSP type_sp) 270{ 271 SummaryNavigator::MapValueType retval; 272 273 if (type_sp) 274 { 275 if (type_sp->IsRegex()) 276 m_regex_summary_nav->GetExact(ConstString(type_sp->GetName()),retval); 277 else 278 m_summary_nav->GetExact(ConstString(type_sp->GetName()),retval); 279 } 280 281 return retval; 282} 283 284TypeCategoryImpl::FilterNavigator::MapValueType 285TypeCategoryImpl::GetFilterForType (lldb::TypeNameSpecifierImplSP type_sp) 286{ 287 FilterNavigator::MapValueType retval; 288 289 if (type_sp) 290 { 291 if (type_sp->IsRegex()) 292 m_regex_filter_nav->GetExact(ConstString(type_sp->GetName()),retval); 293 else 294 m_filter_nav->GetExact(ConstString(type_sp->GetName()),retval); 295 } 296 297 return retval; 298} 299 300#ifndef LLDB_DISABLE_PYTHON 301TypeCategoryImpl::SynthNavigator::MapValueType 302TypeCategoryImpl::GetSyntheticForType (lldb::TypeNameSpecifierImplSP type_sp) 303{ 304 SynthNavigator::MapValueType retval; 305 306 if (type_sp) 307 { 308 if (type_sp->IsRegex()) 309 m_regex_synth_nav->GetExact(ConstString(type_sp->GetName()),retval); 310 else 311 m_synth_nav->GetExact(ConstString(type_sp->GetName()),retval); 312 } 313 314 return retval; 315} 316#endif 317 318lldb::TypeNameSpecifierImplSP 319TypeCategoryImpl::GetTypeNameSpecifierForSummaryAtIndex (size_t index) 320{ 321 if (index < m_summary_nav->GetCount()) 322 return m_summary_nav->GetTypeNameSpecifierAtIndex(index); 323 else 324 return m_regex_summary_nav->GetTypeNameSpecifierAtIndex(index-m_summary_nav->GetCount()); 325} 326 327TypeCategoryImpl::SummaryNavigator::MapValueType 328TypeCategoryImpl::GetSummaryAtIndex (size_t index) 329{ 330 if (index < m_summary_nav->GetCount()) 331 return m_summary_nav->GetAtIndex(index); 332 else 333 return m_regex_summary_nav->GetAtIndex(index-m_summary_nav->GetCount()); 334} 335 336TypeCategoryImpl::FilterNavigator::MapValueType 337TypeCategoryImpl::GetFilterAtIndex (size_t index) 338{ 339 if (index < m_filter_nav->GetCount()) 340 return m_filter_nav->GetAtIndex(index); 341 else 342 return m_regex_filter_nav->GetAtIndex(index-m_filter_nav->GetCount()); 343} 344 345lldb::TypeNameSpecifierImplSP 346TypeCategoryImpl::GetTypeNameSpecifierForFilterAtIndex (size_t index) 347{ 348 if (index < m_filter_nav->GetCount()) 349 return m_filter_nav->GetTypeNameSpecifierAtIndex(index); 350 else 351 return m_regex_filter_nav->GetTypeNameSpecifierAtIndex(index-m_filter_nav->GetCount()); 352} 353 354#ifndef LLDB_DISABLE_PYTHON 355TypeCategoryImpl::SynthNavigator::MapValueType 356TypeCategoryImpl::GetSyntheticAtIndex (size_t index) 357{ 358 if (index < m_synth_nav->GetCount()) 359 return m_synth_nav->GetAtIndex(index); 360 else 361 return m_regex_synth_nav->GetAtIndex(index-m_synth_nav->GetCount()); 362} 363 364lldb::TypeNameSpecifierImplSP 365TypeCategoryImpl::GetTypeNameSpecifierForSyntheticAtIndex (size_t index) 366{ 367 if (index < m_synth_nav->GetCount()) 368 return m_synth_nav->GetTypeNameSpecifierAtIndex(index); 369 else 370 return m_regex_synth_nav->GetTypeNameSpecifierAtIndex(index - m_synth_nav->GetCount()); 371} 372#endif 373 374void 375TypeCategoryImpl::Enable (bool value, uint32_t position) 376{ 377 Mutex::Locker locker(m_mutex); 378 m_enabled = value; 379 m_enabled_position = position; 380 if (m_change_listener) 381 m_change_listener->Changed(); 382} 383