X-Git-Url: http://g0dil.de/git?a=blobdiff_plain;f=PPI%2FDebugModules.hh;h=1ea0f2b755c05cfc21ad13910e336ff066ea4e59;hb=81f84badf27b66dbadec9890646ca1193e998505;hp=5545871c49c51ed41922b098d25d0acd0bf9cdc8;hpb=026887c8f93c5dc89fb68446ae014205de559451;p=senf.git diff --git a/PPI/DebugModules.hh b/PPI/DebugModules.hh index 5545871..1ea0f2b 100644 --- a/PPI/DebugModules.hh +++ b/PPI/DebugModules.hh @@ -1,8 +1,8 @@ // $Id$ // -// Copyright (C) 2007 -// Fraunhofer Institut fuer offene Kommunikationssysteme (FOKUS) -// Kompetenzzentrum fuer Satelitenkommunikation (SatCom) +// Copyright (C) 2007 +// Fraunhofer Institute for Open Communication Systems (FOKUS) +// Competence Center NETwork research (NET), St. Augustin, GERMANY // Stefan Bund // // This program is free software; you can redistribute it and/or modify @@ -23,13 +23,16 @@ /** \file \brief DebugModules public header */ -#ifndef HH_DebugModules_ -#define HH_DebugModules_ 1 +#ifndef HH_SENF_PPI_DebugModules_ +#define HH_SENF_PPI_DebugModules_ 1 // Custom includes #include -#include "Packets/Packets.hh" +#include "../Utils/safe_bool.hh" +#include "../Packets/Packets.hh" #include "Module.hh" +#include "ActiveFeeder.hh" +#include "../Utils/Logger/SenfLog.hh" //#include "DebugModules.mpp" ///////////////////////////////hh.p//////////////////////////////////////// @@ -38,79 +41,246 @@ namespace senf { namespace ppi { namespace module { namespace debug { - - class ActivePacketSource - : public Module + + /** \namespace senf::ppi::module::debug + \brief Debug modules + + This namespace collects several modules helpful for PPI debugging. The modules allow to + manually pass packets into a network and read back the output packets. + + There are three categories of modules: + + \li Active modules (ActiveSource, ActiveSink) are triggered by external + calls. Calling \c submit() / \c request() will send the request into the module network + synchronously. From this it follows, that senf::ppi::run() should \e not be + called. Instead senf::ppi::init() is used to initialize the network and explicit calls + to the active debug modules drive the execution. + \li Passive modules (PassiveSource, PassiveSink) contain a queue to save packets + (either packets to be transmitted or packets received) and are driven by the network. + \li Feeder (almost-)modules (ActiveFeederSource, ActiveFeederSink) are a hybrid of + both types of modules: They contain a packet queue but actively drive the network and + are used together with senf::ppi::run(). senf::ppi::run() will automatically terminate + if all available packets have been processed. These are not modules, they are + collections combining a passive debug module and a senf::ppi::ActiveFeeder. + */ + + /** \brief Debug packet source with active output + + This module provides packets into the network. Each call to submit() will process the packet + synchronously. + + \note This module should not be used together with senf::ppi::run(). Instead use + senf::ppi::init() and explicit submit() calls. It follows, that no events will be + signaled in the network. + */ + class ActiveSource + : public Module, + public safe_bool { + SENF_PPI_MODULE(ActiveSource); + public: - connector::ActiveOutput output; + connector::ActiveOutput<> output; - ActivePacketSource(); + ActiveSource(); - void submit(Packet packet); + void submit(Packet const & packet); ///< Submit packet + /**< \pre boolean_test() is \c true */ + + bool boolean_test() const; ///< \c true if \a output is not throttled }; - class PassivePacketSource + /** \brief Debug packet source with passive output + + This module provides a queue of packets for reading by the network. Each submit() call adds + a packet to the queue which will be sent into the network when requested. The output is + automatically throttled when the queue becomes empty. + */ + class PassiveSource : public Module { + SENF_PPI_MODULE(PassiveSource); + typedef std::deque Queue; public: typedef Queue::size_type size_type; - - PassivePacketSource(); - - connector::PassiveOutput output; - - void submit(Packet packet); - bool empty(); - size_type size(); + connector::PassiveOutput<> output; + + PassiveSource(); + + void throttle(); ///< Throttle output connector + void unthrottle(); ///< Unthrottle output connector + + void submit(Packet const & packet); ///< Enqueue packet + + bool empty(); ///< \c true if queue is empty + size_type size(); ///< Number of packets in queue private: void request(); - + virtual void v_init(); + Queue packets_; }; - class ActivePacketSink - : public Module + /** \brief Debug packet sink with active input + + This module requests packets from the network. Each call to request() will pass a packet + request into the network. + + \note This module should not be used together with senf::ppi::run(). Instead use + senf::ppi::init() and explicit request() calls. It follows, that no events will be + signaled in the network. + */ + class ActiveSink + : public Module, + public safe_bool { + SENF_PPI_MODULE(ActiveSink); + public: - connector::ActiveInput input; + connector::ActiveInput<> input; - ActivePacketSink(); + ActiveSink(); - Packet request(); + Packet request(); ///< Request packet + /**< \pre boolean_test() is \c true */ + + bool boolean_test() const; ///< \c true, if \a input is not throttled }; - class PassivePacketSink + /** \brief Debug packet sink with passive input + + This module provides a queue for the network to write packets into. The packets can then + later be analyzed. + */ + class PassiveSink : public Module { + SENF_PPI_MODULE(PassiveSink); + typedef std::deque Queue; public: typedef Queue::size_type size_type; typedef Queue::const_iterator iterator; - connector::PassiveInput input; + connector::PassiveInput<> input; + + PassiveSink(); + + void throttle(); ///< Throttle input connection + void unthrottle(); ///< Unthrottle input connection + + bool empty(); ///< \c true, if queue is empty + size_type size(); ///< number of packets in the queue + iterator begin(); ///< begin iterator of packets in the queue + iterator end(); ///< past-the-end iterator of packets in the queue + + Packet front(); ///< first packet in the queue + Packet pop_front(); ///< remove and return first packet in the queue + + void clear(); ///< clear the queue + + private: + void request(); - PassivePacketSink(); + Queue packets_; + }; + + /** \brief Active, queue-based packet source + + The ActiveFeederSource contains a packet queue containing the packets to be precessed. These + packets are actively fed into the network when it is run with senf::ppi::run() until it is + empty, when senf::ppi::run() will return. + + \note senf::ppi::run will return as soon as no events are active. If want you want is to + precess a set of packets placed into the ActiveFeederSource queue you must make sure, + that eventually all events in the module are disabled by throttling or other + activities. Otherwise, senf::ppi::run() will \e not return. + + ActiveFeederSource is not a module but a collection of two modules: a PassiveSource and an + ActiveFeeder. + */ + class ActiveFeederSource + { + private: + PassiveSource source; + ActiveFeeder feeder; + + public: + typedef PassiveSource::size_type size_type; + + connector::ActiveOutput<> & output; + + ActiveFeederSource(); + + void submit(Packet packet); ///< enqueue packet + bool empty(); ///< \c true, if queue is empty + size_type size(); ///< number of packets in the queue + }; + + /** \brief Active, queue-based packet sink + + The ActiveFeederSink contains a packet queue to receive the packets from the network. The + ActiveFeederSink will actively request packets from the network until it's input is + throttled. + + \note ActiveFeederSink does \e not have a termination condition like ActiveFeederSource, it + relies on the network to throttle it's input. Additionally, the restrictions of + ActiveFeederSource apply here too: You need to ensure, that no (additional) events are + active (eventually) or senf::ppi::run will not return. + + ActiveFeederSink is not a module but a collection of two modules: a PassiveSink and an + ActiveFeeder. + */ + class ActiveFeederSink + { + private: + PassiveSink sink; + ActiveFeeder feeder; + + public: + typedef PassiveSink::size_type size_type; + typedef PassiveSink::iterator iterator; + + connector::ActiveInput<> & input; + + ActiveFeederSink(); bool empty(); size_type size(); iterator begin(); iterator end(); - Packet back(); - Packet pop_back(); + Packet front(); + Packet pop_front(); void clear(); + }; + + /** \brief Log received packets + + This module will log all packets sent to it's input using SENF_LOG to the given log + \a Stream, \a Area and \a Level. + */ + template < class Stream = log::Debug, + class Area = log::DefaultArea, + class Level = log::VERBOSE > + class LogSink + : public module::Module + { + SENF_PPI_MODULE(LogSink); + public: + + connector::PassiveInput<> input; + + LogSink(); private: void request(); - - Queue packets_; }; }}}} @@ -118,7 +288,7 @@ namespace debug { ///////////////////////////////hh.e//////////////////////////////////////// #include "DebugModules.cci" //#include "DebugModules.ct" -//#include "DebugModules.cti" +#include "DebugModules.cti" #endif