Index: trunk/FACT++/src/EventBuilderWrapper.h
===================================================================
--- trunk/FACT++/src/EventBuilderWrapper.h	(revision 16691)
+++ trunk/FACT++/src/EventBuilderWrapper.h	(revision 16694)
@@ -99,4 +99,5 @@
     Queue<vector<char>>                             fQueueRawData;
     Queue<tuple<Time,uint32_t,array<float,1440*4>>> fQueueEventData;
+    Queue<tuple<Time, array<uint32_t,40>, array<int16_t,160>>> fQueueTempRefClk;
 
     string   fPath;
@@ -206,13 +207,15 @@
                                                            "DNA of FAD boards"
                                                            "|DNA[hex]:Hex identifier of each FAD board"),
-        fDimTemperature ("FAD_CONTROL/TEMPERATURE",        "F:82",
+        fDimTemperature ("FAD_CONTROL/TEMPERATURE",        "S:1;F:160",
                                                            "FADs temperatures"
-                                                           "|temp[deg. C]:0 global min, 1-40 min, 41 global max, 42-81 max"),
+                                                           "|cnt[uint16]:Counter of averaged values",
+                                                           "|temp[deg C]:average temp of all DRS chips"),
         fDimPrescaler   ("FAD_CONTROL/PRESCALER",          "S:42",
                                                            "Trigger generator prescaler of fad boards"
                                                            "|prescaler[int]:Trigger generator prescaler value, for each board"),
-        fDimRefClock    ("FAD_CONTROL/REFERENCE_CLOCK",    "I:42",
+        fDimRefClock    ("FAD_CONTROL/REFERENCE_CLOCK",    "S:1;F:40",
                                                            "Reference clock of FAD boards"
-                                                           "|refClocks[t]:ref clocks of FAD boards. 40=min, 41=max"),
+                                                           "|cnt[uint16]:Counter of averaged values"
+                                                           "|clk[Hz]:Averaged clock of ref clocks of FAD boards"),
         fDimRoi         ("FAD_CONTROL/REGION_OF_INTEREST", "S:2",  "roi:|roi_rm:"),
         fDimDac         ("FAD_CONTROL/DAC",                "S:336",
@@ -243,4 +246,5 @@
         fQueueRawData(    std::bind(&EventBuilderWrapper::UpdateDimRawData,     this, placeholders::_1)),
         fQueueEventData(  std::bind(&EventBuilderWrapper::UpdateDimEventData,   this, placeholders::_1)),
+        fQueueTempRefClk( std::bind(&EventBuilderWrapper::UpdateDimTempRefClk,  this, placeholders::_1)),
         fNightAsInt(0), fRunInProgress(-1),
         fMaxEvent(make_pair(-FLT_MAX, array<float,1440*4>()))
@@ -641,13 +645,121 @@
     }
 
+    void UpdateDimTempRefClk(const tuple<Time, array<uint32_t,40>, array<int16_t,160>> &dat)
+    {
+        const Time &tm = get<0>(dat);
+
+        const array<uint32_t,40> &clk = get<1>(dat);
+        const array<int16_t,160> &tmp = get<2>(dat);
+
+        // --------------- RefClock ---------------
+
+        // history, add current data to history
+        static list<pair<Time,array<uint32_t,40>>> listclk;
+        listclk.emplace_back(tm, clk);
+
+        // --------------- Temperatures ---------------
+
+        // history, add current data to history
+        static list<pair<Time,array<int16_t,160>>> listtmp;
+        listtmp.emplace_back(tm, tmp);
+
+        // ========== Update dim services once a second =========
+
+        static Time oldt(boost::date_time::neg_infin);
+        Time newt;
+
+        if (newt<oldt+boost::posix_time::seconds(1))
+            return;
+
+        oldt = newt;
+
+        // --------------- RefClock ---------------
+
+        // remove expired data from history
+        while (1)
+        {
+            auto it=listclk.begin();
+            if (it==listclk.end() || it->first+boost::posix_time::seconds(1)>tm)
+                break;
+            listclk.pop_front();
+        }
+
+        // Structure for dim service
+        struct Clock
+        {
+            uint16_t num;
+            float val[40];
+            Clock() { memset(this, 0, sizeof(Clock)); }
+        } __attribute__((__packed__));
+
+        // Calculate average and fll structure
+        vector<uint16_t> clknum(40);
+
+        Clock avgclk;
+        avgclk.num = listclk.size();
+        for (auto it=listclk.begin(); it!=listclk.end(); it++)
+            for (int i=0; i<40; i++)
+                if (it->second[i]!=UINT32_MAX)
+                {
+                    avgclk.val[i] += it->second[i];
+                    clknum[i]++;
+                }
+        for (int i=0; i<40; i++)
+            avgclk.val[i] *= 2.048/clknum[i];
+
+        // Update dim service
+        fDimRefClock.setData(avgclk);
+        fDimRefClock.Update(tm);
+
+        // --------------- Temperatures ---------------
+
+        // remove expired data from history
+        while (1)
+        {
+            auto it=listtmp.begin();
+            if (it==listtmp.end() || it->first+boost::posix_time::seconds(5)>tm)
+                break;
+            listtmp.pop_front();
+        }
+
+        // Structure for dim service
+        struct Temp
+        {
+            uint16_t num;
+            float val[160];
+            Temp() { memset(this, 0, sizeof(Temp)); }
+        } __attribute__((__packed__));
+
+        // Calculate average and fll structure
+        vector<uint32_t> tmpnum(160);
+
+        Temp avgtmp;
+        avgtmp.num = listtmp.size();
+        for (auto it=listtmp.begin(); it!=listtmp.end(); it++)
+            for (int i=0; i<160; i++)
+                if (it->second[i]!=INT16_MIN)
+                {
+                    avgtmp.val[i] += it->second[i];
+                    tmpnum[i]++;
+                }
+        for (int i=0; i<160; i++)
+            avgtmp.val[i] /= tmpnum[i]*16;
+
+        // Update dim service
+        fDimTemperature.setData(avgtmp);
+        fDimTemperature.Update(tm);
+    }
+
     bool eventCheck(const EVT_CTRL2 &evt)
     {
         const EVENT *event = evt.fEvent;
 
+        const Time tm(evt.time);
+
 	const array<uint16_t,2> roi = {{ event->Roi, event->RoiTM }};
 
 	if (roi!=fVecRoi)
         {
-            fQueueRoi.emplace(Time(), roi);
+            fQueueRoi.emplace(tm, roi);
 	    fVecRoi = roi;
 	}
@@ -657,4 +769,17 @@
 
         // FIMXE: Compare with target configuration
+
+        // Copy data to array
+        array<uint32_t,40> clk;
+        array<int16_t,160> tmp;
+
+        for (int i=0; i<40; i++)
+            clk[i] = UINT32_MAX;
+
+        for (int i=0; i<160; i++)
+            tmp[i] = INT16_MIN;
+
+        //fill(clk.data(), clk.data()+ 40, UINT32_MAX);
+        //fill(tmp.data(), tmp.data()+160,  INT16_MIN);
 
         for (const FAD::EventHeader *ptr=beg; ptr!=end; ptr++)
@@ -667,4 +792,8 @@
                 continue;
             }
