Skip to content

Commit

Permalink
Debugger: Cache hash match results on symbol tree nodes
Browse files Browse the repository at this point in the history
  • Loading branch information
chaoticgd authored and F0bes committed Oct 18, 2024
1 parent 2c3abe3 commit f963291
Show file tree
Hide file tree
Showing 4 changed files with 95 additions and 81 deletions.
81 changes: 2 additions & 79 deletions pcsx2-qt/Debugger/SymbolTree/SymbolTreeModel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -106,8 +106,8 @@ QVariant SymbolTreeModel::data(const QModelIndex& index, int role) const
bool active = true;

// Gray out the names of symbols that have been overwritten in memory.
if (index.column() == NAME && node->symbol.valid())
active = symbolMatchesMemory(node->symbol);
if (index.column() == NAME)
active = node->matchesMemory();

// Gray out the values of variables that are dead.
if (index.column() == VALUE && node->liveness().has_value())
Expand Down Expand Up @@ -521,80 +521,3 @@ bool SymbolTreeModel::nodeHasChildren(const ccc::ast::Node& logical_type, const

return result;
}

bool SymbolTreeModel::symbolMatchesMemory(ccc::MultiSymbolHandle& symbol) const
{
bool matching = true;
switch (symbol.descriptor())
{
case ccc::SymbolDescriptor::FUNCTION:
{
m_cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::Function* function = database.functions.symbol_from_handle(symbol.handle());
if (!function || function->original_hash() == 0)
return;

matching = function->current_hash() == function->original_hash();
});
break;
}
case ccc::SymbolDescriptor::GLOBAL_VARIABLE:
{
m_cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::GlobalVariable* global_variable = database.global_variables.symbol_from_handle(symbol.handle());
if (!global_variable)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(global_variable->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
case ccc::SymbolDescriptor::LOCAL_VARIABLE:
{
m_cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::LocalVariable* local_variable = database.local_variables.symbol_from_handle(symbol.handle());
if (!local_variable)
return;

const ccc::Function* function = database.functions.symbol_from_handle(local_variable->function());
if (!function)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(function->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
case ccc::SymbolDescriptor::PARAMETER_VARIABLE:
{
m_cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::ParameterVariable* parameter_variable = database.parameter_variables.symbol_from_handle(symbol.handle());
if (!parameter_variable)
return;

const ccc::Function* function = database.functions.symbol_from_handle(parameter_variable->function());
if (!function)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(function->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
default:
{
}
}

return matching;
}
2 changes: 0 additions & 2 deletions pcsx2-qt/Debugger/SymbolTree/SymbolTreeModel.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,8 +76,6 @@ class SymbolTreeModel : public QAbstractItemModel

static bool nodeHasChildren(const ccc::ast::Node& logical_type, const ccc::SymbolDatabase& database);

bool symbolMatchesMemory(ccc::MultiSymbolHandle& symbol) const;

std::unique_ptr<SymbolTreeNode> m_root;
QString m_filter;
DebugInterface& m_cpu;
Expand Down
89 changes: 89 additions & 0 deletions pcsx2-qt/Debugger/SymbolTree/SymbolTreeNode.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ bool SymbolTreeNode::readFromVM(DebugInterface& cpu, const ccc::SymbolDatabase&

data_changed |= updateDisplayString(cpu, database);
data_changed |= updateLiveness(cpu);
data_changed |= updateHash(cpu);

return data_changed;
}
Expand Down Expand Up @@ -478,6 +479,94 @@ bool SymbolTreeNode::updateLiveness(DebugInterface& cpu)
return true;
}

bool SymbolTreeNode::updateHash(DebugInterface& cpu)
{
bool matching = true;

switch (symbol.descriptor())
{
case ccc::SymbolDescriptor::FUNCTION:
{
cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::Function* function = database.functions.symbol_from_handle(symbol.handle());
if (!function || function->original_hash() == 0)
return;

matching = function->current_hash() == function->original_hash();
});
break;
}
case ccc::SymbolDescriptor::GLOBAL_VARIABLE:
{
cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::GlobalVariable* global_variable = database.global_variables.symbol_from_handle(symbol.handle());
if (!global_variable)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(global_variable->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
case ccc::SymbolDescriptor::LOCAL_VARIABLE:
{
cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::LocalVariable* local_variable = database.local_variables.symbol_from_handle(symbol.handle());
if (!local_variable)
return;

const ccc::Function* function = database.functions.symbol_from_handle(local_variable->function());
if (!function)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(function->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
case ccc::SymbolDescriptor::PARAMETER_VARIABLE:
{
cpu.GetSymbolGuardian().Read([&](const ccc::SymbolDatabase& database) -> void {
const ccc::ParameterVariable* parameter_variable = database.parameter_variables.symbol_from_handle(symbol.handle());
if (!parameter_variable)
return;

const ccc::Function* function = database.functions.symbol_from_handle(parameter_variable->function());
if (!function)
return;

const ccc::SourceFile* source_file = database.source_files.symbol_from_handle(function->source_file());
if (!source_file)
return;

matching = source_file->functions_match();
});
break;
}
default:
{
}
}

if (matching == m_matches_memory)
return false;

m_matches_memory = matching;

return true;
}

bool SymbolTreeNode::matchesMemory() const
{
return m_matches_memory;
}

bool SymbolTreeNode::anySymbolsValid(const ccc::SymbolDatabase& database) const
{
if (symbol.lookup_symbol(database))
Expand Down
4 changes: 4 additions & 0 deletions pcsx2-qt/Debugger/SymbolTree/SymbolTreeNode.h
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,9 @@ struct SymbolTreeNode

bool updateLiveness(DebugInterface& cpu);

bool updateHash(DebugInterface& cpu);
bool matchesMemory() const;

bool anySymbolsValid(const ccc::SymbolDatabase& database) const;

const SymbolTreeNode* parent() const;
Expand All @@ -79,6 +82,7 @@ struct SymbolTreeNode
QVariant m_value;
QString m_display_value;
std::optional<bool> m_liveness;
bool m_matches_memory = true;

SymbolTreeNode* m_parent = nullptr;
std::vector<std::unique_ptr<SymbolTreeNode>> m_children;
Expand Down

0 comments on commit f963291

Please sign in to comment.