00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #ifndef UTAP_SIGNALFLOW_HH
00023 #define UTAP_SIGNALFLOW_HH
00024
00025 #include "utap/system.h"
00026 #include "utap/statement.h"
00027
00028 #include <list>
00029 #include <set>
00030 #include <map>
00031 #include <stack>
00032
00033 namespace UTAP
00034 {
00054 class SignalFlow: public StatementVisitor
00055 {
00056 public:
00057 struct less_str {
00058 bool operator() (const char* s1, const char* s2) const {
00059 return (strcmp(s1,s2)<0);
00060 }
00061 };
00062 typedef std::set<const char*, const less_str> strs_t;
00063 struct proc_t;
00064 typedef std::map<const proc_t*, strs_t> proc2strs_t;
00065 typedef std::map<const char*, strs_t> str2strs_t;
00066
00067 typedef struct proc_t {
00068 const char* name;
00069 strs_t inChans, outChans;
00070 str2strs_t rdVars, wtVars;
00071 proc2strs_t outEdges;
00072 proc_t(const char* _name): name(_name) {}
00073 };
00074 typedef std::set<proc_t*> procs_t;
00075 typedef std::map<const char*, procs_t, less_str> str2procs_t;
00076
00077 protected:
00078 int verbosity;
00079 const char* title;
00080 procs_t procs;
00081 str2procs_t receivers, transmiters;
00082 strs_t processes, channels, variables;
00083 proc_t* cTA;
00084 instance_t* cP;
00085 const char* cChan;
00086 bool inp, out, sync, paramsExpanded;
00087 std::stack<std::pair<bool, bool> > ioStack;
00088
00089 bool checkParams(const symbol_t &s);
00090 void addChan(const symbol_t &, strs_t &, str2procs_t&);
00091 void addVar(const symbol_t &, str2strs_t&, str2procs_t&);
00092 void visitProcess(instance_t &);
00093 void visitExpression(const expression_t &);
00094 void pushIO(){
00095 ioStack.push(std::make_pair<bool, bool>(inp, out));
00096 }
00097 void popIO() {
00098 inp = ioStack.top().first;
00099 out = ioStack.top().second;
00100 ioStack.pop();
00101 }
00102
00103 public:
00107 SignalFlow(const char* _title, TimedAutomataSystem& ta);
00108
00109 void setVerbose(int verbose) { verbosity = verbose; }
00113 virtual ~SignalFlow();
00114
00118 void printForTron(std::ostream &os);
00119
00126 void printForDot(std::ostream &os, bool ranked, bool erd, bool cEdged);
00127
00133 int32_t visitEmptyStatement(EmptyStatement *stat);
00134 int32_t visitExprStatement(ExprStatement *stat);
00135 int32_t visitForStatement(ForStatement *stat);
00136 int32_t visitIterationStatement(IterationStatement *stat);
00137 int32_t visitWhileStatement(WhileStatement *stat);
00138 int32_t visitDoWhileStatement(DoWhileStatement *stat);
00139 int32_t visitBlockStatement(BlockStatement *stat);
00140 int32_t visitSwitchStatement(SwitchStatement *stat);
00141 int32_t visitCaseStatement(CaseStatement *stat);
00142 int32_t visitDefaultStatement(DefaultStatement *stat);
00143 int32_t visitIfStatement(IfStatement *stat);
00144 int32_t visitBreakStatement(BreakStatement *stat);
00145 int32_t visitContinueStatement(ContinueStatement *stat);
00146 int32_t visitReturnStatement(ReturnStatement *stat);
00147 int32_t visitAssertStatement(UTAP::AssertStatement *stat);
00148 };
00149
00154 template <class T>
00155 struct print: public std::unary_function<T, void>
00156 {
00157 std::ostream& os;
00158 const char *infix;
00159 bool need;
00160 print(std::ostream& out, const char* sep):
00161 os(out), infix(sep), need(false) {}
00162 void operator()(const T& x)
00163 {
00164 if (need) os << infix;
00165 os << x; need = true;
00166 }
00167 };
00168
00169 inline std::ostream& operator<<(std::ostream& os, const SignalFlow::strs_t& s)
00170 {
00171 for_each(s.begin(), s.end(), print<const char*>(os, ", "));
00172 return os;
00173 }
00174
00175 inline std::ostream& operator<<(std::ostream& os, const SignalFlow::procs_t& ps)
00176 {
00177 SignalFlow::procs_t::const_iterator p=ps.begin(), e=ps.end();
00178 if (p!=e) { os << (*p)->name; ++p; }
00179 while (p!=e) { os << ", " << (*p)->name; ++p; }
00180 return os;
00181 }
00182
00208 class Partitioner: public SignalFlow
00209 {
00210 protected:
00211 procs_t procsEnv, procsIUT, procsBad;
00212 strs_t chansIntEnv, chansIntIUT, observable, chansBad;
00213 strs_t varsEnv, varsIUT, varsBad;
00214 strs_t chansInp, chansOut;
00215 const char* rule;
00216
00217 void addProcs(const strs_t& chans, const str2procs_t& index,
00218 procs_t& result, procs_t& exclude);
00219 void addIntChans(const procs_t& procs,
00220 strs_t& result, strs_t& exclude);
00221 void addIntVars(const procs_t& procs, strs_t& result,
00222 strs_t& exclude);
00223 void addProcsByVars(const strs_t& vars, procs_t& procs,
00224 procs_t& exclude);
00225 public:
00226 Partitioner(const char* _title, TimedAutomataSystem& ta):
00227 SignalFlow(_title, ta) {}
00228 ~Partitioner();
00229
00230 int partition(const strs_t& inputs, const strs_t& outputs);
00231 int partition(std::istream& ioinfo);
00232 void printForDot(std::ostream &os, bool ranked, bool erd, bool cEdged);
00233 void printViolation(const proc_t* process, const char* variable);
00234 void fillWithEnvProcs(strs_t& procs);
00235 void fillWithIUTProcs(strs_t& procs);
00236 };
00237 }
00238
00239 #endif