/**
* @file tests/plot/graph_manager.cpp
* @author The PARADEVS Development Team
* See the AUTHORS or Authors.txt file
*/
/*
* PARADEVS - the multimodeling and simulation environment
* This file is a part of the PARADEVS environment
*
* Copyright (C) 2013-2015 ULCO http://www.univ-litoral.fr
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
#ifndef TESTS_PLOT_GRAPH_MANAGER_HPP
#define TESTS_PLOT_GRAPH_MANAGER_HPP 1
#include
#include
#include
#include
#include
using namespace paradevs::tests::boost_graph;
namespace paradevs { namespace tests { namespace plot {
struct GraphParameters
{
OrientedGraph _graph;
InputEdges _input_edges;
OutputEdges _output_edges;
GraphParameters(const OrientedGraph& graph,
const InputEdges& input_edges,
const OutputEdges& output_edges) :
_graph(graph), _input_edges(input_edges), _output_edges(output_edges)
{ }
};
template < class Parameters >
class FlatGraphManager :
public paradevs::pdevs::GraphManager < common::DoubleTime,
Parameters >
{
public:
FlatGraphManager(common::Coordinator < common::DoubleTime >* coordinator,
const Parameters& parameters) :
paradevs::pdevs::GraphManager < common::DoubleTime, Parameters >(
coordinator, parameters)
{ }
virtual ~FlatGraphManager()
{
for (typename Simulators::const_iterator it =
_simulators.begin(); it != _simulators.end();
++it) {
delete it->second;
}
}
void build_flat_graph(const OrientedGraph& g, const InputEdges& inputs)
{
OrientedGraph::vertex_iterator vertexIt, vertexEnd;
boost::tie(vertexIt, vertexEnd) = boost::vertices(g);
for (; vertexIt != vertexEnd; ++vertexIt) {
std::ostringstream ss;
PlotParameters parameters(g[*vertexIt]._index,
g[*vertexIt]._points,
g[*vertexIt]._neighbour_number);
ss << "" << g[*vertexIt]._index;
// std::cout << "CREATE SIMULATOR: " << g[*vertexIt]._index
// << std::endl;
_simulators[g[*vertexIt]._index] = new Simulator(ss.str(),
parameters);
_simulators[g[*vertexIt]._index]->add_out_port("out");
_simulators[g[*vertexIt]._index]->add_in_port("in");
FlatGraphManager < Parameters >::add_child(
_simulators[g[*vertexIt]._index]);
}
boost::tie(vertexIt, vertexEnd) = boost::vertices(g);
for (; vertexIt != vertexEnd; ++vertexIt)
{
OrientedGraph::adjacency_iterator neighbourIt, neighbourEnd;
boost::tie(neighbourIt, neighbourEnd) =
boost::adjacent_vertices(*vertexIt, g);
for (; neighbourIt != neighbourEnd; ++neighbourIt) {
paradevs::common::Model < common::DoubleTime >* a = 0;
paradevs::common::Model < common::DoubleTime >* b = 0;
a = _simulators[g[*vertexIt]._index];
b = _simulators[g[*neighbourIt]._index];
FlatGraphManager < Parameters >::add_link(a, "out",
b, "in");
}
}
}
protected:
typedef pdevs::Simulator < common::DoubleTime,
Plot,
PlotParameters > Simulator;
typedef std::map < int, Simulator* > Simulators;
Simulators _simulators;
};
class BuiltFlatGraphManager :
public FlatGraphManager < GraphParameters >
{
public:
BuiltFlatGraphManager(
common::Coordinator < common::DoubleTime >* coordinator,
const GraphParameters& parameters) :
FlatGraphManager < GraphParameters >(
coordinator, parameters)
{
BuiltFlatGraphManager::build_flat_graph(
parameters._graph, parameters._input_edges);
// input
for (Edges::const_iterator it = parameters._input_edges.begin();
it != parameters._input_edges.end(); ++it) {
std::ostringstream ss_in;
ss_in << "in_" << it->first;
if (not coordinator->exist_in_port(ss_in.str())) {
coordinator->add_in_port(ss_in.str());
}
// std::cout << "CREATE LINK TO => " << it->second << " "
// << std::endl;
BuiltFlatGraphManager::add_link(
coordinator, ss_in.str(),
BuiltFlatGraphManager::_simulators[it->second], "in");
// BuiltFlatGraphManager::_simulators[
// parameters._graph[it->second]._index], "in");
}
// output
for (Edges::const_iterator it = parameters._output_edges.begin();
it != parameters._output_edges.end(); ++it) {
std::ostringstream ss_out;
ss_out << "out_" << it->first;
if (not coordinator->exist_out_port(ss_out.str())) {
coordinator->add_out_port(ss_out.str());
}
if (not BuiltFlatGraphManager::exist_link(
BuiltFlatGraphManager::_simulators[it->first],
"out", coordinator, ss_out.str())) {
BuiltFlatGraphManager::add_link(
BuiltFlatGraphManager::_simulators[it->first],
"out", coordinator, ss_out.str());
}
}
}
virtual ~BuiltFlatGraphManager()
{ }
};
class ParallelBuiltFlatGraphManager :
public FlatGraphManager < GraphParameters >
{
public:
ParallelBuiltFlatGraphManager(
common::Coordinator < common::DoubleTime >* coordinator,
const GraphParameters& parameters) :
FlatGraphManager < GraphParameters >(
coordinator, parameters)
{
ParallelBuiltFlatGraphManager::build_flat_graph(
parameters._graph, parameters._input_edges);
// input
for (Edges::const_iterator it = parameters._input_edges.begin();
it != parameters._input_edges.end(); ++it) {
std::ostringstream ss_in;
ss_in << "in_" << it->first;
if (not coordinator->exist_in_port(ss_in.str())) {
coordinator->add_in_port(ss_in.str());
}
ParallelBuiltFlatGraphManager::add_link(
coordinator, ss_in.str(),
ParallelBuiltFlatGraphManager::_simulators[it->second],
"in");
}
// output
for (Edges::const_iterator it = parameters._output_edges.begin();
it != parameters._output_edges.end(); ++it) {
std::ostringstream ss_out;
ss_out << "out_" << it->first;
if (not coordinator->exist_out_port(ss_out.str())) {
coordinator->add_out_port(ss_out.str());
}
if (not ParallelBuiltFlatGraphManager::exist_link(
ParallelBuiltFlatGraphManager::_simulators[it->first],
"out", coordinator, ss_out.str())) {
ParallelBuiltFlatGraphManager::add_link(
ParallelBuiltFlatGraphManager::_simulators[it->first],
"out", coordinator, ss_out.str());
}
}
}
void init()
{ }
void start(common::DoubleTime::type /* t */)
{ }
void transition(
const common::Models < common::DoubleTime >& /* receivers */,
common::DoubleTime::type /* t */)
{ }
virtual ~ParallelBuiltFlatGraphManager()
{ }
};
struct GraphManagerParameters
{
GraphManagerParameters(const std::string& file_name,
int cluster_number) :
cluster_number(cluster_number), file_name(file_name)
{ }
int cluster_number;
std::string file_name;
};
class HierarchicalGraphManager :
public paradevs::pdevs::GraphManager < common::DoubleTime,
GraphManagerParameters >
{
public:
HierarchicalGraphManager(
common::Coordinator < common::DoubleTime >* coordinator,
const GraphManagerParameters& parameters) :
paradevs::pdevs::GraphManager < common::DoubleTime,
GraphManagerParameters >(
coordinator, parameters)
{
GraphBuilder graph_builder(parameters.file_name,
parameters.cluster_number);
OrientedGraphs graphs;
InputEdgeList input_edges;
OutputEdgeList output_edges;
Connections parent_connections;
graph_builder.build(graphs, input_edges, output_edges,
parent_connections);
// build coordinators (graphs)
for (unsigned int i = 0; i < graphs.size(); ++i) {
Coordinator* coordinator = 0;
std::ostringstream ss;
ss << "S" << i;
coordinator =
new Coordinator(ss.str(), paradevs::common::NoParameters(),
GraphParameters(graphs[i],
input_edges[i],
output_edges[i]));
_coordinators.push_back(coordinator);
add_child(coordinator);
}
// builds internal connections (edges)
for (Connections::const_iterator it = parent_connections.begin();
it != parent_connections.end(); ++it) {
const Connection& connection = *it;
std::ostringstream ss_out;
std::ostringstream ss_in;
ss_out << "out_" << connection.first.second;
ss_in << "in_" << connection.first.second;
if (not exist_link(
_coordinators[connection.first.first - 1],
ss_out.str(),
_coordinators[connection.second.first - 1],
ss_in.str())) {
add_link(
_coordinators[connection.first.first - 1],
ss_out.str(),
_coordinators[connection.second.first - 1],
ss_in.str());
}
}
}
virtual ~HierarchicalGraphManager()
{
for (typename Coordinators::const_iterator it = _coordinators.begin();
it != _coordinators.end(); ++it) {
delete *it;
}
}
private:
typedef paradevs::pdevs::Coordinator <
common::DoubleTime,
BuiltFlatGraphManager,
common::NoParameters,
GraphParameters
> Coordinator;
typedef std::vector < Coordinator* > Coordinators;
Coordinators _coordinators;
};
class ParallelHierarchicalGraphManager :
public paradevs::pdevs::GraphManager < common::DoubleTime,
GraphManagerParameters >
{
public:
ParallelHierarchicalGraphManager(
common::Coordinator < common::DoubleTime >* coordinator,
const GraphManagerParameters& parameters) :
paradevs::pdevs::GraphManager < common::DoubleTime,
GraphManagerParameters >(
coordinator, parameters)
{
GraphBuilder graph_builder(parameters.file_name,
parameters.cluster_number);
OrientedGraphs graphs;
InputEdgeList input_edges;
OutputEdgeList output_edges;
Connections parent_connections;
graph_builder.build(graphs, input_edges, output_edges,
parent_connections);
// build coordinators (graphs)
for (unsigned int i = 0; i < graphs.size(); ++i) {
ParallelCoordinator* coordinator = 0;
std::ostringstream ss;
ss << "S" << i;
coordinator =
new ParallelCoordinator(ss.str(),
paradevs::common::NoParameters(),
GraphParameters(graphs[i],
input_edges[i],
output_edges[i]));
_coordinators.push_back(coordinator);
add_child(coordinator);
}
// builds internal connections (edges)
for (Connections::const_iterator it = parent_connections.begin();
it != parent_connections.end(); ++it) {
const Connection& connection = *it;
std::ostringstream ss_out;
std::ostringstream ss_in;
ss_out << "out_" << connection.first.second;
ss_in << "in_" << connection.first.second;
if (not exist_link(
_coordinators[connection.first.first - 1],
ss_out.str(),
_coordinators[connection.second.first - 1],
ss_in.str())) {
add_link(
_coordinators[connection.first.first - 1],
ss_out.str(),
_coordinators[connection.second.first - 1],
ss_in.str());
}
}
}
virtual ~ParallelHierarchicalGraphManager()
{
for (typename Coordinators::const_iterator it = _coordinators.begin();
it != _coordinators.end(); ++it) {
delete *it;
}
}
void init()
{
for (typename Coordinators::const_iterator it = _coordinators.begin();
it != _coordinators.end(); ++it) {
(*it)->set_sender(
dynamic_cast < paradevs::pdevs::multithreading::Coordinator <
common::DoubleTime,
ParallelHierarchicalGraphManager,
paradevs::common::NoParameters,
GraphManagerParameters >*
>(get_coordinator())->get_sender());
}
}
void start(common::DoubleTime::type t)
{
for (typename Coordinators::const_iterator it = _coordinators.begin();
it != _coordinators.end(); ++it) {
(*it)->get_sender().send(
paradevs::pdevs::multithreading::start_message <
paradevs::common::DoubleTime >(t));
}
}
void transition(const common::Models < common::DoubleTime >& receivers,
paradevs::common::DoubleTime::type t)
{
common::Models < common::DoubleTime >::const_iterator it =
receivers.begin();
while (it != receivers.end()) {
if (not (*it)->is_atomic()) {
typename Coordinators::const_iterator itc =
std::find(_coordinators.begin(), _coordinators.end(), *it);
(*itc)->get_sender().send(
paradevs::pdevs::multithreading::transition_message <
paradevs::common::DoubleTime >(t));
}
++it;
}
}
private:
typedef paradevs::pdevs::multithreading::Coordinator <
common::DoubleTime,
ParallelBuiltFlatGraphManager,
common::NoParameters,
GraphParameters
> ParallelCoordinator;
typedef std::vector < ParallelCoordinator* > Coordinators;
Coordinators _coordinators;
};
} } } // namespace paradevs tests plot
#endif