trace_recorder: adopt Genode::Dictionary

genodelabs/genode#4610
This commit is contained in:
Johannes Schlatow 2022-09-15 10:40:07 +02:00 committed by Christian Helmuth
parent ab7c0b40f2
commit 4fd1b52d1f
5 changed files with 38 additions and 129 deletions

View File

@ -14,32 +14,33 @@
#ifndef _BACKEND_H_
#define _BACKEND_H_
/* Genode includes */
#include <util/dictionary.h>
/* local includes */
#include <named_registry.h>
#include <writer.h>
namespace Trace_recorder {
class Backend_base;
using Backends = Named_registry<Backend_base>;
using Backend_name = Genode::String<64>;
using Backends = Genode::Dictionary<Backend_base, Backend_name>;
}
class Trace_recorder::Backend_base : Backends::Element
{
protected:
friend class Backends::Element;
friend class Avl_node<Backend_base>;
friend class Avl_tree<Backend_base>;
friend class Genode::Dictionary<Backend_base, Backend_name>;
friend class Genode::Avl_node<Backend_base>;
friend class Genode::Avl_tree<Backend_base>;
public:
using Name = Backends::Element::Name;
using Name = Backend_name;
using Backends::Element::name;
using Backends::Element::Element;
Backend_base(Backends & registry, Name const &name)
: Backends::Element(registry, name)
Backend_base(Backends & backends, Name const &name)
: Backends::Element(backends, name)
{ }
virtual ~Backend_base() { }

View File

@ -104,11 +104,14 @@ void Trace_recorder::Monitor::start(Xml_node config)
/* find and assign policy; create/insert if not present */
Policy::Name const policy_name = session_policy.attribute_value("policy", Policy::Name());
bool create = true;
_policies.apply(policy_name, [&] (Policy & policy) {
_trace.trace(id, policy.id(), buffer_sz);
create = false;
});
bool const create =
_policies.with_element(policy_name,
[&] /* match */ (Policy & policy) {
_trace.trace(id, policy.id(), buffer_sz);
return false;
},
[&] /* no_match */ { return true; }
);
/* create policy if it did not exist */
if (create) {
@ -128,14 +131,17 @@ void Trace_recorder::Monitor::start(Xml_node config)
/* create and register writers at trace buffer */
session_policy.for_each_sub_node([&] (Xml_node & node) {
bool present = false;
_backends.apply(node.type(), [&] (Backend_base &backend) {
backend.create_writer(_alloc,
buffer.writers(),
_trace_directory->root(),
_trace_directory->subject_path(buffer.info()));
present = true;
});
bool const present =
_backends.with_element(node.type(),
[&] /* match */ (Backend_base &backend) {
backend.create_writer(_alloc,
buffer.writers(),
_trace_directory->root(),
_trace_directory->subject_path(buffer.info()));
return true;
},
[&] /* no_match */ { return false; }
);
if (!present)
error("No writer available for <", node.type(), "/>.");

View File

@ -1,96 +0,0 @@
/*
* \brief Utility for finding objecs by name
* \author Norman Feske
* \date 2021-11-11
*/
/*
* Copyright (C) 2021 Genode Labs GmbH
*
* This file is part of the Genode OS framework, which is distributed
* under the terms of the GNU Affero General Public License version 3.
*/
#ifndef _NAMED_REGISTRY_H_
#define _NAMED_REGISTRY_H_
#include <util/string.h>
#include <util/avl_tree.h>
#include <util/noncopyable.h>
namespace Trace_recorder {
using namespace Genode;
template <typename T> class Named_registry;
}
template <typename T>
class Trace_recorder::Named_registry : Noncopyable
{
private:
Avl_tree<T> _tree { };
public:
class Element : private Avl_node<T>
{
public:
using Name = Genode::String<64>;
Name const name;
private:
Named_registry<T> &_registry;
bool higher(T const *other) const { return name > other->name; }
friend class Avl_tree<T>;
friend class Avl_node<T>;
friend class Named_registry<T>;
static T *_matching_sub_tree(T &curr, Name const &name)
{
typename Avl_node<T>::Side side = (curr.name > name);
return curr.Avl_node<T>::child(side);
}
public:
Element(Named_registry &registry, Name const &name)
:
name(name), _registry(registry)
{
_registry._tree.insert(this);
}
~Element()
{
_registry._tree.remove(this);
}
};
template <typename FN>
void apply(typename Element::Name const &name, FN && fn)
{
T *curr_ptr = _tree.first();
for (;;) {
if (!curr_ptr)
return;
if (curr_ptr->name == name) {
fn(*curr_ptr);
return;
}
curr_ptr = Element::_matching_sub_tree(*curr_ptr, name);
}
}
template <typename FN>
void for_each(FN && fn) { _tree.for_each(fn); }
};
#endif /* _NAMED_REGISTRY_H_ */

View File

@ -19,9 +19,9 @@ using namespace Genode;
Trace_recorder::Policy::Policy(Env &env,
Trace::Connection &trace,
Policy::Name const &name,
Policies &registry)
Policies &policies)
:
Policies::Element(registry, name),
Policies::Element(policies, name),
_env(env), _trace(trace), _rom(env, name.string())
{
Dataspace_capability dst_ds = _trace.policy(_id);

View File

@ -14,10 +14,8 @@
#ifndef _POLICY_H_
#define _POLICY_H_
/* local includes */
#include <named_registry.h>
/* Genode includes */
#include <util/dictionary.h>
#include <rom_session/connection.h>
#include <trace_session/connection.h>
#include <dataspace/client.h>
@ -25,7 +23,8 @@
namespace Trace_recorder {
class Policy;
using Policies = Named_registry<Policy>;
using Policy_name = Genode::String<64>;
using Policies = Genode::Dictionary<Policy, Policy_name>;
}
@ -35,7 +34,7 @@ namespace Trace_recorder {
class Trace_recorder::Policy : Policies::Element
{
private:
friend class Policies::Element;
friend class Genode::Dictionary<Policy, Policy_name>;
friend class Genode::Avl_node<Policy>;
friend class Genode::Avl_tree<Policy>;
@ -48,14 +47,13 @@ class Trace_recorder::Policy : Policies::Element
public:
using Name = Policies::Element::Name;
using Name = Policy_name;
using Policies::Element::name;
using Policies::Element::Element;
Policy(Genode::Env &env,
Genode::Trace::Connection &trace,
Name const &name,
Policies &registry);
Policies &policies);
/***************