/* * \brief Registry containing possible sources of tracing data * \author Norman Feske * \date 2013-08-09 */ /* * Copyright (C) 2013 Genode Labs GmbH * * This file is part of the Genode OS framework, which is distributed * under the terms of the GNU General Public License version 2. */ #ifndef _CORE__INCLUDE__TRACE__SOURCE_REGISTRY_H_ #define _CORE__INCLUDE__TRACE__SOURCE_REGISTRY_H_ #include #include #include #include /* core includes */ #include /* base-internal include */ #include namespace Genode { namespace Trace { class Source; class Source_owner; class Source_registry; } } struct Genode::Trace::Source_owner { }; /** * Source of tracing data * * There is one instance per thread. */ class Genode::Trace::Source : public Genode::Volatile_object, public Genode::List::Element { private: unsigned const _unique_id; Session_label const &_label; Thread_name const _name; Control &_control; Dataspace_capability _policy; Dataspace_capability _buffer; Source_owner const *_owner; static unsigned _alloc_unique_id(); public: Source(Session_label const &label, Thread_name const &name, Control &control) : _unique_id(_alloc_unique_id()), _label(label), _name(name), _control(control), _owner(0) { } /************************************* ** Interface used by TRACE service ** *************************************/ Session_label const &label() const { return _label; } Thread_name const &name() const { return _name; } void trace(Dataspace_capability policy, Dataspace_capability buffer) { _buffer = buffer; _policy = policy; _control.trace(); } void enable() { _control.enable(); } void disable() { _control.disable(); } bool try_acquire(Source_owner const *new_owner) { if (_owner && _owner != new_owner) return false; _owner = new_owner; return true; } bool is_owned_by(Source_owner const *owner) { return owner == _owner; } void release_ownership(Source_owner const *owner) { if (is_owned_by(owner)) _owner = 0; } bool error() const { return _control.has_error(); } bool enabled() const { return _control.is_enabled(); } /*********************************** ** Interface used by CPU service ** ***********************************/ Dataspace_capability buffer() const { return _buffer; } Dataspace_capability policy() const { return _policy; } unsigned unique_id() const { return _unique_id; } }; /** * Registry to tracing sources * * There is a single instance within core. */ class Genode::Trace::Source_registry { private: Lock _lock; List _entries; public: /*********************************** ** Interface used by CPU service ** ***********************************/ void insert(Source *entry) { Lock::Guard guard(_lock); _entries.insert(entry); } void remove(Source *entry) { Lock::Guard guard(_lock); _entries.remove(entry); } /************************************* ** Interface used by TRACE service ** *************************************/ template void export_sources(TEST &test, INSERT &insert) { for (Source *s = _entries.first(); s; s = s->next()) if (!test(s->unique_id())) insert(s->unique_id(), s->weak_ptr(), s->label(), s->name()); } }; #endif /* _CORE__INCLUDE__TRACE__SOURCE_REGISTRY_H_ */