#ifdef SYSTEMC
#ifndef morpheo_behavioural_Simulation_h
#define morpheo_behavioural_Simulation_h

/*
 * $Id: Simulation.h 138 2010-05-12 17:34:01Z rosiere $
 *
 * [ Description ]
 * 
 */

#include "Common/include/Debug.h"
#include "Behavioural/include/Model.h"
#include <stdint.h>
#include <systemc.h>
#include <vector>

namespace morpheo              {
namespace behavioural          {

  typedef enum
    {
      ALL_THREAD,
      EACH_THREAD_AND_CONTINUE,
      EACH_THREAD_AND_STOP
    } stop_type_t;

  extern bool                _simulation_stop_exception;
  extern double              _simulation_nb_cycle;
  extern double              _simulation_nb_instruction;
  extern std::vector<double> _simulation_nb_instruction_commited;
  extern stop_type_t         _simulation_stop_type;
  extern bool                _simulation_file_with_date;
  extern bool                _simulation_file_with_pid ;
  
  extern Model               _model;

  bool simulation_test_end (void);
  void simulation_init     (double      nb_cycle,
                            double      denug_nb_cycle,
                            double      nb_instruction,
                            stop_type_t stop_type,
                            bool        file_with_date,
                            bool        file_with_pid);
}; // end namespace behavioural          

  template<> inline std::string toString<morpheo::behavioural::stop_type_t>(const morpheo::behavioural::stop_type_t& x)
  {
    switch (x)
      {
      case morpheo::behavioural::ALL_THREAD               : return "all_thread"; break;
      case morpheo::behavioural::EACH_THREAD_AND_CONTINUE : return "each_thread_and_continue"; break;
      case morpheo::behavioural::EACH_THREAD_AND_STOP     : return "each_thread_and_stop"; break;
      default : return ""; break;
      }
  };

  template<> inline morpheo::behavioural::stop_type_t fromString<morpheo::behavioural::stop_type_t>(const std::string& x)
  {
    if ((x.compare(toString(static_cast<uint32_t>(morpheo::behavioural::ALL_THREAD))) == 0) or
        (x.compare(toString(                      morpheo::behavioural::ALL_THREAD )) == 0))
      return morpheo::behavioural::ALL_THREAD;

    if ((x.compare(toString(static_cast<uint32_t>(morpheo::behavioural::EACH_THREAD_AND_CONTINUE))) == 0) or
        (x.compare(toString(                      morpheo::behavioural::EACH_THREAD_AND_CONTINUE )) == 0))
      return morpheo::behavioural::EACH_THREAD_AND_CONTINUE;

    if ((x.compare(toString(static_cast<uint32_t>(morpheo::behavioural::EACH_THREAD_AND_STOP))) == 0) or
        (x.compare(toString(                      morpheo::behavioural::EACH_THREAD_AND_STOP )) == 0))
      return morpheo::behavioural::EACH_THREAD_AND_STOP;

    throw (ERRORMORPHEO ("fromString","Unknow string : \""+x+"\""));
  };

}; // end namespace morpheo              

#endif
#endif
