Index: /library/bdm/mpdm/arx_agent.h
===================================================================
--- /library/bdm/mpdm/arx_agent.h (revision 787)
+++ /library/bdm/mpdm/arx_agent.h (revision 819)
@@ -22,4 +22,6 @@
 class ARXAgent : public Participant {
 	protected:
+		//! Pointers to neighbours
+		Array<string > neighbours;
 		
 		//! Internal ARX Controller
Index: /library/bdm/base/participants.h
===================================================================
--- /library/bdm/base/participants.h (revision 776)
+++ /library/bdm/base/participants.h (revision 819)
@@ -29,6 +29,4 @@
 	//! name - ID of the participant 
 	string name;
-	//! Pointers to neighbours
-	Array<string > neighbours;
 public:
 	//! Empty constructor
Index: /applications/doprava/traffic_agent.h
===================================================================
--- /applications/doprava/traffic_agent.h (revision 819)
+++ /applications/doprava/traffic_agent.h (revision 819)
@@ -0,0 +1,208 @@
+/*!
+  \file
+  \brief Traffic Light Agents 
+  \author Vaclav Smidl.
+*/
+
+#ifndef TRAGE_H
+#define TRAGE_H
+
+
+#include <base/participants.h>
+	
+using namespace bdm;
+
+//! detector of traffic variables
+class Detector{
+	public:
+		string name;             //! detector name
+		int distance;		     //! distance from stop-line
+		//! function loading info from Setting
+		void from_setting(const Setting &set){
+			UI::get(name,set,"name",UI::compulsory);
+			UI::get(distance,set,"distance",UI::compulsory);
+		}
+};
+
+//! detector fo incomming flow
+class DetectorIn : public Detector{
+	string from; // from agent
+	Array<string> to; // to signal plans
+	void from_setting(const Setting &set){
+		Detector::from_setting(set);
+		UI::get(from,set,"from",UI::compulsory);
+		UI::get(to, set, "to", UI::compulsory);
+	}
+};
+
+//! structure for output detectors
+class RequestOut {
+	public:
+	string to; // agent
+	Array<string> from; //detectors
+	void from_setting(const Setting &set){
+		UI::get(from,set,"from",UI::compulsory);
+		UI::get(to, set, "to", UI::compulsory);
+	}
+};
+
+
+//! class with physical information about a signal group
+class SignalGroup {
+	public:
+		string name;                 //! names of the group
+		Array<Detector> detectors;   //! (possible) detectors
+		
+		//! function that loads information from Setting
+		void from_setting(const Setting &set);		
+};
+
+//! class that operates on a signal group
+class SignalGroupHandler {
+	protected:
+		//! pointer to physical signal group
+		SignalGroup *sg;
+		
+	public:
+		//! actual data from the relevant signal group
+		vec det_data;
+		//! description of det_data
+		RV rv_det_data;
+		//! link from global measured data 
+		datalink ds2data;
+		//! link from data to global out_data
+		datalink data2out;
+	public:
+		SignalGroupHandler(SignalGroup *sg0, const string &agent_name):rv_det_data(){
+			sg=sg0;
+			for (int i=0;i<sg->detectors.length();i++){
+				rv_det_data.add(RV(agent_name + sg->detectors(i).name, 1)); //TODO intensity occupancy
+			}
+			
+		}
+		
+		//! arbitrary function that computes the need of the signal group for green light in common units (number of waiting cars?)
+		double expected_load(){
+			if (det_data.length()>0){
+				return det_data(0); // whatever
+			} else {
+				return 1.0; // mean value
+			}
+		}
+};
+
+class RequestHandler{
+	protected:
+		RequestOut *rq;
+	public:
+		RV rv;
+		datalink outdata2out;
+	public:
+		RequestHandler(RequestOut *rq0, const string &agent_name){
+			rq=rq0;
+			for (int i=0;i<rq->from.length();i++){
+				rv.add(RV(agent_name + rq->from(i), 1)); //TODO intensity occupancy
+			}
+		}
+};
+
+/*!
+\brief  Basic Traffic Agent
+
+*/
+class BaseTrafficAgent : public Participant {
+	protected:
+		//! Signal Groups
+		Array<SignalGroup> sg;
+
+		Array<SignalGroupHandler> sgh;
+										
+		//!data from messages
+		vec input_data;
+		
+		//! decription of msg_data
+		RV input_rv;
+		
+		//! data to broadcast
+		vec output_data;
+		
+		//! description of broadcast dataind
+		RV output_rv;
+			
+		RV action_rv;
+		
+		datalink_part action2ds;
+		
+		//! output recepient
+		Array<RequestOut> requests;
+		Array<RequestHandler> request_handler;
+		
+	public:
+		void validate(){
+			// write internal checks if all was loaded OK
+		}
+		void receive(const Setting &msg){
+			string what;
+			UI::get(what, msg, "what", UI::compulsory);
+			
+			if (what=="data"){ // 
+				// field data 
+				//! decription of detected data
+				shared_ptr<RV> rv=UI::build<RV>(msg,"rv",UI::compulsory);
+				ivec ind=rv->dataind(input_rv); // position of rv in in_rv;
+				if (ind.length()>0){ //data belong here
+					vec dt;
+					UI::get(dt, msg, "value",UI::compulsory);
+					set_subvector(input_data, ind,  dt); //check size?
+				}				
+			} else {
+				bdm_warning("Unknown message of type "+what);
+			}
+		}
+		void broadcast(Setting& set){
+			// broadcast data to all neighbours
+			for (int i=0; i<request_handler.length(); i++){
+				Setting &msg =set.add(Setting::TypeGroup);
+				RequestHandler &R=request_handler(i);
+				
+				// copy from create message
+				Setting &m_to=msg.add("to",Setting::TypeString);
+				m_to=requests(i).to;
+				Setting &m_what=msg.add("what",Setting::TypeString);
+				m_what="data";
+				//Setting &m_data=msg.add("data",Setting::TypeGroup);
+				Setting &m_rv=msg.add("rv",Setting::TypeGroup);
+				R.rv.to_setting(m_rv);
+				Setting &m_val=msg.add("value",Setting::TypeGroup);
+				vec val =R.outdata2out.pushdown(output_data);
+				UI::save(val, m_val);
+			}
+		}
+		void adapt(const vec &glob_dt){			
+			// copy data from global vector to sSGHandlers
+			for (int i=0; i<sgh.length();i++){
+				sgh(i).ds2data.filldown(glob_dt, sgh(i).det_data);
+			}
+			// copy sg_length ...
+		}
+		void act(vec &glob_ut){
+			vec needs(sgh.length());
+			for (int i=0; i<sgh.length();i++){
+				needs(i) = sgh(i).expected_load();
+			}
+			vec action = needs/sum(needs); // trivial stuff
+			action2ds.filldown(action,glob_ut);
+		}
+		
+		void ds_register(const DS &ds){
+			for (int i=0; i<sgh.length(); i++){
+				sgh(i).ds2data.set_connection(ds._drv(), sgh(i).rv_det_data);
+			}
+			action2ds.set_connection(action_rv, ds._urv());
+		}
+		
+		void from_setting(const Setting &set){};
+};
+UIREGISTER(BaseTrafficAgent);
+
+#endif //TRAGE_H
Index: /applications/doprava/Zlicin.cfg
===================================================================
--- /applications/doprava/Zlicin.cfg (revision 816)
+++ /applications/doprava/Zlicin.cfg (revision 819)
@@ -1,4 +1,5 @@
 agents = {
 { // agent 1
+	class = "BaseTrafficAgent";
   name = "495";
   sg = {
@@ -18,19 +19,20 @@
     }
   };
-  input = {
+  input = { // remote detectors 
     {
-      from = "601";
-      name = "DVA1";
+      name = "601DVA1";
+		distance = 100;
       to = {"VC","VD"};
     },
     {
-      from = "601";
-      name = "DVA";
+      name = "601DVA";
+		distance = 100;
       to = {"VC","VD"};
     }
   };
-  output = {
+  output = { // 
      {
-      from = {"DVC","DVD"};
+      from = "VC";
+		detector ="495DVC";
       to = "601";
       }
@@ -40,4 +42,5 @@
 },
 { // agent 2
+	class = "BaseTrafficAgent";
   name = "601";
   sg = {
Index: /applications/doprava/traffic_agent.cpp
===================================================================
--- /applications/doprava/traffic_agent.cpp (revision 819)
+++ /applications/doprava/traffic_agent.cpp (revision 819)
@@ -0,0 +1,17 @@
+#include "traffic_agent.h"
+
+void SignalGroup::from_setting(const libconfig::Setting& set)
+{
+UI::get(name,set, "name", UI::compulsory);
+UI::get(detectors, set, "detectors", UI::optional);
+//
+// TODO make some analysis of the detectors
+
+}
+
+void ARXAgent::from_setting(const libconfig::Setting& set)
+{
+    bdm::Participant::from_setting(set);
+	
+	
+}
Index: /applications/doprava/main_loop.cpp
===================================================================
--- /applications/doprava/main_loop.cpp (revision 814)
+++ /applications/doprava/main_loop.cpp (revision 819)
@@ -2,6 +2,6 @@
 /*!
 \file
-\brief Multi-Estimator (developped for PMSM)
-
+\brief Distributed Traffic light Control Scenario 
+\author Vasek Smidl 
 
  */
@@ -9,26 +9,81 @@
 #include "base/user_info.h"
 #include "base/loggers.h"
-#include "estim/kalman.h"
-#include "pmsmDS.h"
-#include "filters.h"
 #include "aimsun_bdm/aimsun_ds.h"
-
+#include "traffic_agent.h"
 
 using namespace bdm;
+
 int main ( int argc, char* argv[] ) {
 	const char *fname;
 	if ( argc>1 ) {fname = argv[1];	}
 	else { cout << "Missing configuration file.\n Usage: \n $> estimator config_file.cfg"<<endl; abort(); }
-	UIFile F ( fname );
+	UIFile Cfg ( fname );
 
-	AimsunDS DS;
-	shared_ptr<logger> L = UI::build <logger>( F, "logger" );
+	// SYSTEM TO CONTROL
+	AimsunDS Ds; //hard-coded so far
+
+	// AGENTS
+	Array<shared_ptr<Participant> > Ags;
+	UI::get ( Ags,Cfg, "agents" );
+
+	// LOGGER
+	shared_ptr<logger> L = UI::build <logger>( Cfg, "logger" );
+	if (!L) {L=new stdlog();} // DEFAULT LOGGER <== poor choice, use better ones
+
+	Config MsgStore;
+	MsgStore.setAutoConvert(true);
+	Setting& Queue = MsgStore.getRoot().add("queue", Setting::TypeList);
+
+	// REGISTER ACTIVE OBJECTS IN LOGGER
+	Ds.log_register ( *L, "DS" );
+	for ( int i=0; i<Ags.length(); i++ ) {
+		Ags ( i )->log_register ( *L,Ags(i)->_name() ); // estimate
+		Ags ( i )->ds_register(Ds);            // allows agents to update their datalinks
+	}
+	L->init();
+
+	vec glob_dt(Ds._drv()._dsize() );
+	vec glob_ut(Ds._urv()._dsize() );
+	for ( int tK=0;tK<Ds.max_length();tK++ ) {
+		Ds.log_write ( ); // write stuff to 
+		Ds.getdata(glob_dt);
+		
+		for ( int i=0; i<Ags.length(); i++ ) {
+			Ags(i) -> adapt(glob_dt);
+		}
+		for ( int i=0; i<Ags.length(); i++ ) {
+			Ags(i) -> broadcast(Queue);
+		}
+		// parse message queue
+		for ( int m=Queue.getLength()-1; m>=0; m-- ) { // go backwards - last mesages are discarded
+			for ( int i=0; i<Ags.length(); i++ ) {
+				Setting& msg=Queue[m];
+				string m_to=msg["to"];
+				if (m_to==Ags(i)->_name()) {
+					Ags(i)->receive(msg);
+					Queue.remove(m);
+					break;
+					// message delivered;
+				}
+			}
+		}
+		if (Queue.getLength()>0){bdm_error("undelivered messages - probably unknown neighbours");}
+		
+		for ( int i=0; i<Ags.length(); i++ ) {
+			Ags(i) -> act(glob_ut);
+		}
+		
+		L->step();
+		Ds.write(glob_ut);
+		Ds.step();							// simulator step
+		
+		for ( int i=0; i<Ags.length(); i++ ) {
+			Ags(i) -> step();
+		}
+		
+	}
 
 	L->finalize();
 
-	for (int i=0; i<nE; i++){
-		delete Dls(i);
-		delete Dlsc(i);
-	}
 	return 0;
 }
