mis.hpp
Go to the documentation of this file.
1 /**********************************************************************
2  * mis.hpp -- MoC interfaces for the SystemC map of the ForSyDe *
3  * library *
4  * *
5  * Authors: Gilmar Besera (gilmar@kth.se) *
6  * Hosein Attarzadeh (shan2@kth.se) *
7  * *
8  * Purpose: Providing MoC interfaces for ForSyDe-SystemC *
9  * *
10  * Usage: This file is included automatically *
11  * *
12  * License: BSD3 *
13  *******************************************************************/
14 
15 #ifndef MIS_HPP
16 #define MIS_HPP
17 
25 namespace ForSyDe
26 {
27 using namespace sc_core;
28 
30 enum A2DMode {LINEAR, HOLD};
31 
33 
40 class SY2CT : public process
41 {
42 public:
45 
47 
51  SY2CT(sc_module_name _name,
52  sc_time sample_period,
53  A2DMode op_mode = HOLD
54  ) : process(_name), iport1("iport1"), oport1("oport1"),
55  sample_period(sample_period), op_mode(op_mode)
56  {
57 #ifdef FORSYDE_INTROSPECTION
58  std::stringstream ss;
59  ss << sample_period;
60  arg_vec.push_back(std::make_tuple("sample_period", ss.str()));
61  ss.str("");
62  ss << op_mode;
63  arg_vec.push_back(std::make_tuple("op_mode", ss.str()));
64 #endif
65  }
66 
68  std::string forsyde_kind() const {return "MI::SY2CT";}
69 
70 private:
71  sc_time sample_period;
72  A2DMode op_mode;
73 
74  // Internal variables
75  CTTYPE previousVal, currentVal;
76  sub_signal subsig;
77  unsigned long iter;
78 
79  //Implementing the abstract semantics
80  void init()
81  {
82  currentVal = previousVal = 0;
83  iter = 0;
84  }
85 
86  void prep()
87  {
88  currentVal = (CTTYPE)from_abst_ext(iport1.read(), previousVal);
89  }
90 
91  void exec()
92  {
93  set_range(subsig, sample_period*iter, sample_period*(iter+1));
94  if(op_mode==HOLD)
95  {
96  CTTYPE pv = previousVal;
97  set_function(subsig,[pv](const sc_time& t)
98  {
99  return pv;
100  }
101  );
102  }
103  else
104  {
105  CTTYPE dv = currentVal - previousVal;
106  CTTYPE pv = previousVal;
107  unsigned long itr = iter;
108  sc_time sp = sample_period;
109  set_function(subsig,[pv,itr,sp,dv](const sc_time& t)
110  {
111  return (t-itr*sp)/sp*dv + pv;
112  });
113  }
114  }
115 
116  void prod()
117  {
118  WRITE_MULTIPORT(oport1, subsig)
119  wait(get_end_time(subsig) - sc_time_stamp());
120  iter++;
121  previousVal = currentVal;
122  }
123 
124  void clean() {}
125 
126 #ifdef FORSYDE_INTROSPECTION
127  void bindInfo()
128  {
129  boundInChans.resize(1); // only one input port
130  boundInChans[0].port = &iport1;
131  boundOutChans.resize(1); // only one output port
132  boundOutChans[0].port = &oport1;
133  }
134 #endif
135 };
136 
138 
142 class CT2SY : public process
143 {
144 public:
147 
149 
153  CT2SY(sc_module_name _name,
154  sc_time sample_period
155  ) : process(_name), iport1("iport1"), oport1("oport1"),
156  sample_period(sample_period)
157  {
158 #ifdef FORSYDE_INTROSPECTION
159  std::stringstream ss;
160  ss << sample_period;
161  arg_vec.push_back(std::make_tuple("sample_period", ss.str()));
162 #endif
163  }
164 
166  std::string forsyde_kind() const {return "MI::CT2SY";}
167 
168 private:
169  sc_time sample_period;
170 
171  // Internal variables
172  sub_signal in_ss;
173  CTTYPE out_val;
174  sc_time local_time, sampling_time;
175 
176  //Implementing the abstract semantics
177  void init()
178  {
179  local_time = sampling_time = SC_ZERO_TIME;
180  }
181 
182  void prep()
183  {
184  while (sampling_time >= local_time)
185  {
186  in_ss = iport1.read();
187  local_time = get_end_time(in_ss);
188  }
189  }
190 
191  void exec()
192  {
193  out_val = in_ss(sampling_time);
194  }
195 
196  void prod()
197  {
198  WRITE_MULTIPORT(oport1, out_val)
199  wait(sampling_time - sc_time_stamp());
200  sampling_time += sample_period;
201  }
202 
203  void clean() {}
204 
205 #ifdef FORSYDE_INTROSPECTION
206  void bindInfo()
207  {
208  boundInChans.resize(1); // only one input port
209  boundInChans[0].port = &iport1;
210  boundOutChans.resize(1); // only one output port
211  boundOutChans[0].port = &oport1;
212  }
213 #endif
214 };
215 
217 
221 template<class T>
222 class CT2DDE : public process
223 {
224 public:
228 
230 
234  CT2DDE(sc_module_name _name
235  ) : process(_name), iport1("iport1"), oport1("oport1")
236  {}
237 
239  std::string forsyde_kind() const {return "MI::CT2DDE";}
240 
241 private:
242  // Internal variables
243  sub_signal f;
244  std::vector<sub_signal > vecCTsignal; // a queue to be committed
245  //~ sub_signal in_val;
246  abst_ext<T> out_val;
247  sc_time samplingT;
248  unsigned int samplingType, iter;
249 
250  //Implementing the abstract semantics
251  void init()
252  {
253  iter = 0;
254  //~ in_val = iport1.read();
255  //~ cur_time = get_start_time(in_val);
256  }
257 
258  void prep()
259  {
260  //~ while (cur_time >= get_end_time(in_val)) in_val = iport1.read();
261  auto e = iport2.read();
262  samplingType = unsafe_from_abst_ext(get_value(e)); // FIXME: what if absent?
263  samplingT = get_time(e);
264  }
265 
266  void exec() {}
267 
268  void prod()
269  {
270  //FIXME: this code should be split between prep, prod, and probably exec
271  if(samplingType!=1)
272  {
273  // just sampling (without commitment) in
274  // adaptive mode '0', or non-adapitve mode '2'
275  if(iter==0)
276  {
277  f = iport1.read();
278  if(samplingType==0)
279  vecCTsignal.push_back(f);
280  }
281  if((samplingT >= get_start_time(f)) && (samplingT < get_end_time(f)))
282  {
283  WRITE_MULTIPORT(oport1,ttn_event<T>(f(samplingT), samplingT))
284  wait(samplingT - sc_time_stamp());
285  }
286  else if(samplingT >= get_end_time(f))
287  {
288  f = iport1.read();
289  if(samplingType==0)
290  vecCTsignal.push_back(f);
291  if ((samplingT >= get_start_time(f)) && (samplingT < get_end_time(f)))
292  {
293  WRITE_MULTIPORT(oport1,ttn_event<T>(f(samplingT), samplingT))
294  wait(samplingT - sc_time_stamp());
295  }
296  else
297  {
298  while(samplingT >= get_end_time(f))
299  {
300  f = iport1.read();
301  if(samplingType==0)
302  vecCTsignal.push_back(f);
303  }
304  WRITE_MULTIPORT(oport1,ttn_event<T>(f(samplingT), samplingT))
305  wait(samplingT - sc_time_stamp());
306  }
307  }
308  else
309  {
310  // To check the sampling from the queue
311  while(!vecCTsignal.empty())
312  {
313  if(samplingT >= get_end_time(vecCTsignal.front()))
314  vecCTsignal.erase(vecCTsignal.begin());
315  else
316  {
317  WRITE_MULTIPORT(oport1,ttn_event<T>(vecCTsignal.front()(samplingT), samplingT))
318  wait(samplingT - sc_time_stamp());
319  break;
320  }
321  }
322  if(vecCTsignal.empty())
323  assert(0); // if have not get the sampling
324  }
325  }
326  else
327  {
328  // a commitment event in adaptive mode '1'
329  while(!vecCTsignal.empty())
330  {
331  if(samplingT >= get_end_time(vecCTsignal.front()))
332  vecCTsignal.erase(vecCTsignal.begin());
333  else
334  break;
335  }
336  if(vecCTsignal.empty())
337  assert(0); // if have not get the sampling
338  }
339  iter++;
340  }
341 
342  void clean() {}
343 
344 #ifdef FORSYDE_INTROSPECTION
345  void bindInfo()
346  {
347  boundInChans.resize(2); // only one input port
348  boundInChans[0].port = &iport1;
349  boundInChans[1].port = &iport2;
350  boundOutChans.resize(1); // only one output port
351  boundOutChans[0].port = &oport1;
352  }
353 #endif
354 };
355 
357 
361 template<class T>
362 class CT2DDEf : public process
363 {
364 public:
367 
369 
373  CT2DDEf(sc_module_name _name,
374  sc_time samp_period
375  ) : process(_name), iport1("iport1"), oport1("oport1"), samp_period(samp_period)
376  {}
377 
379  std::string forsyde_kind() const {return "MI::CT2DDEf";}
380 
381 private:
382  // Internal variables
383  sc_time samp_period;
384  abst_ext<T> out_val;
385  sc_time local_time, sampling_time;
386  sub_signal in_ss;
387 
388  //Implementing the abstract semantics
389  void init()
390  {
391  local_time = sampling_time = SC_ZERO_TIME;
392  }
393 
394  void prep()
395  {
396  while (sampling_time >= local_time)
397  {
398  in_ss = iport1.read();
399  local_time = get_end_time(in_ss);
400  }
401  }
402 
403  void exec()
404  {
405  out_val = abst_ext<T>(in_ss(sampling_time));
406  }
407 
408  void prod()
409  {
410  WRITE_MULTIPORT(oport1,ttn_event<T>(out_val, sampling_time))
411  wait(sampling_time - sc_time_stamp());
412  sampling_time += samp_period;
413  }
414 
415  void clean() {}
416 
417 #ifdef FORSYDE_INTROSPECTION
418  void bindInfo()
419  {
420  boundInChans.resize(1); // only one input port
421  boundInChans[0].port = &iport1;
422  boundOutChans.resize(1); // only one output port
423  boundOutChans[0].port = &oport1;
424  }
425 #endif
426 };
427 
429 
436 template<class T>
437 class DDE2CT : public process
438 {
439 public:
442 
444 
448  DDE2CT(sc_module_name _name,
449  A2DMode op_mode = HOLD
450  ) : process(_name), iport1("iport1"), oport1("oport1"),
451  op_mode(op_mode)
452  {
453 #ifdef FORSYDE_INTROSPECTION
454  std::stringstream ss;
455  ss << op_mode;
456  arg_vec.push_back(std::make_tuple("op_mode", ss.str()));
457 #endif
458  }
459 
461  std::string forsyde_kind() const {return "MI::DDE2CT";}
462 
463 private:
464  A2DMode op_mode;
465 
466  // Internal variables
467  CTTYPE previousVal, currentVal;
468  sc_time previousT, currentT;
469  sub_signal subsig;
470 
471  //Implementing the abstract semantics
472  void init()
473  {
474  previousVal = currentVal = 0;
475  previousT = currentT = SC_ZERO_TIME;
476  }
477 
478  void prep()
479  {
480  while (currentT <= previousT)
481  {
482  auto in_ev = iport1.read();
483  currentVal = (double)from_abst_ext(get_value(in_ev), previousVal);
484  currentT = get_time(in_ev);
485  }
486  }
487 
488  void exec()
489  {
490  set_range(subsig, previousT, currentT);
491  if(op_mode==HOLD)
492  {
493  CTTYPE pv = previousVal;
494  set_function(subsig,[=](sc_time t){
495  return pv;
496  });
497  }
498  else
499  {
500  CTTYPE dv = currentVal - previousVal;
501  sc_time dt = currentT - previousT;
502  sc_time pt = previousT;
503  CTTYPE pv = previousVal;
504  set_function(subsig,[=](sc_time t)->CTTYPE{
505  return ((t-pt)/dt*dv + pv);
506  });
507  }
508  }
509 
510  void prod()
511  {
512  WRITE_MULTIPORT(oport1, subsig)
513  wait(get_end_time(subsig) - sc_time_stamp());
514  previousVal = currentVal;
515  previousT = currentT;
516  }
517 
518  void clean() {}
519 
520 #ifdef FORSYDE_INTROSPECTION
521  void bindInfo()
522  {
523  boundInChans.resize(1); // only one input port
524  boundInChans[0].port = &iport1;
525  boundOutChans.resize(1); // only one output port
526  boundOutChans[0].port = &oport1;
527  }
528 #endif
529 };
530 
532 
535 template<class T>
536 class SY2SDF : public process
537 {
538 public:
541 
543 
547  SY2SDF(sc_module_name _name
548  ) : process(_name), iport1("iport1"), oport1("oport1")
549  {
550 #ifdef FORSYDE_INTROSPECTION
551  std::stringstream ss;
552  ss << 1;
553  arg_vec.push_back(std::make_tuple("o1toks", ss.str()));
554 #endif
555  }
556 
558  std::string forsyde_kind() const {return "MI::SY2SDF";}
559 
560 private:
561 
562  // Internal variables
563  T* val;
564 
565  //Implementing the abstract semantics
566  void init()
567  {
568  val = new T;
569  }
570 
571  void prep()
572  {
573  auto tok = iport1.read();
574  while (is_absent(tok))
575  tok = iport1.read();
576  *val = unsafe_from_abst_ext(tok);
577  }
578 
579  void exec() {}
580 
581  void prod()
582  {
583  WRITE_MULTIPORT(oport1, *val)
584  }
585 
586  void clean()
587  {
588  delete val;
589  }
590 
591 #ifdef FORSYDE_INTROSPECTION
592  void bindInfo()
593  {
594  boundInChans.resize(1); // only one input port
595  boundInChans[0].port = &iport1;
596  boundOutChans.resize(1); // only one output port
597  boundOutChans[0].port = &oport1;
598  }
599 #endif
600 };
601 
603 
606 template<class T>
607 class SDF2SY : public process
608 {
609 public:
612 
614 
618  SDF2SY(sc_module_name _name
619  ) : process(_name), iport1("iport1"), oport1("oport1")
620  {
621 #ifdef FORSYDE_INTROSPECTION
622  std::stringstream ss;
623  ss << 1;
624  arg_vec.push_back(std::make_tuple("i1toks", ss.str()));
625 #endif
626  }
627 
629  std::string forsyde_kind() const {return "MI::SDF2SY";}
630 
631 private:
632 
633  // Internal variables
634  T* val;
635 
636  //Implementing the abstract semantics
637  void init()
638  {
639  val = new T;
640  }
641 
642  void prep()
643  {
644  *val = iport1.read();
645  }
646 
647  void exec() {}
648 
649  void prod()
650  {
651  WRITE_MULTIPORT(oport1, abst_ext<T>(*val))
652  }
653 
654  void clean() {}
655 
656 #ifdef FORSYDE_INTROSPECTION
657  void bindInfo()
658  {
659  boundInChans.resize(1); // only one input port
660  boundInChans[0].port = &iport1;
661  boundOutChans.resize(1); // only one output port
662  boundOutChans[0].port = &oport1;
663  }
664 #endif
665 };
666 
668 
671 template<class T>
672 class SY2DDE : public process
673 {
674 public:
677 
679 
683  SY2DDE(sc_module_name _name,
684  sc_time sample_period
685  ) : process(_name), iport1("iport1"), oport1("oport1"),
686  sample_period(sample_period)
687  {
688 #ifdef FORSYDE_INTROSPECTION
689  std::stringstream ss;
690  ss << sample_period;
691  arg_vec.push_back(std::make_tuple("sample_period", ss.str()));
692 #endif
693  }
694 
696  std::string forsyde_kind() const {return "MI::SY2DDE";}
697 
698 private:
699  sc_time sample_period;
700 
701  // Internal variables
702  abst_ext<T>* tok;
703  T* val;
704  sc_time cur_time;
705 
706  //Implementing the abstract semantics
707  void init()
708  {
709  tok = new abst_ext<T>();
710  val = new T;
711  cur_time = SC_ZERO_TIME;
712  }
713 
714  void prep()
715  {
716  *tok = iport1.read();
717  if (is_present(*tok))
718  *val = unsafe_from_abst_ext(*tok);
719  }
720 
721  void exec() {}
722 
723  void prod()
724  {
725  WRITE_MULTIPORT(oport1, tt_event<T>(*val,cur_time))
726  wait(cur_time - sc_time_stamp());
727  cur_time += sample_period;
728  }
729 
730  void clean()
731  {
732  delete val;
733  delete tok;
734  }
735 
736 #ifdef FORSYDE_INTROSPECTION
737  void bindInfo()
738  {
739  boundInChans.resize(1); // only one input port
740  boundInChans[0].port = &iport1;
741  boundOutChans.resize(1); // only one output port
742  boundOutChans[0].port = &oport1;
743  }
744 #endif
745 };
746 
748 
751 template<class T>
752 class DDE2SY : public process
753 {
754 public:
757 
759 
763  DDE2SY(sc_module_name _name,
764  sc_time sample_period
765  ) : process(_name), iport1("iport1"), oport1("oport1"),
766  sample_period(sample_period)
767  {
768 #ifdef FORSYDE_INTROSPECTION
769  std::stringstream ss;
770  ss << sample_period;
771  arg_vec.push_back(std::make_tuple("sample_period", ss.str()));
772 #endif
773  }
774 
776  std::string forsyde_kind() const {return "MI::DDE2SY";}
777 
778 private:
779  sc_time sample_period;
780 
781  // Internal variables
782  tt_event<T>* tok;
783  T* prev_val;
784  sc_time cur_time;
785 
786  //Implementing the abstract semantics
787  void init()
788  {
789  tok = new tt_event<T>();
790  prev_val = new T;
791  cur_time = SC_ZERO_TIME;
792  *tok = iport1.read();
793  }
794 
795  void prep()
796  {
797  while (get_time(*tok) <= cur_time)
798  {
799  *prev_val = get_value(*tok);
800  *tok = iport1.read();
801  }
802  }
803 
804  void exec() {}
805 
806  void prod()
807  {
808  WRITE_MULTIPORT(oport1, abst_ext<T>(*prev_val))
809  cur_time += sample_period;
810  }
811 
812  void clean() {}
813 
814 #ifdef FORSYDE_INTROSPECTION
815  void bindInfo()
816  {
817  boundInChans.resize(1); // only one input port
818  boundInChans[0].port = &iport1;
819  boundOutChans.resize(1); // only one output port
820  boundOutChans[0].port = &oport1;
821  }
822 #endif
823 };
824 
825 }
826 
827 #endif
Time-tagged data types.
Definition: tt_event.hpp:32
SDF::SDF_in< T > iport1
port for the input channel
Definition: mis.hpp:610
SY2SDF(sc_module_name _name)
The constructor requires the module name.
Definition: mis.hpp:547
The sub-signal type used to construct a CT signal.
Definition: sub_signal.hpp:38
DDE::DDE_in< T > iport1
port for the input channel
Definition: mis.hpp:755
SY::SY_out< CTTYPE > oport1
port for the output channel
Definition: mis.hpp:146
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:696
CT2SY(sc_module_name _name, sc_time sample_period)
The constructor requires the module name.
Definition: mis.hpp:153
double CTTYPE
Type of the values used in the CT MoC (currently fixed)
Definition: sub_signal.hpp:27
DDE2CT(sc_module_name _name, A2DMode op_mode=HOLD)
The constructor requires the module name.
Definition: mis.hpp:448
The namespace for ForSyDe.
Definition: abssemantics.hpp:30
Process constructor for a DDE2CT MoC interfaces.
Definition: mis.hpp:437
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:629
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:776
SDF::SDF_out< T > oport1
port for the output channel
Definition: mis.hpp:540
A2DMode
Operation modes for the SY2CT converter.
Definition: mis.hpp:30
Process constructor for a SY2DDE MoC interfaces.
Definition: mis.hpp:672
CT::CT_in iport1
port for the input channel
Definition: mis.hpp:365
SY::SY_out< T > oport1
port for the output channel
Definition: mis.hpp:611
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:68
CT::CT_in iport1
port for the input channel
Definition: mis.hpp:145
The UT_out port is used for output ports of UT processes.
Definition: ut_process.hpp:68
The CT_out port is used for output ports of CT processes.
Definition: ct_process.hpp:64
SDF2SY(sc_module_name _name)
The constructor requires the module name.
Definition: mis.hpp:618
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:379
SY::SY_in< T > iport1
port for the input channel
Definition: mis.hpp:539
Process constructor for a SY2SDF MoC interfaces.
Definition: mis.hpp:536
DDE::DDE_out< T > oport1
port for the output channel
Definition: mis.hpp:676
SY::SY_out< T > oport1
port for the output channel
Definition: mis.hpp:756
Process constructor for a SDF2SY MoC interface.
Definition: mis.hpp:607
CT::CT_out oport1
port for the output channel
Definition: mis.hpp:44
Process constructor for a CT2DDE MoC interface.
Definition: mis.hpp:222
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:166
DDE::DDE_out< T > oport1
port for the output channel
Definition: mis.hpp:227
The process constructor which defines the abstract semantics of execution.
Definition: abssemantics.hpp:212
CT2DDEf(sc_module_name _name, sc_time samp_period)
The constructor requires the module name.
Definition: mis.hpp:373
SY2CT(sc_module_name _name, sc_time sample_period, A2DMode op_mode=HOLD)
The constructor requires the module name.
Definition: mis.hpp:51
Process constructor for a CT2SY MoC interface.
Definition: mis.hpp:142
CT2DDE(sc_module_name _name)
The constructor requires the module name.
Definition: mis.hpp:234
Absent-extended data types.
Definition: abst_ext.hpp:32
CT::CT_in iport1
port for the input channel
Definition: mis.hpp:225
DDE2SY(sc_module_name _name, sc_time sample_period)
The constructor requires the module name.
Definition: mis.hpp:763
Process constructor for a CT2DDEf MoC interface.
Definition: mis.hpp:362
The UT_in port is used for input ports of UT processes.
Definition: ut_process.hpp:55
The CT_in port is used for input ports of CT processes.
Definition: ct_process.hpp:53
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:461
DDE::DDE_out< T > oport1
port for the output channel
Definition: mis.hpp:366
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:558
The DDE_out port is used for output ports of DDE processes.
Definition: dde_process.hpp:69
DDE::DDE_in< unsigned int > iport2
port for the sampling channel
Definition: mis.hpp:226
Process constructor for a SY2CT MoC interfaces.
Definition: mis.hpp:40
DDE::DDE_in< T > iport1
port for the input channel
Definition: mis.hpp:440
std::string forsyde_kind() const
Specifying from which process constructor is the module built.
Definition: mis.hpp:239
SY::SY_in< CTTYPE > iport1
port for the input channel
Definition: mis.hpp:43
SY2DDE(sc_module_name _name, sc_time sample_period)
The constructor requires the module name.
Definition: mis.hpp:683
SY::SY_in< T > iport1
port for the input channel
Definition: mis.hpp:675
Process constructor for a DDE2SY MoC interface.
Definition: mis.hpp:752
CT::CT_out oport1
port for the output channel
Definition: mis.hpp:441