SBTypeCategory.cpp revision 598df88bd6fc33c6fb330bc859bdc277795501f3
1//===-- SBTypeCategory.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/API/SBTypeCategory.h" 11 12#include "lldb/API/SBTypeFilter.h" 13#include "lldb/API/SBTypeFormat.h" 14#include "lldb/API/SBTypeSummary.h" 15#include "lldb/API/SBTypeSynthetic.h" 16#include "lldb/API/SBTypeNameSpecifier.h" 17#include "lldb/API/SBStream.h" 18 19#include "lldb/Core/DataVisualization.h" 20#include "lldb/Core/Debugger.h" 21#include "lldb/Interpreter/CommandInterpreter.h" 22#include "lldb/Interpreter/ScriptInterpreter.h" 23 24using namespace lldb; 25using namespace lldb_private; 26 27typedef std::pair<lldb::TypeCategoryImplSP,user_id_t> ImplType; 28 29SBTypeCategory::SBTypeCategory() : 30m_opaque_sp() 31{ 32} 33 34SBTypeCategory::SBTypeCategory (const char* name) : 35m_opaque_sp() 36{ 37 DataVisualization::Categories::GetCategory(ConstString(name), m_opaque_sp); 38} 39 40SBTypeCategory::SBTypeCategory (const lldb::SBTypeCategory &rhs) : 41m_opaque_sp(rhs.m_opaque_sp) 42{ 43} 44 45SBTypeCategory::~SBTypeCategory () 46{ 47} 48 49bool 50SBTypeCategory::IsValid() const 51{ 52 return (m_opaque_sp.get() != NULL); 53} 54 55bool 56SBTypeCategory::GetEnabled () 57{ 58 if (!IsValid()) 59 return false; 60 return m_opaque_sp->IsEnabled(); 61} 62 63void 64SBTypeCategory::SetEnabled (bool enabled) 65{ 66 if (!IsValid()) 67 return; 68 if (enabled) 69 DataVisualization::Categories::Enable(m_opaque_sp); 70 else 71 DataVisualization::Categories::Disable(m_opaque_sp); 72} 73 74const char* 75SBTypeCategory::GetName() 76{ 77 if (!IsValid()) 78 return false; 79 return m_opaque_sp->GetName(); 80} 81 82uint32_t 83SBTypeCategory::GetNumFormats () 84{ 85 if (!IsDefaultCategory()) 86 return 0; 87 88 return DataVisualization::ValueFormats::GetCount(); 89} 90 91uint32_t 92SBTypeCategory::GetNumSummaries () 93{ 94 if (!IsValid()) 95 return 0; 96 return m_opaque_sp->GetSummaryNavigator()->GetCount() + m_opaque_sp->GetRegexSummaryNavigator()->GetCount(); 97} 98 99uint32_t 100SBTypeCategory::GetNumFilters () 101{ 102 if (!IsValid()) 103 return 0; 104 return m_opaque_sp->GetFilterNavigator()->GetCount() + m_opaque_sp->GetRegexFilterNavigator()->GetCount(); 105} 106 107#ifndef LLDB_DISABLE_PYTHON 108uint32_t 109SBTypeCategory::GetNumSynthetics () 110{ 111 if (!IsValid()) 112 return 0; 113 return m_opaque_sp->GetSyntheticNavigator()->GetCount() + m_opaque_sp->GetRegexSyntheticNavigator()->GetCount(); 114} 115#endif 116 117lldb::SBTypeNameSpecifier 118SBTypeCategory::GetTypeNameSpecifierForFilterAtIndex (uint32_t index) 119{ 120 if (!IsValid()) 121 return SBTypeNameSpecifier(); 122 return SBTypeNameSpecifier(m_opaque_sp->GetTypeNameSpecifierForFilterAtIndex(index)); 123} 124 125lldb::SBTypeNameSpecifier 126SBTypeCategory::GetTypeNameSpecifierForFormatAtIndex (uint32_t index) 127{ 128 if (!IsDefaultCategory()) 129 return SBTypeNameSpecifier(); 130 return SBTypeNameSpecifier(DataVisualization::ValueFormats::GetTypeNameSpecifierForFormatAtIndex(index)); 131} 132 133lldb::SBTypeNameSpecifier 134SBTypeCategory::GetTypeNameSpecifierForSummaryAtIndex (uint32_t index) 135{ 136 if (!IsValid()) 137 return SBTypeNameSpecifier(); 138 return SBTypeNameSpecifier(m_opaque_sp->GetTypeNameSpecifierForSummaryAtIndex(index)); 139} 140 141#ifndef LLDB_DISABLE_PYTHON 142lldb::SBTypeNameSpecifier 143SBTypeCategory::GetTypeNameSpecifierForSyntheticAtIndex (uint32_t index) 144{ 145 if (!IsValid()) 146 return SBTypeNameSpecifier(); 147 return SBTypeNameSpecifier(m_opaque_sp->GetTypeNameSpecifierForSyntheticAtIndex(index)); 148} 149#endif 150 151SBTypeFilter 152SBTypeCategory::GetFilterForType (SBTypeNameSpecifier spec) 153{ 154 if (!IsValid()) 155 return SBTypeFilter(); 156 157 if (!spec.IsValid()) 158 return SBTypeFilter(); 159 160 lldb::SyntheticChildrenSP children_sp; 161 162 if (spec.IsRegex()) 163 m_opaque_sp->GetRegexFilterNavigator()->GetExact(ConstString(spec.GetName()), children_sp); 164 else 165 m_opaque_sp->GetFilterNavigator()->GetExact(ConstString(spec.GetName()), children_sp); 166 167 if (!children_sp) 168 return lldb::SBTypeFilter(); 169 170 TypeFilterImplSP filter_sp = STD_STATIC_POINTER_CAST(TypeFilterImpl,children_sp); 171 172 return lldb::SBTypeFilter(filter_sp); 173 174} 175SBTypeFormat 176SBTypeCategory::GetFormatForType (SBTypeNameSpecifier spec) 177{ 178 if (!IsDefaultCategory()) 179 return SBTypeFormat(); 180 181 if (!spec.IsValid()) 182 return SBTypeFormat(); 183 184 if (spec.IsRegex()) 185 return SBTypeFormat(); 186 187 return SBTypeFormat(DataVisualization::ValueFormats::GetFormat(ConstString(spec.GetName()))); 188} 189 190#ifndef LLDB_DISABLE_PYTHON 191SBTypeSummary 192SBTypeCategory::GetSummaryForType (SBTypeNameSpecifier spec) 193{ 194 if (!IsValid()) 195 return SBTypeSummary(); 196 197 if (!spec.IsValid()) 198 return SBTypeSummary(); 199 200 lldb::TypeSummaryImplSP summary_sp; 201 202 if (spec.IsRegex()) 203 m_opaque_sp->GetRegexSummaryNavigator()->GetExact(ConstString(spec.GetName()), summary_sp); 204 else 205 m_opaque_sp->GetSummaryNavigator()->GetExact(ConstString(spec.GetName()), summary_sp); 206 207 if (!summary_sp) 208 return lldb::SBTypeSummary(); 209 210 return lldb::SBTypeSummary(summary_sp); 211} 212#endif // LLDB_DISABLE_PYTHON 213 214#ifndef LLDB_DISABLE_PYTHON 215SBTypeSynthetic 216SBTypeCategory::GetSyntheticForType (SBTypeNameSpecifier spec) 217{ 218 if (!IsValid()) 219 return SBTypeSynthetic(); 220 221 if (!spec.IsValid()) 222 return SBTypeSynthetic(); 223 224 lldb::SyntheticChildrenSP children_sp; 225 226 if (spec.IsRegex()) 227 m_opaque_sp->GetRegexSyntheticNavigator()->GetExact(ConstString(spec.GetName()), children_sp); 228 else 229 m_opaque_sp->GetSyntheticNavigator()->GetExact(ConstString(spec.GetName()), children_sp); 230 231 if (!children_sp) 232 return lldb::SBTypeSynthetic(); 233 234 TypeSyntheticImplSP synth_sp = STD_STATIC_POINTER_CAST(TypeSyntheticImpl,children_sp); 235 236 return lldb::SBTypeSynthetic(synth_sp); 237} 238#endif 239 240#ifndef LLDB_DISABLE_PYTHON 241SBTypeFilter 242SBTypeCategory::GetFilterAtIndex (uint32_t index) 243{ 244 if (!IsValid()) 245 return SBTypeFilter(); 246 lldb::SyntheticChildrenSP children_sp = m_opaque_sp->GetSyntheticAtIndex((index)); 247 248 if (!children_sp.get()) 249 return lldb::SBTypeFilter(); 250 251 TypeFilterImplSP filter_sp = STD_STATIC_POINTER_CAST(TypeFilterImpl,children_sp); 252 253 return lldb::SBTypeFilter(filter_sp); 254} 255#endif 256 257SBTypeFormat 258SBTypeCategory::GetFormatAtIndex (uint32_t index) 259{ 260 if (!IsDefaultCategory()) 261 return SBTypeFormat(); 262 return SBTypeFormat(DataVisualization::ValueFormats::GetFormatAtIndex((index))); 263} 264 265#ifndef LLDB_DISABLE_PYTHON 266SBTypeSummary 267SBTypeCategory::GetSummaryAtIndex (uint32_t index) 268{ 269 if (!IsValid()) 270 return SBTypeSummary(); 271 return SBTypeSummary(m_opaque_sp->GetSummaryAtIndex((index))); 272} 273#endif 274 275#ifndef LLDB_DISABLE_PYTHON 276SBTypeSynthetic 277SBTypeCategory::GetSyntheticAtIndex (uint32_t index) 278{ 279 if (!IsValid()) 280 return SBTypeSynthetic(); 281 lldb::SyntheticChildrenSP children_sp = m_opaque_sp->GetSyntheticAtIndex((index)); 282 283 if (!children_sp.get()) 284 return lldb::SBTypeSynthetic(); 285 286 TypeSyntheticImplSP synth_sp = STD_STATIC_POINTER_CAST(TypeSyntheticImpl,children_sp); 287 288 return lldb::SBTypeSynthetic(synth_sp); 289} 290#endif 291 292bool 293SBTypeCategory::AddTypeFormat (SBTypeNameSpecifier type_name, 294 SBTypeFormat format) 295{ 296 if (!IsDefaultCategory()) 297 return false; 298 299 if (!type_name.IsValid()) 300 return false; 301 302 if (!format.IsValid()) 303 return false; 304 305 if (type_name.IsRegex()) 306 return false; 307 308 DataVisualization::ValueFormats::Add(ConstString(type_name.GetName()), format.GetSP()); 309 310 return true; 311} 312 313bool 314SBTypeCategory::DeleteTypeFormat (SBTypeNameSpecifier type_name) 315{ 316 if (!IsDefaultCategory()) 317 return false; 318 319 if (!type_name.IsValid()) 320 return false; 321 322 if (type_name.IsRegex()) 323 return false; 324 325 return DataVisualization::ValueFormats::Delete(ConstString(type_name.GetName())); 326} 327 328#ifndef LLDB_DISABLE_PYTHON 329bool 330SBTypeCategory::AddTypeSummary (SBTypeNameSpecifier type_name, 331 SBTypeSummary summary) 332{ 333 if (!IsValid()) 334 return false; 335 336 if (!type_name.IsValid()) 337 return false; 338 339 if (!summary.IsValid()) 340 return false; 341 342 // FIXME: we need to iterate over all the Debugger objects and have each of them contain a copy of the function 343 // since we currently have formatters live in a global space, while Python code lives in a specific Debugger-related environment 344 // this should eventually be fixed by deciding a final location in the LLDB object space for formatters 345 if (summary.IsFunctionCode()) 346 { 347 void *name_token = (void*)ConstString(type_name.GetName()).GetCString(); 348 const char* script = summary.GetData(); 349 StringList input; input.SplitIntoLines(script, strlen(script)); 350 uint32_t num_debuggers = lldb_private::Debugger::GetNumDebuggers(); 351 bool need_set = true; 352 for (uint32_t j = 0; 353 j < num_debuggers; 354 j++) 355 { 356 DebuggerSP debugger_sp = lldb_private::Debugger::GetDebuggerAtIndex(j); 357 if (debugger_sp) 358 { 359 ScriptInterpreter* interpreter_ptr = debugger_sp->GetCommandInterpreter().GetScriptInterpreter(); 360 if (interpreter_ptr) 361 { 362 std::string output; 363 if (interpreter_ptr->GenerateTypeScriptFunction(input, output, name_token) && !output.empty()) 364 { 365 if (need_set) 366 { 367 need_set = false; 368 summary.SetFunctionName(output.c_str()); 369 } 370 } 371 } 372 } 373 } 374 } 375 376 if (type_name.IsRegex()) 377 m_opaque_sp->GetRegexSummaryNavigator()->Add(lldb::RegularExpressionSP(new RegularExpression(type_name.GetName())), summary.GetSP()); 378 else 379 m_opaque_sp->GetSummaryNavigator()->Add(ConstString(type_name.GetName()), summary.GetSP()); 380 381 return true; 382} 383#endif 384 385bool 386SBTypeCategory::DeleteTypeSummary (SBTypeNameSpecifier type_name) 387{ 388 if (!IsValid()) 389 return false; 390 391 if (!type_name.IsValid()) 392 return false; 393 394 if (type_name.IsRegex()) 395 return m_opaque_sp->GetRegexSummaryNavigator()->Delete(ConstString(type_name.GetName())); 396 else 397 return m_opaque_sp->GetSummaryNavigator()->Delete(ConstString(type_name.GetName())); 398} 399 400bool 401SBTypeCategory::AddTypeFilter (SBTypeNameSpecifier type_name, 402 SBTypeFilter filter) 403{ 404 if (!IsValid()) 405 return false; 406 407 if (!type_name.IsValid()) 408 return false; 409 410 if (!filter.IsValid()) 411 return false; 412 413 if (type_name.IsRegex()) 414 m_opaque_sp->GetRegexFilterNavigator()->Add(lldb::RegularExpressionSP(new RegularExpression(type_name.GetName())), filter.GetSP()); 415 else 416 m_opaque_sp->GetFilterNavigator()->Add(ConstString(type_name.GetName()), filter.GetSP()); 417 418 return true; 419} 420 421bool 422SBTypeCategory::DeleteTypeFilter (SBTypeNameSpecifier type_name) 423{ 424 if (!IsValid()) 425 return false; 426 427 if (!type_name.IsValid()) 428 return false; 429 430 if (type_name.IsRegex()) 431 return m_opaque_sp->GetRegexFilterNavigator()->Delete(ConstString(type_name.GetName())); 432 else 433 return m_opaque_sp->GetFilterNavigator()->Delete(ConstString(type_name.GetName())); 434} 435 436#ifndef LLDB_DISABLE_PYTHON 437bool 438SBTypeCategory::AddTypeSynthetic (SBTypeNameSpecifier type_name, 439 SBTypeSynthetic synth) 440{ 441 if (!IsValid()) 442 return false; 443 444 if (!type_name.IsValid()) 445 return false; 446 447 if (!synth.IsValid()) 448 return false; 449 450 // FIXME: we need to iterate over all the Debugger objects and have each of them contain a copy of the function 451 // since we currently have formatters live in a global space, while Python code lives in a specific Debugger-related environment 452 // this should eventually be fixed by deciding a final location in the LLDB object space for formatters 453 if (synth.IsClassCode()) 454 { 455 void *name_token = (void*)ConstString(type_name.GetName()).GetCString(); 456 const char* script = synth.GetData(); 457 StringList input; input.SplitIntoLines(script, strlen(script)); 458 uint32_t num_debuggers = lldb_private::Debugger::GetNumDebuggers(); 459 bool need_set = true; 460 for (uint32_t j = 0; 461 j < num_debuggers; 462 j++) 463 { 464 DebuggerSP debugger_sp = lldb_private::Debugger::GetDebuggerAtIndex(j); 465 if (debugger_sp) 466 { 467 ScriptInterpreter* interpreter_ptr = debugger_sp->GetCommandInterpreter().GetScriptInterpreter(); 468 if (interpreter_ptr) 469 { 470 std::string output; 471 if (interpreter_ptr->GenerateTypeSynthClass(input, output, name_token) && !output.empty()) 472 { 473 if (need_set) 474 { 475 need_set = false; 476 synth.SetClassName(output.c_str()); 477 } 478 } 479 } 480 } 481 } 482 } 483 484 if (type_name.IsRegex()) 485 m_opaque_sp->GetRegexSyntheticNavigator()->Add(lldb::RegularExpressionSP(new RegularExpression(type_name.GetName())), synth.GetSP()); 486 else 487 m_opaque_sp->GetSyntheticNavigator()->Add(ConstString(type_name.GetName()), synth.GetSP()); 488 489 return true; 490} 491 492bool 493SBTypeCategory::DeleteTypeSynthetic (SBTypeNameSpecifier type_name) 494{ 495 if (!IsValid()) 496 return false; 497 498 if (!type_name.IsValid()) 499 return false; 500 501 if (type_name.IsRegex()) 502 return m_opaque_sp->GetRegexSyntheticNavigator()->Delete(ConstString(type_name.GetName())); 503 else 504 return m_opaque_sp->GetSyntheticNavigator()->Delete(ConstString(type_name.GetName())); 505} 506#endif // LLDB_DISABLE_PYTHON 507 508bool 509SBTypeCategory::GetDescription (lldb::SBStream &description, 510 lldb::DescriptionLevel description_level) 511{ 512 if (!IsValid()) 513 return false; 514 description.Printf("Category name: %s\n",GetName()); 515 return true; 516} 517 518lldb::SBTypeCategory & 519SBTypeCategory::operator = (const lldb::SBTypeCategory &rhs) 520{ 521 if (this != &rhs) 522 { 523 m_opaque_sp = rhs.m_opaque_sp; 524 } 525 return *this; 526} 527 528bool 529SBTypeCategory::operator == (lldb::SBTypeCategory &rhs) 530{ 531 if (IsValid() == false) 532 return !rhs.IsValid(); 533 534 return m_opaque_sp.get() == rhs.m_opaque_sp.get(); 535 536} 537 538bool 539SBTypeCategory::operator != (lldb::SBTypeCategory &rhs) 540{ 541 if (IsValid() == false) 542 return rhs.IsValid(); 543 544 return m_opaque_sp.get() != rhs.m_opaque_sp.get(); 545} 546 547lldb::TypeCategoryImplSP 548SBTypeCategory::GetSP () 549{ 550 if (!IsValid()) 551 return lldb::TypeCategoryImplSP(); 552 return m_opaque_sp; 553} 554 555void 556SBTypeCategory::SetSP (const lldb::TypeCategoryImplSP &typecategory_impl_sp) 557{ 558 m_opaque_sp = typecategory_impl_sp; 559} 560 561SBTypeCategory::SBTypeCategory (const lldb::TypeCategoryImplSP &typecategory_impl_sp) : 562m_opaque_sp(typecategory_impl_sp) 563{ 564} 565 566bool 567SBTypeCategory::IsDefaultCategory() 568{ 569 if (!IsValid()) 570 return false; 571 572 return (strcmp(m_opaque_sp->GetName(),"default") == 0); 573} 574 575