blob: 557020dc8b276ba3c6142492744fff1e752ff4a8 [file] [log] [blame]
// Copyright 2021 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "src/ui/scenic/lib/view_tree/snapshot_dump.h"
#include <lib/syslog/cpp/macros.h>
#include <stack>
#include <string>
namespace view_tree {
void SnapshotDump::OnNewViewTreeSnapshot(std::shared_ptr<const Snapshot> snapshot) {
LogDump snapshotLogDump = DumpSnapshotInfo(snapshot);
if (snapshotLogDump.status == DumpStatus::Failure) {
FX_LOGS(ERROR) << snapshotLogDump.message << "\n";
} else {
FX_LOGS(INFO) << "\n" << snapshotLogDump.message << "\n";
}
}
// Generates the log string to be dumped using dfs traversal of the view tree
LogDump SnapshotDump::DumpSnapshotInfo(std::shared_ptr<const Snapshot> snapshot) {
if (snapshot == nullptr) {
return {"Invalid Snapshot Received", DumpStatus::Failure};
}
zx_koid_t root = snapshot->root;
std::ostringstream dump;
// Stack takes a pair of the form (zx_koid_t,uint16_t) the former being the Node ID and the latter
// being the depth of the node
std::stack<std::pair<zx_koid_t, uint16_t>> stack;
std::unordered_set<zx_koid_t> visited;
stack.push({root, 0});
while (!stack.empty()) {
auto [node, depth] = stack.top();
stack.pop();
// Checks if there is a cycle present in the view tree
if (visited.count(node) != 0) {
return {"Cycle Present in the View tree. Invalid Snapshot", DumpStatus::Failure};
}
visited.insert(node);
auto& view_tree = snapshot->view_tree;
if (view_tree.count(node) == 0) {
std::ostringstream error_dump;
error_dump << "Node: " << node << " not present in view_tree. Invalid Request";
return {error_dump.str(), DumpStatus::Failure};
}
for (const auto child : view_tree.at(node).children) {
stack.push({child, depth + 1});
}
Indent(dump, depth);
DumpNodeInfo(dump, node, view_tree.at(node));
}
dump << "Hit testers# : " << snapshot->hit_testers.size() << "\n";
dump << "Unconnected Views : ";
std::for_each(snapshot->unconnected_views.begin(), snapshot->unconnected_views.end(),
[&dump](zx_koid_t view_koid) { dump << view_koid << " "; });
return {dump.str(), DumpStatus::Success};
}
// Adjusts tabs in the string to represent a tree
void SnapshotDump::Indent(std::ostream& dump, uint16_t depth) {
while (depth-- != 0)
dump << " ";
}
// Adds information about the View node which should be displayed on the console.
void SnapshotDump::DumpNodeInfo(std::ostream& dump, zx_koid_t id, const view_tree::ViewNode& node) {
dump << "|[Node:" << id << "] Parent:" << node.parent << "\n";
}
} // End namespace view_tree