예제 #1
0
  void RuntimeSystem::addModule(const std::string& moduleClassName,
				int moduleID)
  {
    IModule* newModule = moduleFactory.buildNewModule(moduleClassName,
						      typeFactory);
    newModule->setID(moduleID);
		
    ModuleControlBlockPtr newBlock ( new ModuleControlBlock(newModule) );
		
    m_modules[moduleID] = newBlock;
    
    // no output or notdeterministic => module is a sink
    if (( newModule->getOutputs().size() == 0 ) ||
	( !newModule->isDeterministic()) ) 
      m_sinks.push_front(newBlock);
    
#if (ENGINE_VERBOSITY > 0)
    std::cout << "Added new Module (id " << moduleID << ") of Class " 
	      << moduleClassName << std::endl;
#endif
  }
예제 #2
0
  void RuntimeSystem::deleteModule(int moduleID)
  {
    // get the control block for the moduleid
    ControlBlockMap::iterator it = m_modules.find(moduleID);
    
    if (it == m_modules.end())
      {
	// a module with that id doesnt exist
	throw std::runtime_error("Module does not exist at "
				 "RuntimeSystem::deleteModule()");
      }

    // a module with that id must exist
    assert(it != m_modules.end());

    ModuleControlBlockPtr block = it->second;  
    IModule* n = block->module();

    // disconnect all modules that are connected to an output
    for (ControlBlockMap::iterator i = m_modules.begin(); 
	 i != m_modules.end(); ++i)
      {
	// is this possible?
	// if (i->second == 0) continue;
	assert(i->second != 0);

	ModuleControlBlockPtr block = i->second;
	IModule* m = block->module();	

	// check all inputs of that module
	for (unsigned int j = 0; j < m->getInputs().size(); ++j)
	  {
	    IModule::IInputPtr in = m->getInputs()[j];

	    // is it connected?
	    if (in->getConnectedModule() == n) 
	      {
		// yes, the unplug it
		in->unPlug();
		// and signal change
		block->hasChanged(j);
	      }
	  }
      }

    // disconnect all modules that are connected to an input
    for (unsigned int j = 0; j < n->getInputs().size(); ++j)
      {
	IModule::IInputPtr in = n->getInputs()[j];

	if (in->getConnectedModule() != 0)
	  in->unPlug();
      }
		
    // remove the module from the sink list	  

    if (n->getOutputs().size() == 0 || !n->isDeterministic())
	m_sinks.remove(block);

    // remove it from the module set
    // the module control block should be deleted here by its autoptr
    m_modules.erase(it);
		
#if (ENGINE_VERBOSITY > 0)
    std::cout << "Deleted Module # " << moduleID << std::endl;
#endif
  }
예제 #3
0
  void RuntimeSystem::update(IControlValueReceiver* cvr,
			     IModuleStatisticsReceiver* msr)
  {	
    std::stack<ModuleControlBlockPtr> stack;
    
    // push the sinks (modules with no output) on the stack
    for (std::list<ModuleControlBlockPtr>::iterator sink = m_sinks.begin();
	 sink != m_sinks.end(); ++sink)
      {
	(*sink)->activate();
	stack.push(*sink);
      }

#if (ENGINE_VERBOSITY > 2)
    std::cout << " ***** update begins\n";
    std::cout << "Pushed all m_sinks onto the stack." << std::endl;
    std::cout << "Number of m_sinks: " << m_sinks.size() << std::endl;
#endif
		
    while (!stack.empty())
      {
	ModuleControlBlockPtr block = stack.top();
			
	IModule* m = block->module();
			
	assert (block->isActive());

#if (ENGINE_VERBOSITY > 3)
        std::cout << "On Stack: " << m->getID() << "\n";
#endif
			
	IInput* dep = m->dependencies();
			
	// is there a not satisfied dependency left?
	if (dep != 0)
	  {
	    IModule* temp = dep->getConnectedModule();
	
	    // is the input connected to an other module?
	    if (temp != 0)
              {
#if (ENGINE_VERBOSITY > 3)
                std::cout << "   Following connection to " << temp->getID()
                          << "\n";
#endif    
		// check that module
		ModuleControlBlockPtr current = getControlBlock(temp);
		
		// 1. in case the module is on the stack we detected a cycle
		// the solution is to use the old value of that output
		// 2. the module is already updatet in this cycle
		// we dont want do update it again
		if (current->isActive()||(current->lastUpdated()==frameCount))
		  {
		    // it could be that the value changed (conservative)
		    block->setChanged(dep->getIndex());
#if (ENGINE_VERBOSITY > 3)
                    std::cout << "     [already done]" << temp->getID()
                              << "\n";
#endif    
		  }
		else
		  {
#if (ENGINE_VERBOSITY > 3)
                    std::cout << "     [pushed on stack]" << temp->getID()
                              << "\n";
#endif
		    // we must update this module
		    current->activate();
		    stack.push(current);		    
		  }
              }
	  }
	else
	  {
	    // all dependencies are satisfied

	    // is a update necessary?
	    if (!m->isDeterministic() || block->hasChanged())
	      {
#if (ENGINE_VERBOSITY > 3)
                std::cout << "   Updating...\n";
#endif    
		// lets update the module
		unsigned long startTime = utils::Timing::getTimeInMillis();
		//TODO: if an exception is caught, remove the module!
		try {
                  m->update();
		}
		catch (std::exception& e){
                  std::ostringstream os;
                  os << "error at update: " << e.what() << "\n"
                     << "module id = " << m->getID() << "\n"
                     << "module class = " << m->module_class_name() << "\n";

                  m_logger->error("Runtimesystem", os.str());
		}
		catch (...) {
                  std::ostringstream os;
                  os << "error at update\n"
                     << "module id = " << m->getID() << "\n"
                     << "module class = " << m->module_class_name() << "\n";

                  m_logger->error("Runtimesystem", os.str());
		}
		unsigned long stopTime = utils::Timing::getTimeInMillis();
		block->addTime(stopTime-startTime);
			
		// should we send the statistic data?
		// is there a receiver?
		// is it the right time?
		if (msr != 0 && (frameCount & 7) == 7)
		  {
		    // send statistic data
		    msr->modExecTimeSignal(m->getID(),block->avgTime());
		  }

		// send the changes values to the controlValueReceiver
		// and set them there to changed
		sendInputValues(block,cvr,m_modules,frameCount);
	      }
            else
              {
#if (ENGINE_VERBOSITY > 3)
                std::cout << "   Skipping update (deterministic and no "
                          << "needed input changed)...\n";
#endif    
              }
		
	    // this module is now updated
	    stack.pop(); 
	    block->reset();
	    block->updated(frameCount);
	  }
      }
		
    // all sinks are uptodate we can finish now
    // increase the timestamp
    ++frameCount;

#if (ENGINE_VERBOSITY > 2)
    std::cout << "**** update finished" << std::endl;
#endif
  }