+
+            clk[ptr->Id()] = ptr->fFreqRefClock;
+            for (int i=0; i<4; i++)
+                tmp[ptr->Id()*4+i] = ptr->fTempDrs[i];
 
             if (beg->fStatus != ptr->fStatus)
@@ -700,4 +829,5 @@
             }
 
+            // FIXME: Check with first event!
             if (beg->fAdcClockPhaseShift != ptr->fAdcClockPhaseShift)
             {
@@ -706,4 +836,5 @@
             }
 
+            // FIXME: Check with first event!
             if (memcmp(beg->fDac, ptr->fDac, sizeof(beg->fDac)))
             {
@@ -718,4 +849,6 @@
             }
         }
+
+        fQueueTempRefClk.emplace(tm, clk, tmp);
 
         // check REFCLK_frequency
@@ -1171,67 +1304,4 @@
             Update(fDimDac, dacs, t);
         }
-
-        // -----------
-
-        static Time oldt(boost::date_time::neg_infin);
-        Time newt;
-
-        if (newt>oldt+boost::posix_time::seconds(1))
-        {
-            oldt = newt;
-
-            // --- RefClock
-
-            const array<uint32_t,42> clk = Compare(&fVecHeader[0], &fVecHeader[0].fFreqRefClock);
-            Update(fDimRefClock, clk, t);
-
-            // --- Temperatures
-
-            const array<int16_t,42> tmp[4] =
-            {
-                Compare(&fVecHeader[0], &fVecHeader[0].fTempDrs[0]),    // 0-39:val, 40:min, 41:max
-                Compare(&fVecHeader[0], &fVecHeader[0].fTempDrs[1]),    // 0-39:val, 40:min, 41:max
-                Compare(&fVecHeader[0], &fVecHeader[0].fTempDrs[2]),    // 0-39:val, 40:min, 41:max
-                Compare(&fVecHeader[0], &fVecHeader[0].fTempDrs[3])     // 0-39:val, 40:min, 41:max
-            };
-
-            vector<int16_t> data;
-            data.reserve(82);
-            data.push_back(tmp[0][40]);                                 // min: 0
-            data.insert(data.end(), tmp[0].data(), tmp[0].data()+40);   // val: 1-40
-            data.push_back(tmp[0][41]);                                 // max: 41
-            data.insert(data.end(), tmp[0].data(), tmp[0].data()+40);   // val: 42-81
-
-            for (int j=1; j<=3; j++)
-            {
-                const array<int16_t,42> &ref = tmp[j];
-
-                // Gloabl min
-                if (ref[40]<data[0])           // 40=min
-                    data[0] = ref[40];
-
-                // Global max
-                if (ref[41]>data[41])          // 41=max
-                    data[41] = ref[41];
-
-                for (int i=0; i<40; i++)
-                {
-                    // min per board
-                    if (ref[i]<data[i+1])      // data:  1-40
-                        data[i+1] = ref[i];    // ref:   0-39
-
-                    // max per board
-                    if (ref[i]>data[i+42])     // data: 42-81
-                        data[i+42] = ref[i];   // ref:   0-39
-                }
-            }
-
-            vector<float> deg(82);              //  0: global min,  1-40: min
-            for (int i=0; i<82; i++)            // 41: global max, 42-81: max
-                deg[i] = data[i]/16.;
-
-            fDimTemperature.setData(deg.data(), 82*sizeof(float));
-            fDimTemperature.Update(t);
-        }
     }
 
